Import Debian changes 4.92-8+deb10u3
[hcoop/debian/exim4.git] / src / routers / rf_get_munge_headers.c
CommitLineData
420a0d19
CE
1/*************************************************
2* Exim - an Internet mail transport agent *
3*************************************************/
4
2ea97746 5/* Copyright (c) University of Cambridge 1995 - 2018 */
420a0d19
CE
6/* See the file NOTICE for conditions of use and distribution. */
7
8#include "../exim.h"
9#include "rf_functions.h"
10
11
12/*************************************************
13* Get additional headers for a router *
14*************************************************/
15
16/* This function is called by routers to sort out the additional headers
17and header remove list for a particular address.
18
19Arguments:
20 addr the input address
21 rblock the router instance
22 extra_headers points to where to hang the header chain
23 remove_headers points to where to hang the remove list
24
25Returns: OK if no problem
26 DEFER if expanding a string caused a deferment
27 or a big disaster (e.g. expansion failure)
28*/
29
30int
31rf_get_munge_headers(address_item *addr, router_instance *rblock,
32 header_line **extra_headers, uschar **remove_headers)
33{
34/* Default is to retain existing headers */
2ea97746 35*extra_headers = addr->prop.extra_headers;
420a0d19
CE
36
37if (rblock->extra_headers)
38 {
2ea97746 39 const uschar * list = rblock->extra_headers;
420a0d19
CE
40 int sep = '\n';
41 uschar * s;
42 int slen;
43
44 while ((s = string_nextinlist(&list, &sep, NULL, 0)))
45 if (!(s = expand_string(s)))
46 {
2ea97746 47 if (!f.expand_string_forcedfail)
420a0d19 48 {
2ea97746
CE
49 addr->message = string_sprintf(
50 "%s router failed to expand add_headers item \"%s\": %s",
51 rblock->name, s, expand_string_message);
420a0d19
CE
52 return DEFER;
53 }
54 }
55 else if ((slen = Ustrlen(s)) > 0)
56 {
57 /* Expand succeeded. Put extra headers at the start of the chain because
58 further down it may point to headers from other routers, which may be
59 shared with other addresses. The output function outputs them in reverse
60 order. */
61
62 header_line * h = store_get(sizeof(header_line));
63
64 /* We used to use string_sprintf() to add the newline if needed, but that
65 causes problems if the header line is exceedingly long (e.g. adding
66 something to a pathologically long line). So avoid it. */
67
68 if (s[slen-1] == '\n')
69 h->text = s;
70 else
71 {
72 h->text = store_get(slen+2);
73 memcpy(h->text, s, slen);
74 h->text[slen++] = '\n';
75 h->text[slen] = 0;
76 }
77
78 h->next = *extra_headers;
79 h->type = htype_other;
80 h->slen = slen;
81 *extra_headers = h;
82 }
83 }
84
85/* Default is to retain existing removes */
2ea97746 86*remove_headers = addr->prop.remove_headers;
420a0d19
CE
87
88/* Expand items from colon-sep list separately, then build new list */
89if (rblock->remove_headers)
90 {
2ea97746 91 const uschar * list = rblock->remove_headers;
420a0d19
CE
92 int sep = ':';
93 uschar * s;
2ea97746 94 gstring * g = NULL;
420a0d19 95
2ea97746
CE
96 if (*remove_headers)
97 g = string_cat(NULL, *remove_headers);
98
99 while ((s = string_nextinlist(&list, &sep, NULL, 0)))
420a0d19
CE
100 if (!(s = expand_string(s)))
101 {
2ea97746 102 if (!f.expand_string_forcedfail)
420a0d19 103 {
2ea97746
CE
104 addr->message = string_sprintf(
105 "%s router failed to expand remove_headers item \"%s\": %s",
106 rblock->name, s, expand_string_message);
420a0d19
CE
107 return DEFER;
108 }
109 }
110 else if (*s)
2ea97746
CE
111 g = string_append_listele(g, ':', s);
112
113 if (g)
114 *remove_headers = g->s;
420a0d19
CE
115 }
116
117return OK;
118}
119
2ea97746
CE
120/* vi: aw ai sw=2
121*/
420a0d19 122/* End of rf_get_munge_headers.c */