Postfix3.3.1
header_opts.c
[詳解]
1 /*++
2 /* NAME
3 /* header_opts 3
4 /* SUMMARY
5 /* message header classification
6 /* SYNOPSIS
7 /* #include <header_opts.h>
8 /*
9 /* const HEADER_OPTS *header_opts_find(string)
10 /* const char *string;
11 /* DESCRIPTION
12 /* header_opts_find() takes a message header line and looks up control
13 /* information for the corresponding header type.
14 /* DIAGNOSTICS
15 /* Panic: input is not a valid header line. The result is a pointer
16 /* to HEADER_OPTS in case of success, a null pointer when the header
17 /* label was not recognized.
18 /* SEE ALSO
19 /* header_opts(3h) the gory details
20 /* LICENSE
21 /* .ad
22 /* .fi
23 /* The Secure Mailer license must be distributed with this software.
24 /* AUTHOR(S)
25 /* Wietse Venema
26 /* IBM T.J. Watson Research
27 /* P.O. Box 704
28 /* Yorktown Heights, NY 10598, USA
29 /*--*/
30 
31 /* System library. */
32 
33 #include <sys_defs.h>
34 #include <ctype.h>
35 
36 /* Utility library. */
37 
38 #include <msg.h>
39 #include <htable.h>
40 #include <vstring.h>
41 #include <stringops.h>
42 #include <argv.h>
43 #include <mymalloc.h>
44 
45 /* Global library. */
46 
47 #include <mail_params.h>
48 #include <header_opts.h>
49 
50  /*
51  * Header names are given in the preferred capitalization. The lookups are
52  * case-insensitive.
53  *
54  * XXX Removing Return-Path: headers should probably be done only with mail
55  * that enters via a non-SMTP channel. Changing this now could break other
56  * software. See also comments in bounce_notify_util.c.
57  */
58 static HEADER_OPTS header_opts[] = {
59  "Apparently-To", HDR_APPARENTLY_TO, HDR_OPT_RECIP,
60  "Bcc", HDR_BCC, HDR_OPT_XRECIP,
61  "Cc", HDR_CC, HDR_OPT_XRECIP,
62  "Content-Description", HDR_CONTENT_DESCRIPTION, HDR_OPT_MIME,
63  "Content-Disposition", HDR_CONTENT_DISPOSITION, HDR_OPT_MIME,
64  "Content-ID", HDR_CONTENT_ID, HDR_OPT_MIME,
65  "Content-Length", HDR_CONTENT_LENGTH, 0,
66  "Content-Transfer-Encoding", HDR_CONTENT_TRANSFER_ENCODING, HDR_OPT_MIME,
67  "Content-Type", HDR_CONTENT_TYPE, HDR_OPT_MIME,
68  "Delivered-To", HDR_DELIVERED_TO, 0,
69  "Disposition-Notification-To", HDR_DISP_NOTIFICATION, HDR_OPT_SENDER,
70  "Date", HDR_DATE, 0,
71  "Errors-To", HDR_ERRORS_TO, HDR_OPT_SENDER,
72  "From", HDR_FROM, HDR_OPT_SENDER,
73  "Mail-Followup-To", HDR_MAIL_FOLLOWUP_TO, HDR_OPT_SENDER,
74  "Message-Id", HDR_MESSAGE_ID, 0,
75  "MIME-Version", HDR_MIME_VERSION, HDR_OPT_MIME,
76  "Received", HDR_RECEIVED, 0,
77  "Reply-To", HDR_REPLY_TO, HDR_OPT_SENDER,
78  "Resent-Bcc", HDR_RESENT_BCC, HDR_OPT_XRECIP | HDR_OPT_RR,
79  "Resent-Cc", HDR_RESENT_CC, HDR_OPT_XRECIP | HDR_OPT_RR,
80  "Resent-Date", HDR_RESENT_DATE, HDR_OPT_RR,
81  "Resent-From", HDR_RESENT_FROM, HDR_OPT_SENDER | HDR_OPT_RR,
82  "Resent-Message-Id", HDR_RESENT_MESSAGE_ID, HDR_OPT_RR,
83  "Resent-Reply-To", HDR_RESENT_REPLY_TO, HDR_OPT_RECIP | HDR_OPT_RR,
84  "Resent-Sender", HDR_RESENT_SENDER, HDR_OPT_SENDER | HDR_OPT_RR,
85  "Resent-To", HDR_RESENT_TO, HDR_OPT_XRECIP | HDR_OPT_RR,
86  "Return-Path", HDR_RETURN_PATH, HDR_OPT_SENDER,
87  "Return-Receipt-To", HDR_RETURN_RECEIPT_TO, HDR_OPT_SENDER,
88  "Sender", HDR_SENDER, HDR_OPT_SENDER,
89  "To", HDR_TO, HDR_OPT_XRECIP,
90 };
91 
92 #define HEADER_OPTS_SIZE (sizeof(header_opts) / sizeof(header_opts[0]))
93 
94 static HTABLE *header_hash; /* quick lookup */
95 static VSTRING *header_key;
96 
97 /* header_opts_init - initialize */
98 
99 static void header_opts_init(void)
100 {
101  const HEADER_OPTS *hp;
102  const char *cp;
103 
104  /*
105  * Build a hash table for quick lookup, and allocate memory for
106  * lower-casing the lookup key.
107  */
108  header_key = vstring_alloc(10);
109  header_hash = htable_create(HEADER_OPTS_SIZE);
110  for (hp = header_opts; hp < header_opts + HEADER_OPTS_SIZE; hp++) {
111  VSTRING_RESET(header_key);
112  for (cp = hp->name; *cp; cp++)
113  VSTRING_ADDCH(header_key, TOLOWER(*cp));
114  VSTRING_TERMINATE(header_key);
115  htable_enter(header_hash, vstring_str(header_key), (void *) hp);
116  }
117 }
118 
119 /* header_drop_init - initialize "header drop" flags */
120 
121 static void header_drop_init(void)
122 {
123  ARGV *hdr_drop_list;
124  char **cpp;
125  HTABLE_INFO *ht;
126  HEADER_OPTS *hp;
127 
128  /*
129  * Having one main.cf parameter for the "drop" header flag does not
130  * generalize to the "sender", "extract", etc., flags. Flags would need
131  * to be grouped by header name, but that would be unwieldy, too:
132  *
133  * message_header_flags = { apparently-to = recipient }, { bcc = recipient,
134  * extract, drop }, { from = sender }, ...
135  *
136  * Thus, it is unlikely that all header flags will become configurable.
137  */
138  hdr_drop_list = argv_split(var_drop_hdrs, CHARS_COMMA_SP);
139  for (cpp = hdr_drop_list->argv; *cpp; cpp++) {
140  lowercase(*cpp);
141  if ((ht = htable_locate(header_hash, *cpp)) == 0) {
142  hp = (HEADER_OPTS *) mymalloc(sizeof(*hp));
143  hp->type = HDR_OTHER;
144  hp->flags = HDR_OPT_DROP;
145  ht = htable_enter(header_hash, *cpp, (void *) hp);
146  hp->name = ht->key;
147  } else
148  hp = (HEADER_OPTS *) ht->value;
149  hp->flags |= HDR_OPT_DROP;
150  }
151  argv_free(hdr_drop_list);
152 }
153 
154 /* header_opts_find - look up header options */
155 
156 const HEADER_OPTS *header_opts_find(const char *string)
157 {
158  const char *cp;
159 
160  if (header_hash == 0) {
161  header_opts_init();
162  header_drop_init();
163  }
164 
165  /*
166  * Look up the lower-cased version of the header name.
167  */
168  VSTRING_RESET(header_key);
169  for (cp = string; *cp != ':'; cp++) {
170  if (*cp == 0)
171  msg_panic("header_opts_find: no colon in header: %.30s", string);
172  VSTRING_ADDCH(header_key, TOLOWER(*cp));
173  }
174  vstring_truncate(header_key,
175  trimblanks(vstring_str(header_key), cp - string)
176  - vstring_str(header_key));
177  VSTRING_TERMINATE(header_key);
178  return ((const HEADER_OPTS *) htable_find(header_hash, vstring_str(header_key)));
179 }
#define HDR_CONTENT_DESCRIPTION
Definition: header_opts.h:53
#define HDR_SENDER
Definition: header_opts.h:50
void * value
Definition: htable.h:18
#define HDR_OPT_DROP
Definition: header_opts.h:62
HTABLE_INFO * htable_locate(HTABLE *table, const char *key)
Definition: htable.c:242
ARGV * argv_free(ARGV *argvp)
Definition: argv.c:136
Definition: argv.h:17
NORETURN msg_panic(const char *fmt,...)
Definition: msg.c:295
#define HDR_RETURN_PATH
Definition: header_opts.h:48
#define vstring_str(vp)
Definition: vstring.h:71
#define HDR_RESENT_FROM
Definition: header_opts.h:43
#define HDR_RESENT_REPLY_TO
Definition: header_opts.h:45
#define HDR_DATE
Definition: header_opts.h:33
char ** argv
Definition: argv.h:20
#define HDR_DISP_NOTIFICATION
Definition: header_opts.h:57
VSTRING * vstring_truncate(VSTRING *vp, ssize_t len)
Definition: vstring.c:415
#define HDR_MESSAGE_ID
Definition: header_opts.h:37
char * var_drop_hdrs
Definition: mail_params.c:348
Definition: htable.h:25
#define HDR_TO
Definition: header_opts.h:51
#define HDR_ERRORS_TO
Definition: header_opts.h:35
#define HDR_RESENT_SENDER
Definition: header_opts.h:46
#define HDR_OPT_SENDER
Definition: header_opts.h:63
#define VSTRING_TERMINATE(vp)
Definition: vstring.h:74
const char * name
Definition: header_opts.h:17
HTABLE * htable_create(ssize_t size)
Definition: htable.c:179
#define VSTRING_ADDCH(vp, ch)
Definition: vstring.h:81
#define HDR_APPARENTLY_TO
Definition: header_opts.h:27
#define HDR_OPT_RECIP
Definition: header_opts.h:64
#define HDR_CC
Definition: header_opts.h:29
#define HDR_RESENT_TO
Definition: header_opts.h:47
#define HDR_RETURN_RECEIPT_TO
Definition: header_opts.h:49
#define HDR_OTHER
Definition: header_opts.h:26
#define HDR_MIME_VERSION
Definition: header_opts.h:56
#define HDR_BCC
Definition: header_opts.h:28
#define HDR_RESENT_DATE
Definition: header_opts.h:42
#define VSTRING_RESET(vp)
Definition: vstring.h:77
#define HDR_CONTENT_LENGTH
Definition: header_opts.h:30
#define HDR_FROM
Definition: header_opts.h:36
char * key
Definition: htable.h:17
VSTRING * vstring_alloc(ssize_t len)
Definition: vstring.c:353
#define HDR_RECEIVED
Definition: header_opts.h:38
#define HDR_CONTENT_ID
Definition: header_opts.h:55
void * htable_find(HTABLE *table, const char *key)
Definition: htable.c:227
char * lowercase(char *string)
Definition: lowercase.c:34
char * trimblanks(char *, ssize_t)
Definition: trimblanks.c:37
#define HDR_CONTENT_TRANSFER_ENCODING
Definition: header_opts.h:31
#define CHARS_COMMA_SP
Definition: sys_defs.h:1761
ARGV * argv_split(const char *, const char *)
Definition: argv_split.c:63
#define HDR_RESENT_CC
Definition: header_opts.h:41
#define HEADER_OPTS_SIZE
Definition: header_opts.c:92
#define HDR_CONTENT_DISPOSITION
Definition: header_opts.h:54
#define HDR_MAIL_FOLLOWUP_TO
Definition: header_opts.h:52
#define HDR_REPLY_TO
Definition: header_opts.h:39
#define HDR_RESENT_BCC
Definition: header_opts.h:40
#define TOLOWER(c)
Definition: sys_defs.h:1755
#define HDR_DELIVERED_TO
Definition: header_opts.h:34
const HEADER_OPTS * header_opts_find(const char *string)
Definition: header_opts.c:156
#define HDR_OPT_XRECIP
Definition: header_opts.h:69
#define HDR_OPT_RR
Definition: header_opts.h:65
#define HDR_OPT_MIME
Definition: header_opts.h:67
void * mymalloc(ssize_t len)
Definition: mymalloc.c:150
#define HDR_RESENT_MESSAGE_ID
Definition: header_opts.h:44
HTABLE_INFO * htable_enter(HTABLE *table, const char *key, void *value)
Definition: htable.c:212
#define HDR_CONTENT_TYPE
Definition: header_opts.h:32