ad97f6fef15375c96880ee6ca86c2155a711d4cb
[exim.git] / src / src / expand.c
1 /*************************************************
2 * Exim - an Internet mail transport agent *
3 *************************************************/
4
5 /* Copyright (c) University of Cambridge 1995 - 2014 */
6 /* See the file NOTICE for conditions of use and distribution. */
7
8
9 /* Functions for handling string expansion. */
10
11
12 #include "exim.h"
13
14 /* Recursively called function */
15
16 static uschar *expand_string_internal(const uschar *, BOOL, const uschar **, BOOL, BOOL, BOOL *);
17 static int_eximarith_t expanded_string_integer(const uschar *, BOOL);
18
19 #ifdef STAND_ALONE
20 #ifndef SUPPORT_CRYPTEQ
21 #define SUPPORT_CRYPTEQ
22 #endif
23 #endif
24
25 #ifdef LOOKUP_LDAP
26 #include "lookups/ldap.h"
27 #endif
28
29 #ifdef SUPPORT_CRYPTEQ
30 #ifdef CRYPT_H
31 #include <crypt.h>
32 #endif
33 #ifndef HAVE_CRYPT16
34 extern char* crypt16(char*, char*);
35 #endif
36 #endif
37
38 /* The handling of crypt16() is a mess. I will record below the analysis of the
39 mess that was sent to me. We decided, however, to make changing this very low
40 priority, because in practice people are moving away from the crypt()
41 algorithms nowadays, so it doesn't seem worth it.
42
43 <quote>
44 There is an algorithm named "crypt16" in Ultrix and Tru64. It crypts
45 the first 8 characters of the password using a 20-round version of crypt
46 (standard crypt does 25 rounds). It then crypts the next 8 characters,
47 or an empty block if the password is less than 9 characters, using a
48 20-round version of crypt and the same salt as was used for the first
49 block. Charaters after the first 16 are ignored. It always generates
50 a 16-byte hash, which is expressed together with the salt as a string
51 of 24 base 64 digits. Here are some links to peruse:
52
53 http://cvs.pld.org.pl/pam/pamcrypt/crypt16.c?rev=1.2
54 http://seclists.org/bugtraq/1999/Mar/0076.html
55
56 There's a different algorithm named "bigcrypt" in HP-UX, Digital Unix,
57 and OSF/1. This is the same as the standard crypt if given a password
58 of 8 characters or less. If given more, it first does the same as crypt
59 using the first 8 characters, then crypts the next 8 (the 9th to 16th)
60 using as salt the first two base 64 digits from the first hash block.
61 If the password is more than 16 characters then it crypts the 17th to 24th
62 characters using as salt the first two base 64 digits from the second hash
63 block. And so on: I've seen references to it cutting off the password at
64 40 characters (5 blocks), 80 (10 blocks), or 128 (16 blocks). Some links:
65
66 http://cvs.pld.org.pl/pam/pamcrypt/bigcrypt.c?rev=1.2
67 http://seclists.org/bugtraq/1999/Mar/0109.html
68 http://h30097.www3.hp.com/docs/base_doc/DOCUMENTATION/HTML/AA-Q0R2D-
69 TET1_html/sec.c222.html#no_id_208
70
71 Exim has something it calls "crypt16". It will either use a native
72 crypt16 or its own implementation. A native crypt16 will presumably
73 be the one that I called "crypt16" above. The internal "crypt16"
74 function, however, is a two-block-maximum implementation of what I called
75 "bigcrypt". The documentation matches the internal code.
76
77 I suspect that whoever did the "crypt16" stuff for Exim didn't realise
78 that crypt16 and bigcrypt were different things.
79
80 Exim uses the LDAP-style scheme identifier "{crypt16}" to refer
81 to whatever it is using under that name. This unfortunately sets a
82 precedent for using "{crypt16}" to identify two incompatible algorithms
83 whose output can't be distinguished. With "{crypt16}" thus rendered
84 ambiguous, I suggest you deprecate it and invent two new identifiers
85 for the two algorithms.
86
87 Both crypt16 and bigcrypt are very poor algorithms, btw. Hashing parts
88 of the password separately means they can be cracked separately, so
89 the double-length hash only doubles the cracking effort instead of
90 squaring it. I recommend salted SHA-1 ({SSHA}), or the Blowfish-based
91 bcrypt ({CRYPT}$2a$).
92 </quote>
93 */
94
95
96
97 #ifndef nelements
98 # define nelements(arr) (sizeof(arr) / sizeof(*arr))
99 #endif
100
101 /*************************************************
102 * Local statics and tables *
103 *************************************************/
104
105 /* Table of item names, and corresponding switch numbers. The names must be in
106 alphabetical order. */
107
108 static uschar *item_table[] = {
109 US"acl",
110 US"certextract",
111 US"dlfunc",
112 US"extract",
113 US"filter",
114 US"hash",
115 US"hmac",
116 US"if",
117 US"length",
118 US"listextract",
119 US"lookup",
120 US"map",
121 US"nhash",
122 US"perl",
123 US"prvs",
124 US"prvscheck",
125 US"readfile",
126 US"readsocket",
127 US"reduce",
128 US"run",
129 US"sg",
130 US"sort",
131 US"substr",
132 US"tr" };
133
134 enum {
135 EITEM_ACL,
136 EITEM_CERTEXTRACT,
137 EITEM_DLFUNC,
138 EITEM_EXTRACT,
139 EITEM_FILTER,
140 EITEM_HASH,
141 EITEM_HMAC,
142 EITEM_IF,
143 EITEM_LENGTH,
144 EITEM_LISTEXTRACT,
145 EITEM_LOOKUP,
146 EITEM_MAP,
147 EITEM_NHASH,
148 EITEM_PERL,
149 EITEM_PRVS,
150 EITEM_PRVSCHECK,
151 EITEM_READFILE,
152 EITEM_READSOCK,
153 EITEM_REDUCE,
154 EITEM_RUN,
155 EITEM_SG,
156 EITEM_SORT,
157 EITEM_SUBSTR,
158 EITEM_TR };
159
160 /* Tables of operator names, and corresponding switch numbers. The names must be
161 in alphabetical order. There are two tables, because underscore is used in some
162 cases to introduce arguments, whereas for other it is part of the name. This is
163 an historical mis-design. */
164
165 static uschar *op_table_underscore[] = {
166 US"from_utf8",
167 US"local_part",
168 US"quote_local_part",
169 US"reverse_ip",
170 US"time_eval",
171 US"time_interval"
172 #ifdef EXPERIMENTAL_INTERNATIONAL
173 ,US"utf8_domain_from_alabel",
174 US"utf8_domain_to_alabel",
175 US"utf8_localpart_from_alabel",
176 US"utf8_localpart_to_alabel"
177 #endif
178 };
179
180 enum {
181 EOP_FROM_UTF8,
182 EOP_LOCAL_PART,
183 EOP_QUOTE_LOCAL_PART,
184 EOP_REVERSE_IP,
185 EOP_TIME_EVAL,
186 EOP_TIME_INTERVAL
187 #ifdef EXPERIMENTAL_INTERNATIONAL
188 ,EOP_UTF8_DOMAIN_FROM_ALABEL,
189 EOP_UTF8_DOMAIN_TO_ALABEL,
190 EOP_UTF8_LOCALPART_FROM_ALABEL,
191 EOP_UTF8_LOCALPART_TO_ALABEL
192 #endif
193 };
194
195 static uschar *op_table_main[] = {
196 US"address",
197 US"addresses",
198 US"base62",
199 US"base62d",
200 US"domain",
201 US"escape",
202 US"eval",
203 US"eval10",
204 US"expand",
205 US"h",
206 US"hash",
207 US"hex2b64",
208 US"hexquote",
209 US"l",
210 US"lc",
211 US"length",
212 US"listcount",
213 US"listnamed",
214 US"mask",
215 US"md5",
216 US"nh",
217 US"nhash",
218 US"quote",
219 US"randint",
220 US"rfc2047",
221 US"rfc2047d",
222 US"rxquote",
223 US"s",
224 US"sha1",
225 US"sha256",
226 US"stat",
227 US"str2b64",
228 US"strlen",
229 US"substr",
230 US"uc",
231 US"utf8clean" };
232
233 enum {
234 EOP_ADDRESS = sizeof(op_table_underscore)/sizeof(uschar *),
235 EOP_ADDRESSES,
236 EOP_BASE62,
237 EOP_BASE62D,
238 EOP_DOMAIN,
239 EOP_ESCAPE,
240 EOP_EVAL,
241 EOP_EVAL10,
242 EOP_EXPAND,
243 EOP_H,
244 EOP_HASH,
245 EOP_HEX2B64,
246 EOP_HEXQUOTE,
247 EOP_L,
248 EOP_LC,
249 EOP_LENGTH,
250 EOP_LISTCOUNT,
251 EOP_LISTNAMED,
252 EOP_MASK,
253 EOP_MD5,
254 EOP_NH,
255 EOP_NHASH,
256 EOP_QUOTE,
257 EOP_RANDINT,
258 EOP_RFC2047,
259 EOP_RFC2047D,
260 EOP_RXQUOTE,
261 EOP_S,
262 EOP_SHA1,
263 EOP_SHA256,
264 EOP_STAT,
265 EOP_STR2B64,
266 EOP_STRLEN,
267 EOP_SUBSTR,
268 EOP_UC,
269 EOP_UTF8CLEAN };
270
271
272 /* Table of condition names, and corresponding switch numbers. The names must
273 be in alphabetical order. */
274
275 static uschar *cond_table[] = {
276 US"<",
277 US"<=",
278 US"=",
279 US"==", /* Backward compatibility */
280 US">",
281 US">=",
282 US"acl",
283 US"and",
284 US"bool",
285 US"bool_lax",
286 US"crypteq",
287 US"def",
288 US"eq",
289 US"eqi",
290 US"exists",
291 US"first_delivery",
292 US"forall",
293 US"forany",
294 US"ge",
295 US"gei",
296 US"gt",
297 US"gti",
298 US"inlist",
299 US"inlisti",
300 US"isip",
301 US"isip4",
302 US"isip6",
303 US"ldapauth",
304 US"le",
305 US"lei",
306 US"lt",
307 US"lti",
308 US"match",
309 US"match_address",
310 US"match_domain",
311 US"match_ip",
312 US"match_local_part",
313 US"or",
314 US"pam",
315 US"pwcheck",
316 US"queue_running",
317 US"radius",
318 US"saslauthd"
319 };
320
321 enum {
322 ECOND_NUM_L,
323 ECOND_NUM_LE,
324 ECOND_NUM_E,
325 ECOND_NUM_EE,
326 ECOND_NUM_G,
327 ECOND_NUM_GE,
328 ECOND_ACL,
329 ECOND_AND,
330 ECOND_BOOL,
331 ECOND_BOOL_LAX,
332 ECOND_CRYPTEQ,
333 ECOND_DEF,
334 ECOND_STR_EQ,
335 ECOND_STR_EQI,
336 ECOND_EXISTS,
337 ECOND_FIRST_DELIVERY,
338 ECOND_FORALL,
339 ECOND_FORANY,
340 ECOND_STR_GE,
341 ECOND_STR_GEI,
342 ECOND_STR_GT,
343 ECOND_STR_GTI,
344 ECOND_INLIST,
345 ECOND_INLISTI,
346 ECOND_ISIP,
347 ECOND_ISIP4,
348 ECOND_ISIP6,
349 ECOND_LDAPAUTH,
350 ECOND_STR_LE,
351 ECOND_STR_LEI,
352 ECOND_STR_LT,
353 ECOND_STR_LTI,
354 ECOND_MATCH,
355 ECOND_MATCH_ADDRESS,
356 ECOND_MATCH_DOMAIN,
357 ECOND_MATCH_IP,
358 ECOND_MATCH_LOCAL_PART,
359 ECOND_OR,
360 ECOND_PAM,
361 ECOND_PWCHECK,
362 ECOND_QUEUE_RUNNING,
363 ECOND_RADIUS,
364 ECOND_SASLAUTHD
365 };
366
367
368 /* Types of table entry */
369
370 enum vtypes {
371 vtype_int, /* value is address of int */
372 vtype_filter_int, /* ditto, but recognized only when filtering */
373 vtype_ino, /* value is address of ino_t (not always an int) */
374 vtype_uid, /* value is address of uid_t (not always an int) */
375 vtype_gid, /* value is address of gid_t (not always an int) */
376 vtype_bool, /* value is address of bool */
377 vtype_stringptr, /* value is address of pointer to string */
378 vtype_msgbody, /* as stringptr, but read when first required */
379 vtype_msgbody_end, /* ditto, the end of the message */
380 vtype_msgheaders, /* the message's headers, processed */
381 vtype_msgheaders_raw, /* the message's headers, unprocessed */
382 vtype_localpart, /* extract local part from string */
383 vtype_domain, /* extract domain from string */
384 vtype_string_func, /* value is string returned by given function */
385 vtype_todbsdin, /* value not used; generate BSD inbox tod */
386 vtype_tode, /* value not used; generate tod in epoch format */
387 vtype_todel, /* value not used; generate tod in epoch/usec format */
388 vtype_todf, /* value not used; generate full tod */
389 vtype_todl, /* value not used; generate log tod */
390 vtype_todlf, /* value not used; generate log file datestamp tod */
391 vtype_todzone, /* value not used; generate time zone only */
392 vtype_todzulu, /* value not used; generate zulu tod */
393 vtype_reply, /* value not used; get reply from headers */
394 vtype_pid, /* value not used; result is pid */
395 vtype_host_lookup, /* value not used; get host name */
396 vtype_load_avg, /* value not used; result is int from os_getloadavg */
397 vtype_pspace, /* partition space; value is T/F for spool/log */
398 vtype_pinodes, /* partition inodes; value is T/F for spool/log */
399 vtype_cert /* SSL certificate */
400 #ifndef DISABLE_DKIM
401 ,vtype_dkim /* Lookup of value in DKIM signature */
402 #endif
403 };
404
405 /* Type for main variable table */
406
407 typedef struct {
408 const char *name;
409 enum vtypes type;
410 void *value;
411 } var_entry;
412
413 /* Type for entries pointing to address/length pairs. Not currently
414 in use. */
415
416 typedef struct {
417 uschar **address;
418 int *length;
419 } alblock;
420
421 static uschar * fn_recipients(void);
422
423 /* This table must be kept in alphabetical order. */
424
425 static var_entry var_table[] = {
426 /* WARNING: Do not invent variables whose names start acl_c or acl_m because
427 they will be confused with user-creatable ACL variables. */
428 { "acl_arg1", vtype_stringptr, &acl_arg[0] },
429 { "acl_arg2", vtype_stringptr, &acl_arg[1] },
430 { "acl_arg3", vtype_stringptr, &acl_arg[2] },
431 { "acl_arg4", vtype_stringptr, &acl_arg[3] },
432 { "acl_arg5", vtype_stringptr, &acl_arg[4] },
433 { "acl_arg6", vtype_stringptr, &acl_arg[5] },
434 { "acl_arg7", vtype_stringptr, &acl_arg[6] },
435 { "acl_arg8", vtype_stringptr, &acl_arg[7] },
436 { "acl_arg9", vtype_stringptr, &acl_arg[8] },
437 { "acl_narg", vtype_int, &acl_narg },
438 { "acl_verify_message", vtype_stringptr, &acl_verify_message },
439 { "address_data", vtype_stringptr, &deliver_address_data },
440 { "address_file", vtype_stringptr, &address_file },
441 { "address_pipe", vtype_stringptr, &address_pipe },
442 { "authenticated_fail_id",vtype_stringptr, &authenticated_fail_id },
443 { "authenticated_id", vtype_stringptr, &authenticated_id },
444 { "authenticated_sender",vtype_stringptr, &authenticated_sender },
445 { "authentication_failed",vtype_int, &authentication_failed },
446 #ifdef WITH_CONTENT_SCAN
447 { "av_failed", vtype_int, &av_failed },
448 #endif
449 #ifdef EXPERIMENTAL_BRIGHTMAIL
450 { "bmi_alt_location", vtype_stringptr, &bmi_alt_location },
451 { "bmi_base64_tracker_verdict", vtype_stringptr, &bmi_base64_tracker_verdict },
452 { "bmi_base64_verdict", vtype_stringptr, &bmi_base64_verdict },
453 { "bmi_deliver", vtype_int, &bmi_deliver },
454 #endif
455 { "body_linecount", vtype_int, &body_linecount },
456 { "body_zerocount", vtype_int, &body_zerocount },
457 { "bounce_recipient", vtype_stringptr, &bounce_recipient },
458 { "bounce_return_size_limit", vtype_int, &bounce_return_size_limit },
459 { "caller_gid", vtype_gid, &real_gid },
460 { "caller_uid", vtype_uid, &real_uid },
461 { "compile_date", vtype_stringptr, &version_date },
462 { "compile_number", vtype_stringptr, &version_cnumber },
463 { "config_dir", vtype_stringptr, &config_main_directory },
464 { "config_file", vtype_stringptr, &config_main_filename },
465 { "csa_status", vtype_stringptr, &csa_status },
466 #ifdef EXPERIMENTAL_DCC
467 { "dcc_header", vtype_stringptr, &dcc_header },
468 { "dcc_result", vtype_stringptr, &dcc_result },
469 #endif
470 #ifdef WITH_OLD_DEMIME
471 { "demime_errorlevel", vtype_int, &demime_errorlevel },
472 { "demime_reason", vtype_stringptr, &demime_reason },
473 #endif
474 #ifndef DISABLE_DKIM
475 { "dkim_algo", vtype_dkim, (void *)DKIM_ALGO },
476 { "dkim_bodylength", vtype_dkim, (void *)DKIM_BODYLENGTH },
477 { "dkim_canon_body", vtype_dkim, (void *)DKIM_CANON_BODY },
478 { "dkim_canon_headers", vtype_dkim, (void *)DKIM_CANON_HEADERS },
479 { "dkim_copiedheaders", vtype_dkim, (void *)DKIM_COPIEDHEADERS },
480 { "dkim_created", vtype_dkim, (void *)DKIM_CREATED },
481 { "dkim_cur_signer", vtype_stringptr, &dkim_cur_signer },
482 { "dkim_domain", vtype_stringptr, &dkim_signing_domain },
483 { "dkim_expires", vtype_dkim, (void *)DKIM_EXPIRES },
484 { "dkim_headernames", vtype_dkim, (void *)DKIM_HEADERNAMES },
485 { "dkim_identity", vtype_dkim, (void *)DKIM_IDENTITY },
486 { "dkim_key_granularity",vtype_dkim, (void *)DKIM_KEY_GRANULARITY },
487 { "dkim_key_nosubdomains",vtype_dkim, (void *)DKIM_NOSUBDOMAINS },
488 { "dkim_key_notes", vtype_dkim, (void *)DKIM_KEY_NOTES },
489 { "dkim_key_srvtype", vtype_dkim, (void *)DKIM_KEY_SRVTYPE },
490 { "dkim_key_testing", vtype_dkim, (void *)DKIM_KEY_TESTING },
491 { "dkim_selector", vtype_stringptr, &dkim_signing_selector },
492 { "dkim_signers", vtype_stringptr, &dkim_signers },
493 { "dkim_verify_reason", vtype_dkim, (void *)DKIM_VERIFY_REASON },
494 { "dkim_verify_status", vtype_dkim, (void *)DKIM_VERIFY_STATUS},
495 #endif
496 #ifdef EXPERIMENTAL_DMARC
497 { "dmarc_ar_header", vtype_stringptr, &dmarc_ar_header },
498 { "dmarc_domain_policy", vtype_stringptr, &dmarc_domain_policy },
499 { "dmarc_status", vtype_stringptr, &dmarc_status },
500 { "dmarc_status_text", vtype_stringptr, &dmarc_status_text },
501 { "dmarc_used_domain", vtype_stringptr, &dmarc_used_domain },
502 #endif
503 { "dnslist_domain", vtype_stringptr, &dnslist_domain },
504 { "dnslist_matched", vtype_stringptr, &dnslist_matched },
505 { "dnslist_text", vtype_stringptr, &dnslist_text },
506 { "dnslist_value", vtype_stringptr, &dnslist_value },
507 { "domain", vtype_stringptr, &deliver_domain },
508 { "domain_data", vtype_stringptr, &deliver_domain_data },
509 #ifdef EXPERIMENTAL_EVENT
510 { "event_data", vtype_stringptr, &event_data },
511
512 /*XXX want to use generic vars for as many of these as possible*/
513 { "event_defer_errno", vtype_int, &event_defer_errno },
514
515 { "event_name", vtype_stringptr, &event_name },
516 #endif
517 { "exim_gid", vtype_gid, &exim_gid },
518 { "exim_path", vtype_stringptr, &exim_path },
519 { "exim_uid", vtype_uid, &exim_uid },
520 { "exim_version", vtype_stringptr, &version_string },
521 #ifdef WITH_OLD_DEMIME
522 { "found_extension", vtype_stringptr, &found_extension },
523 #endif
524 { "headers_added", vtype_string_func, &fn_hdrs_added },
525 { "home", vtype_stringptr, &deliver_home },
526 { "host", vtype_stringptr, &deliver_host },
527 { "host_address", vtype_stringptr, &deliver_host_address },
528 { "host_data", vtype_stringptr, &host_data },
529 { "host_lookup_deferred",vtype_int, &host_lookup_deferred },
530 { "host_lookup_failed", vtype_int, &host_lookup_failed },
531 { "host_port", vtype_int, &deliver_host_port },
532 { "inode", vtype_ino, &deliver_inode },
533 { "interface_address", vtype_stringptr, &interface_address },
534 { "interface_port", vtype_int, &interface_port },
535 { "item", vtype_stringptr, &iterate_item },
536 #ifdef LOOKUP_LDAP
537 { "ldap_dn", vtype_stringptr, &eldap_dn },
538 #endif
539 { "load_average", vtype_load_avg, NULL },
540 { "local_part", vtype_stringptr, &deliver_localpart },
541 { "local_part_data", vtype_stringptr, &deliver_localpart_data },
542 { "local_part_prefix", vtype_stringptr, &deliver_localpart_prefix },
543 { "local_part_suffix", vtype_stringptr, &deliver_localpart_suffix },
544 { "local_scan_data", vtype_stringptr, &local_scan_data },
545 { "local_user_gid", vtype_gid, &local_user_gid },
546 { "local_user_uid", vtype_uid, &local_user_uid },
547 { "localhost_number", vtype_int, &host_number },
548 { "log_inodes", vtype_pinodes, (void *)FALSE },
549 { "log_space", vtype_pspace, (void *)FALSE },
550 { "lookup_dnssec_authenticated",vtype_stringptr,&lookup_dnssec_authenticated},
551 { "mailstore_basename", vtype_stringptr, &mailstore_basename },
552 #ifdef WITH_CONTENT_SCAN
553 { "malware_name", vtype_stringptr, &malware_name },
554 #endif
555 { "max_received_linelength", vtype_int, &max_received_linelength },
556 { "message_age", vtype_int, &message_age },
557 { "message_body", vtype_msgbody, &message_body },
558 { "message_body_end", vtype_msgbody_end, &message_body_end },
559 { "message_body_size", vtype_int, &message_body_size },
560 { "message_exim_id", vtype_stringptr, &message_id },
561 { "message_headers", vtype_msgheaders, NULL },
562 { "message_headers_raw", vtype_msgheaders_raw, NULL },
563 { "message_id", vtype_stringptr, &message_id },
564 { "message_linecount", vtype_int, &message_linecount },
565 { "message_size", vtype_int, &message_size },
566 #ifdef EXPERIMENTAL_INTERNATIONAL
567 { "message_smtputf8", vtype_bool, &message_smtputf8 },
568 #endif
569 #ifdef WITH_CONTENT_SCAN
570 { "mime_anomaly_level", vtype_int, &mime_anomaly_level },
571 { "mime_anomaly_text", vtype_stringptr, &mime_anomaly_text },
572 { "mime_boundary", vtype_stringptr, &mime_boundary },
573 { "mime_charset", vtype_stringptr, &mime_charset },
574 { "mime_content_description", vtype_stringptr, &mime_content_description },
575 { "mime_content_disposition", vtype_stringptr, &mime_content_disposition },
576 { "mime_content_id", vtype_stringptr, &mime_content_id },
577 { "mime_content_size", vtype_int, &mime_content_size },
578 { "mime_content_transfer_encoding",vtype_stringptr, &mime_content_transfer_encoding },
579 { "mime_content_type", vtype_stringptr, &mime_content_type },
580 { "mime_decoded_filename", vtype_stringptr, &mime_decoded_filename },
581 { "mime_filename", vtype_stringptr, &mime_filename },
582 { "mime_is_coverletter", vtype_int, &mime_is_coverletter },
583 { "mime_is_multipart", vtype_int, &mime_is_multipart },
584 { "mime_is_rfc822", vtype_int, &mime_is_rfc822 },
585 { "mime_part_count", vtype_int, &mime_part_count },
586 #endif
587 { "n0", vtype_filter_int, &filter_n[0] },
588 { "n1", vtype_filter_int, &filter_n[1] },
589 { "n2", vtype_filter_int, &filter_n[2] },
590 { "n3", vtype_filter_int, &filter_n[3] },
591 { "n4", vtype_filter_int, &filter_n[4] },
592 { "n5", vtype_filter_int, &filter_n[5] },
593 { "n6", vtype_filter_int, &filter_n[6] },
594 { "n7", vtype_filter_int, &filter_n[7] },
595 { "n8", vtype_filter_int, &filter_n[8] },
596 { "n9", vtype_filter_int, &filter_n[9] },
597 { "original_domain", vtype_stringptr, &deliver_domain_orig },
598 { "original_local_part", vtype_stringptr, &deliver_localpart_orig },
599 { "originator_gid", vtype_gid, &originator_gid },
600 { "originator_uid", vtype_uid, &originator_uid },
601 { "parent_domain", vtype_stringptr, &deliver_domain_parent },
602 { "parent_local_part", vtype_stringptr, &deliver_localpart_parent },
603 { "pid", vtype_pid, NULL },
604 { "primary_hostname", vtype_stringptr, &primary_hostname },
605 #ifdef EXPERIMENTAL_PROXY
606 { "proxy_host_address", vtype_stringptr, &proxy_host_address },
607 { "proxy_host_port", vtype_int, &proxy_host_port },
608 { "proxy_session", vtype_bool, &proxy_session },
609 { "proxy_target_address",vtype_stringptr, &proxy_target_address },
610 { "proxy_target_port", vtype_int, &proxy_target_port },
611 #endif
612 { "prvscheck_address", vtype_stringptr, &prvscheck_address },
613 { "prvscheck_keynum", vtype_stringptr, &prvscheck_keynum },
614 { "prvscheck_result", vtype_stringptr, &prvscheck_result },
615 { "qualify_domain", vtype_stringptr, &qualify_domain_sender },
616 { "qualify_recipient", vtype_stringptr, &qualify_domain_recipient },
617 { "rcpt_count", vtype_int, &rcpt_count },
618 { "rcpt_defer_count", vtype_int, &rcpt_defer_count },
619 { "rcpt_fail_count", vtype_int, &rcpt_fail_count },
620 { "received_count", vtype_int, &received_count },
621 { "received_for", vtype_stringptr, &received_for },
622 { "received_ip_address", vtype_stringptr, &interface_address },
623 { "received_port", vtype_int, &interface_port },
624 { "received_protocol", vtype_stringptr, &received_protocol },
625 { "received_time", vtype_int, &received_time },
626 { "recipient_data", vtype_stringptr, &recipient_data },
627 { "recipient_verify_failure",vtype_stringptr,&recipient_verify_failure },
628 { "recipients", vtype_string_func, &fn_recipients },
629 { "recipients_count", vtype_int, &recipients_count },
630 #ifdef WITH_CONTENT_SCAN
631 { "regex_match_string", vtype_stringptr, &regex_match_string },
632 #endif
633 { "reply_address", vtype_reply, NULL },
634 { "return_path", vtype_stringptr, &return_path },
635 { "return_size_limit", vtype_int, &bounce_return_size_limit },
636 { "router_name", vtype_stringptr, &router_name },
637 { "runrc", vtype_int, &runrc },
638 { "self_hostname", vtype_stringptr, &self_hostname },
639 { "sender_address", vtype_stringptr, &sender_address },
640 { "sender_address_data", vtype_stringptr, &sender_address_data },
641 { "sender_address_domain", vtype_domain, &sender_address },
642 { "sender_address_local_part", vtype_localpart, &sender_address },
643 { "sender_data", vtype_stringptr, &sender_data },
644 { "sender_fullhost", vtype_stringptr, &sender_fullhost },
645 { "sender_helo_name", vtype_stringptr, &sender_helo_name },
646 { "sender_host_address", vtype_stringptr, &sender_host_address },
647 { "sender_host_authenticated",vtype_stringptr, &sender_host_authenticated },
648 { "sender_host_dnssec", vtype_bool, &sender_host_dnssec },
649 { "sender_host_name", vtype_host_lookup, NULL },
650 { "sender_host_port", vtype_int, &sender_host_port },
651 { "sender_ident", vtype_stringptr, &sender_ident },
652 { "sender_rate", vtype_stringptr, &sender_rate },
653 { "sender_rate_limit", vtype_stringptr, &sender_rate_limit },
654 { "sender_rate_period", vtype_stringptr, &sender_rate_period },
655 { "sender_rcvhost", vtype_stringptr, &sender_rcvhost },
656 { "sender_verify_failure",vtype_stringptr, &sender_verify_failure },
657 { "sending_ip_address", vtype_stringptr, &sending_ip_address },
658 { "sending_port", vtype_int, &sending_port },
659 { "smtp_active_hostname", vtype_stringptr, &smtp_active_hostname },
660 { "smtp_command", vtype_stringptr, &smtp_cmd_buffer },
661 { "smtp_command_argument", vtype_stringptr, &smtp_cmd_argument },
662 { "smtp_count_at_connection_start", vtype_int, &smtp_accept_count },
663 { "smtp_notquit_reason", vtype_stringptr, &smtp_notquit_reason },
664 { "sn0", vtype_filter_int, &filter_sn[0] },
665 { "sn1", vtype_filter_int, &filter_sn[1] },
666 { "sn2", vtype_filter_int, &filter_sn[2] },
667 { "sn3", vtype_filter_int, &filter_sn[3] },
668 { "sn4", vtype_filter_int, &filter_sn[4] },
669 { "sn5", vtype_filter_int, &filter_sn[5] },
670 { "sn6", vtype_filter_int, &filter_sn[6] },
671 { "sn7", vtype_filter_int, &filter_sn[7] },
672 { "sn8", vtype_filter_int, &filter_sn[8] },
673 { "sn9", vtype_filter_int, &filter_sn[9] },
674 #ifdef WITH_CONTENT_SCAN
675 { "spam_action", vtype_stringptr, &spam_action },
676 { "spam_bar", vtype_stringptr, &spam_bar },
677 { "spam_report", vtype_stringptr, &spam_report },
678 { "spam_score", vtype_stringptr, &spam_score },
679 { "spam_score_int", vtype_stringptr, &spam_score_int },
680 #endif
681 #ifdef EXPERIMENTAL_SPF
682 { "spf_guess", vtype_stringptr, &spf_guess },
683 { "spf_header_comment", vtype_stringptr, &spf_header_comment },
684 { "spf_received", vtype_stringptr, &spf_received },
685 { "spf_result", vtype_stringptr, &spf_result },
686 { "spf_smtp_comment", vtype_stringptr, &spf_smtp_comment },
687 #endif
688 { "spool_directory", vtype_stringptr, &spool_directory },
689 { "spool_inodes", vtype_pinodes, (void *)TRUE },
690 { "spool_space", vtype_pspace, (void *)TRUE },
691 #ifdef EXPERIMENTAL_SRS
692 { "srs_db_address", vtype_stringptr, &srs_db_address },
693 { "srs_db_key", vtype_stringptr, &srs_db_key },
694 { "srs_orig_recipient", vtype_stringptr, &srs_orig_recipient },
695 { "srs_orig_sender", vtype_stringptr, &srs_orig_sender },
696 { "srs_recipient", vtype_stringptr, &srs_recipient },
697 { "srs_status", vtype_stringptr, &srs_status },
698 #endif
699 { "thisaddress", vtype_stringptr, &filter_thisaddress },
700
701 /* The non-(in,out) variables are now deprecated */
702 { "tls_bits", vtype_int, &tls_in.bits },
703 { "tls_certificate_verified", vtype_int, &tls_in.certificate_verified },
704 { "tls_cipher", vtype_stringptr, &tls_in.cipher },
705
706 { "tls_in_bits", vtype_int, &tls_in.bits },
707 { "tls_in_certificate_verified", vtype_int, &tls_in.certificate_verified },
708 { "tls_in_cipher", vtype_stringptr, &tls_in.cipher },
709 { "tls_in_ocsp", vtype_int, &tls_in.ocsp },
710 { "tls_in_ourcert", vtype_cert, &tls_in.ourcert },
711 { "tls_in_peercert", vtype_cert, &tls_in.peercert },
712 { "tls_in_peerdn", vtype_stringptr, &tls_in.peerdn },
713 #if defined(SUPPORT_TLS)
714 { "tls_in_sni", vtype_stringptr, &tls_in.sni },
715 #endif
716 { "tls_out_bits", vtype_int, &tls_out.bits },
717 { "tls_out_certificate_verified", vtype_int,&tls_out.certificate_verified },
718 { "tls_out_cipher", vtype_stringptr, &tls_out.cipher },
719 #ifdef EXPERIMENTAL_DANE
720 { "tls_out_dane", vtype_bool, &tls_out.dane_verified },
721 #endif
722 { "tls_out_ocsp", vtype_int, &tls_out.ocsp },
723 { "tls_out_ourcert", vtype_cert, &tls_out.ourcert },
724 { "tls_out_peercert", vtype_cert, &tls_out.peercert },
725 { "tls_out_peerdn", vtype_stringptr, &tls_out.peerdn },
726 #if defined(SUPPORT_TLS)
727 { "tls_out_sni", vtype_stringptr, &tls_out.sni },
728 #endif
729 #ifdef EXPERIMENTAL_DANE
730 { "tls_out_tlsa_usage", vtype_int, &tls_out.tlsa_usage },
731 #endif
732
733 { "tls_peerdn", vtype_stringptr, &tls_in.peerdn }, /* mind the alphabetical order! */
734 #if defined(SUPPORT_TLS)
735 { "tls_sni", vtype_stringptr, &tls_in.sni }, /* mind the alphabetical order! */
736 #endif
737
738 { "tod_bsdinbox", vtype_todbsdin, NULL },
739 { "tod_epoch", vtype_tode, NULL },
740 { "tod_epoch_l", vtype_todel, NULL },
741 { "tod_full", vtype_todf, NULL },
742 { "tod_log", vtype_todl, NULL },
743 { "tod_logfile", vtype_todlf, NULL },
744 { "tod_zone", vtype_todzone, NULL },
745 { "tod_zulu", vtype_todzulu, NULL },
746 { "transport_name", vtype_stringptr, &transport_name },
747 { "value", vtype_stringptr, &lookup_value },
748 { "verify_mode", vtype_stringptr, &verify_mode },
749 { "version_number", vtype_stringptr, &version_string },
750 { "warn_message_delay", vtype_stringptr, &warnmsg_delay },
751 { "warn_message_recipient",vtype_stringptr, &warnmsg_recipients },
752 { "warn_message_recipients",vtype_stringptr,&warnmsg_recipients },
753 { "warnmsg_delay", vtype_stringptr, &warnmsg_delay },
754 { "warnmsg_recipient", vtype_stringptr, &warnmsg_recipients },
755 { "warnmsg_recipients", vtype_stringptr, &warnmsg_recipients }
756 };
757
758 static int var_table_size = sizeof(var_table)/sizeof(var_entry);
759 static uschar var_buffer[256];
760 static BOOL malformed_header;
761
762 /* For textual hashes */
763
764 static const char *hashcodes = "abcdefghijklmnopqrtsuvwxyz"
765 "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
766 "0123456789";
767
768 enum { HMAC_MD5, HMAC_SHA1 };
769
770 /* For numeric hashes */
771
772 static unsigned int prime[] = {
773 2, 3, 5, 7, 11, 13, 17, 19, 23, 29,
774 31, 37, 41, 43, 47, 53, 59, 61, 67, 71,
775 73, 79, 83, 89, 97, 101, 103, 107, 109, 113};
776
777 /* For printing modes in symbolic form */
778
779 static uschar *mtable_normal[] =
780 { US"---", US"--x", US"-w-", US"-wx", US"r--", US"r-x", US"rw-", US"rwx" };
781
782 static uschar *mtable_setid[] =
783 { US"--S", US"--s", US"-wS", US"-ws", US"r-S", US"r-s", US"rwS", US"rws" };
784
785 static uschar *mtable_sticky[] =
786 { US"--T", US"--t", US"-wT", US"-wt", US"r-T", US"r-t", US"rwT", US"rwt" };
787
788
789
790 /*************************************************
791 * Tables for UTF-8 support *
792 *************************************************/
793
794 /* Table of the number of extra characters, indexed by the first character
795 masked with 0x3f. The highest number for a valid UTF-8 character is in fact
796 0x3d. */
797
798 static uschar utf8_table1[] = {
799 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
800 1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1,
801 2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,2,
802 3,3,3,3,3,3,3,3,4,4,4,4,5,5,5,5 };
803
804 /* These are the masks for the data bits in the first byte of a character,
805 indexed by the number of additional bytes. */
806
807 static int utf8_table2[] = { 0xff, 0x1f, 0x0f, 0x07, 0x03, 0x01};
808
809 /* Get the next UTF-8 character, advancing the pointer. */
810
811 #define GETUTF8INC(c, ptr) \
812 c = *ptr++; \
813 if ((c & 0xc0) == 0xc0) \
814 { \
815 int a = utf8_table1[c & 0x3f]; /* Number of additional bytes */ \
816 int s = 6*a; \
817 c = (c & utf8_table2[a]) << s; \
818 while (a-- > 0) \
819 { \
820 s -= 6; \
821 c |= (*ptr++ & 0x3f) << s; \
822 } \
823 }
824
825
826 /*************************************************
827 * Binary chop search on a table *
828 *************************************************/
829
830 /* This is used for matching expansion items and operators.
831
832 Arguments:
833 name the name that is being sought
834 table the table to search
835 table_size the number of items in the table
836
837 Returns: the offset in the table, or -1
838 */
839
840 static int
841 chop_match(uschar *name, uschar **table, int table_size)
842 {
843 uschar **bot = table;
844 uschar **top = table + table_size;
845
846 while (top > bot)
847 {
848 uschar **mid = bot + (top - bot)/2;
849 int c = Ustrcmp(name, *mid);
850 if (c == 0) return mid - table;
851 if (c > 0) bot = mid + 1; else top = mid;
852 }
853
854 return -1;
855 }
856
857
858
859 /*************************************************
860 * Check a condition string *
861 *************************************************/
862
863 /* This function is called to expand a string, and test the result for a "true"
864 or "false" value. Failure of the expansion yields FALSE; logged unless it was a
865 forced fail or lookup defer.
866
867 We used to release all store used, but this is not not safe due
868 to ${dlfunc } and ${acl }. In any case expand_string_internal()
869 is reasonably careful to release what it can.
870
871 The actual false-value tests should be replicated for ECOND_BOOL_LAX.
872
873 Arguments:
874 condition the condition string
875 m1 text to be incorporated in panic error
876 m2 ditto
877
878 Returns: TRUE if condition is met, FALSE if not
879 */
880
881 BOOL
882 expand_check_condition(uschar *condition, uschar *m1, uschar *m2)
883 {
884 int rc;
885 uschar *ss = expand_string(condition);
886 if (ss == NULL)
887 {
888 if (!expand_string_forcedfail && !search_find_defer)
889 log_write(0, LOG_MAIN|LOG_PANIC, "failed to expand condition \"%s\" "
890 "for %s %s: %s", condition, m1, m2, expand_string_message);
891 return FALSE;
892 }
893 rc = ss[0] != 0 && Ustrcmp(ss, "0") != 0 && strcmpic(ss, US"no") != 0 &&
894 strcmpic(ss, US"false") != 0;
895 return rc;
896 }
897
898
899
900
901 /*************************************************
902 * Pseudo-random number generation *
903 *************************************************/
904
905 /* Pseudo-random number generation. The result is not "expected" to be
906 cryptographically strong but not so weak that someone will shoot themselves
907 in the foot using it as a nonce in some email header scheme or whatever
908 weirdness they'll twist this into. The result should ideally handle fork().
909
910 However, if we're stuck unable to provide this, then we'll fall back to
911 appallingly bad randomness.
912
913 If SUPPORT_TLS is defined then this will not be used except as an emergency
914 fallback.
915
916 Arguments:
917 max range maximum
918 Returns a random number in range [0, max-1]
919 */
920
921 #ifdef SUPPORT_TLS
922 # define vaguely_random_number vaguely_random_number_fallback
923 #endif
924 int
925 vaguely_random_number(int max)
926 {
927 #ifdef SUPPORT_TLS
928 # undef vaguely_random_number
929 #endif
930 static pid_t pid = 0;
931 pid_t p2;
932 #if defined(HAVE_SRANDOM) && !defined(HAVE_SRANDOMDEV)
933 struct timeval tv;
934 #endif
935
936 p2 = getpid();
937 if (p2 != pid)
938 {
939 if (pid != 0)
940 {
941
942 #ifdef HAVE_ARC4RANDOM
943 /* cryptographically strong randomness, common on *BSD platforms, not
944 so much elsewhere. Alas. */
945 #ifndef NOT_HAVE_ARC4RANDOM_STIR
946 arc4random_stir();
947 #endif
948 #elif defined(HAVE_SRANDOM) || defined(HAVE_SRANDOMDEV)
949 #ifdef HAVE_SRANDOMDEV
950 /* uses random(4) for seeding */
951 srandomdev();
952 #else
953 gettimeofday(&tv, NULL);
954 srandom(tv.tv_sec | tv.tv_usec | getpid());
955 #endif
956 #else
957 /* Poor randomness and no seeding here */
958 #endif
959
960 }
961 pid = p2;
962 }
963
964 #ifdef HAVE_ARC4RANDOM
965 return arc4random() % max;
966 #elif defined(HAVE_SRANDOM) || defined(HAVE_SRANDOMDEV)
967 return random() % max;
968 #else
969 /* This one returns a 16-bit number, definitely not crypto-strong */
970 return random_number(max);
971 #endif
972 }
973
974
975
976
977 /*************************************************
978 * Pick out a name from a string *
979 *************************************************/
980
981 /* If the name is too long, it is silently truncated.
982
983 Arguments:
984 name points to a buffer into which to put the name
985 max is the length of the buffer
986 s points to the first alphabetic character of the name
987 extras chars other than alphanumerics to permit
988
989 Returns: pointer to the first character after the name
990
991 Note: The test for *s != 0 in the while loop is necessary because
992 Ustrchr() yields non-NULL if the character is zero (which is not something
993 I expected). */
994
995 static const uschar *
996 read_name(uschar *name, int max, const uschar *s, uschar *extras)
997 {
998 int ptr = 0;
999 while (*s != 0 && (isalnum(*s) || Ustrchr(extras, *s) != NULL))
1000 {
1001 if (ptr < max-1) name[ptr++] = *s;
1002 s++;
1003 }
1004 name[ptr] = 0;
1005 return s;
1006 }
1007
1008
1009
1010 /*************************************************
1011 * Pick out the rest of a header name *
1012 *************************************************/
1013
1014 /* A variable name starting $header_ (or just $h_ for those who like
1015 abbreviations) might not be the complete header name because headers can
1016 contain any printing characters in their names, except ':'. This function is
1017 called to read the rest of the name, chop h[eader]_ off the front, and put ':'
1018 on the end, if the name was terminated by white space.
1019
1020 Arguments:
1021 name points to a buffer in which the name read so far exists
1022 max is the length of the buffer
1023 s points to the first character after the name so far, i.e. the
1024 first non-alphameric character after $header_xxxxx
1025
1026 Returns: a pointer to the first character after the header name
1027 */
1028
1029 static const uschar *
1030 read_header_name(uschar *name, int max, const uschar *s)
1031 {
1032 int prelen = Ustrchr(name, '_') - name + 1;
1033 int ptr = Ustrlen(name) - prelen;
1034 if (ptr > 0) memmove(name, name+prelen, ptr);
1035 while (mac_isgraph(*s) && *s != ':')
1036 {
1037 if (ptr < max-1) name[ptr++] = *s;
1038 s++;
1039 }
1040 if (*s == ':') s++;
1041 name[ptr++] = ':';
1042 name[ptr] = 0;
1043 return s;
1044 }
1045
1046
1047
1048 /*************************************************
1049 * Pick out a number from a string *
1050 *************************************************/
1051
1052 /* Arguments:
1053 n points to an integer into which to put the number
1054 s points to the first digit of the number
1055
1056 Returns: a pointer to the character after the last digit
1057 */
1058
1059 static uschar *
1060 read_number(int *n, uschar *s)
1061 {
1062 *n = 0;
1063 while (isdigit(*s)) *n = *n * 10 + (*s++ - '0');
1064 return s;
1065 }
1066
1067 static const uschar *
1068 read_cnumber(int *n, const uschar *s)
1069 {
1070 *n = 0;
1071 while (isdigit(*s)) *n = *n * 10 + (*s++ - '0');
1072 return s;
1073 }
1074
1075
1076
1077 /*************************************************
1078 * Extract keyed subfield from a string *
1079 *************************************************/
1080
1081 /* The yield is in dynamic store; NULL means that the key was not found.
1082
1083 Arguments:
1084 key points to the name of the key
1085 s points to the string from which to extract the subfield
1086
1087 Returns: NULL if the subfield was not found, or
1088 a pointer to the subfield's data
1089 */
1090
1091 static uschar *
1092 expand_getkeyed(uschar *key, const uschar *s)
1093 {
1094 int length = Ustrlen(key);
1095 while (isspace(*s)) s++;
1096
1097 /* Loop to search for the key */
1098
1099 while (*s != 0)
1100 {
1101 int dkeylength;
1102 uschar *data;
1103 const uschar *dkey = s;
1104
1105 while (*s != 0 && *s != '=' && !isspace(*s)) s++;
1106 dkeylength = s - dkey;
1107 while (isspace(*s)) s++;
1108 if (*s == '=') while (isspace((*(++s))));
1109
1110 data = string_dequote(&s);
1111 if (length == dkeylength && strncmpic(key, dkey, length) == 0)
1112 return data;
1113
1114 while (isspace(*s)) s++;
1115 }
1116
1117 return NULL;
1118 }
1119
1120
1121
1122 static var_entry *
1123 find_var_ent(uschar * name)
1124 {
1125 int first = 0;
1126 int last = var_table_size;
1127
1128 while (last > first)
1129 {
1130 int middle = (first + last)/2;
1131 int c = Ustrcmp(name, var_table[middle].name);
1132
1133 if (c > 0) { first = middle + 1; continue; }
1134 if (c < 0) { last = middle; continue; }
1135 return &var_table[middle];
1136 }
1137 return NULL;
1138 }
1139
1140 /*************************************************
1141 * Extract numbered subfield from string *
1142 *************************************************/
1143
1144 /* Extracts a numbered field from a string that is divided by tokens - for
1145 example a line from /etc/passwd is divided by colon characters. First field is
1146 numbered one. Negative arguments count from the right. Zero returns the whole
1147 string. Returns NULL if there are insufficient tokens in the string
1148
1149 ***WARNING***
1150 Modifies final argument - this is a dynamically generated string, so that's OK.
1151
1152 Arguments:
1153 field number of field to be extracted,
1154 first field = 1, whole string = 0, last field = -1
1155 separators characters that are used to break string into tokens
1156 s points to the string from which to extract the subfield
1157
1158 Returns: NULL if the field was not found,
1159 a pointer to the field's data inside s (modified to add 0)
1160 */
1161
1162 static uschar *
1163 expand_gettokened (int field, uschar *separators, uschar *s)
1164 {
1165 int sep = 1;
1166 int count;
1167 uschar *ss = s;
1168 uschar *fieldtext = NULL;
1169
1170 if (field == 0) return s;
1171
1172 /* Break the line up into fields in place; for field > 0 we stop when we have
1173 done the number of fields we want. For field < 0 we continue till the end of
1174 the string, counting the number of fields. */
1175
1176 count = (field > 0)? field : INT_MAX;
1177
1178 while (count-- > 0)
1179 {
1180 size_t len;
1181
1182 /* Previous field was the last one in the string. For a positive field
1183 number, this means there are not enough fields. For a negative field number,
1184 check that there are enough, and scan back to find the one that is wanted. */
1185
1186 if (sep == 0)
1187 {
1188 if (field > 0 || (-field) > (INT_MAX - count - 1)) return NULL;
1189 if ((-field) == (INT_MAX - count - 1)) return s;
1190 while (field++ < 0)
1191 {
1192 ss--;
1193 while (ss[-1] != 0) ss--;
1194 }
1195 fieldtext = ss;
1196 break;
1197 }
1198
1199 /* Previous field was not last in the string; save its start and put a
1200 zero at its end. */
1201
1202 fieldtext = ss;
1203 len = Ustrcspn(ss, separators);
1204 sep = ss[len];
1205 ss[len] = 0;
1206 ss += len + 1;
1207 }
1208
1209 return fieldtext;
1210 }
1211
1212
1213 static uschar *
1214 expand_getlistele(int field, const uschar * list)
1215 {
1216 const uschar * tlist= list;
1217 int sep= 0;
1218 uschar dummy;
1219
1220 if(field<0)
1221 {
1222 for(field++; string_nextinlist(&tlist, &sep, &dummy, 1); ) field++;
1223 sep= 0;
1224 }
1225 if(field==0) return NULL;
1226 while(--field>0 && (string_nextinlist(&list, &sep, &dummy, 1))) ;
1227 return string_nextinlist(&list, &sep, NULL, 0);
1228 }
1229
1230
1231 /* Certificate fields, by name. Worry about by-OID later */
1232 /* Names are chosen to not have common prefixes */
1233
1234 #ifdef SUPPORT_TLS
1235 typedef struct
1236 {
1237 uschar * name;
1238 int namelen;
1239 uschar * (*getfn)(void * cert, uschar * mod);
1240 } certfield;
1241 static certfield certfields[] =
1242 { /* linear search; no special order */
1243 { US"version", 7, &tls_cert_version },
1244 { US"serial_number", 13, &tls_cert_serial_number },
1245 { US"subject", 7, &tls_cert_subject },
1246 { US"notbefore", 9, &tls_cert_not_before },
1247 { US"notafter", 8, &tls_cert_not_after },
1248 { US"issuer", 6, &tls_cert_issuer },
1249 { US"signature", 9, &tls_cert_signature },
1250 { US"sig_algorithm", 13, &tls_cert_signature_algorithm },
1251 { US"subj_altname", 12, &tls_cert_subject_altname },
1252 { US"ocsp_uri", 8, &tls_cert_ocsp_uri },
1253 { US"crl_uri", 7, &tls_cert_crl_uri },
1254 };
1255
1256 static uschar *
1257 expand_getcertele(uschar * field, uschar * certvar)
1258 {
1259 var_entry * vp;
1260 certfield * cp;
1261
1262 if (!(vp = find_var_ent(certvar)))
1263 {
1264 expand_string_message =
1265 string_sprintf("no variable named \"%s\"", certvar);
1266 return NULL; /* Unknown variable name */
1267 }
1268 /* NB this stops us passing certs around in variable. Might
1269 want to do that in future */
1270 if (vp->type != vtype_cert)
1271 {
1272 expand_string_message =
1273 string_sprintf("\"%s\" is not a certificate", certvar);
1274 return NULL; /* Unknown variable name */
1275 }
1276 if (!*(void **)vp->value)
1277 return NULL;
1278
1279 if (*field >= '0' && *field <= '9')
1280 return tls_cert_ext_by_oid(*(void **)vp->value, field, 0);
1281
1282 for(cp = certfields;
1283 cp < certfields + nelements(certfields);
1284 cp++)
1285 if (Ustrncmp(cp->name, field, cp->namelen) == 0)
1286 {
1287 uschar * modifier = *(field += cp->namelen) == ','
1288 ? ++field : NULL;
1289 return (*cp->getfn)( *(void **)vp->value, modifier );
1290 }
1291
1292 expand_string_message =
1293 string_sprintf("bad field selector \"%s\" for certextract", field);
1294 return NULL;
1295 }
1296 #endif /*SUPPORT_TLS*/
1297
1298 /*************************************************
1299 * Extract a substring from a string *
1300 *************************************************/
1301
1302 /* Perform the ${substr or ${length expansion operations.
1303
1304 Arguments:
1305 subject the input string
1306 value1 the offset from the start of the input string to the start of
1307 the output string; if negative, count from the right.
1308 value2 the length of the output string, or negative (-1) for unset
1309 if value1 is positive, unset means "all after"
1310 if value1 is negative, unset means "all before"
1311 len set to the length of the returned string
1312
1313 Returns: pointer to the output string, or NULL if there is an error
1314 */
1315
1316 static uschar *
1317 extract_substr(uschar *subject, int value1, int value2, int *len)
1318 {
1319 int sublen = Ustrlen(subject);
1320
1321 if (value1 < 0) /* count from right */
1322 {
1323 value1 += sublen;
1324
1325 /* If the position is before the start, skip to the start, and adjust the
1326 length. If the length ends up negative, the substring is null because nothing
1327 can precede. This falls out naturally when the length is unset, meaning "all
1328 to the left". */
1329
1330 if (value1 < 0)
1331 {
1332 value2 += value1;
1333 if (value2 < 0) value2 = 0;
1334 value1 = 0;
1335 }
1336
1337 /* Otherwise an unset length => characters before value1 */
1338
1339 else if (value2 < 0)
1340 {
1341 value2 = value1;
1342 value1 = 0;
1343 }
1344 }
1345
1346 /* For a non-negative offset, if the starting position is past the end of the
1347 string, the result will be the null string. Otherwise, an unset length means
1348 "rest"; just set it to the maximum - it will be cut down below if necessary. */
1349
1350 else
1351 {
1352 if (value1 > sublen)
1353 {
1354 value1 = sublen;
1355 value2 = 0;
1356 }
1357 else if (value2 < 0) value2 = sublen;
1358 }
1359
1360 /* Cut the length down to the maximum possible for the offset value, and get
1361 the required characters. */
1362
1363 if (value1 + value2 > sublen) value2 = sublen - value1;
1364 *len = value2;
1365 return subject + value1;
1366 }
1367
1368
1369
1370
1371 /*************************************************
1372 * Old-style hash of a string *
1373 *************************************************/
1374
1375 /* Perform the ${hash expansion operation.
1376
1377 Arguments:
1378 subject the input string (an expanded substring)
1379 value1 the length of the output string; if greater or equal to the
1380 length of the input string, the input string is returned
1381 value2 the number of hash characters to use, or 26 if negative
1382 len set to the length of the returned string
1383
1384 Returns: pointer to the output string, or NULL if there is an error
1385 */
1386
1387 static uschar *
1388 compute_hash(uschar *subject, int value1, int value2, int *len)
1389 {
1390 int sublen = Ustrlen(subject);
1391
1392 if (value2 < 0) value2 = 26;
1393 else if (value2 > Ustrlen(hashcodes))
1394 {
1395 expand_string_message =
1396 string_sprintf("hash count \"%d\" too big", value2);
1397 return NULL;
1398 }
1399
1400 /* Calculate the hash text. We know it is shorter than the original string, so
1401 can safely place it in subject[] (we know that subject is always itself an
1402 expanded substring). */
1403
1404 if (value1 < sublen)
1405 {
1406 int c;
1407 int i = 0;
1408 int j = value1;
1409 while ((c = (subject[j])) != 0)
1410 {
1411 int shift = (c + j++) & 7;
1412 subject[i] ^= (c << shift) | (c >> (8-shift));
1413 if (++i >= value1) i = 0;
1414 }
1415 for (i = 0; i < value1; i++)
1416 subject[i] = hashcodes[(subject[i]) % value2];
1417 }
1418 else value1 = sublen;
1419
1420 *len = value1;
1421 return subject;
1422 }
1423
1424
1425
1426
1427 /*************************************************
1428 * Numeric hash of a string *
1429 *************************************************/
1430
1431 /* Perform the ${nhash expansion operation. The first characters of the
1432 string are treated as most important, and get the highest prime numbers.
1433
1434 Arguments:
1435 subject the input string
1436 value1 the maximum value of the first part of the result
1437 value2 the maximum value of the second part of the result,
1438 or negative to produce only a one-part result
1439 len set to the length of the returned string
1440
1441 Returns: pointer to the output string, or NULL if there is an error.
1442 */
1443
1444 static uschar *
1445 compute_nhash (uschar *subject, int value1, int value2, int *len)
1446 {
1447 uschar *s = subject;
1448 int i = 0;
1449 unsigned long int total = 0; /* no overflow */
1450
1451 while (*s != 0)
1452 {
1453 if (i == 0) i = sizeof(prime)/sizeof(int) - 1;
1454 total += prime[i--] * (unsigned int)(*s++);
1455 }
1456
1457 /* If value2 is unset, just compute one number */
1458
1459 if (value2 < 0)
1460 {
1461 s = string_sprintf("%d", total % value1);
1462 }
1463
1464 /* Otherwise do a div/mod hash */
1465
1466 else
1467 {
1468 total = total % (value1 * value2);
1469 s = string_sprintf("%d/%d", total/value2, total % value2);
1470 }
1471
1472 *len = Ustrlen(s);
1473 return s;
1474 }
1475
1476
1477
1478
1479
1480 /*************************************************
1481 * Find the value of a header or headers *
1482 *************************************************/
1483
1484 /* Multiple instances of the same header get concatenated, and this function
1485 can also return a concatenation of all the header lines. When concatenating
1486 specific headers that contain lists of addresses, a comma is inserted between
1487 them. Otherwise we use a straight concatenation. Because some messages can have
1488 pathologically large number of lines, there is a limit on the length that is
1489 returned. Also, to avoid massive store use which would result from using
1490 string_cat() as it copies and extends strings, we do a preliminary pass to find
1491 out exactly how much store will be needed. On "normal" messages this will be
1492 pretty trivial.
1493
1494 Arguments:
1495 name the name of the header, without the leading $header_ or $h_,
1496 or NULL if a concatenation of all headers is required
1497 exists_only TRUE if called from a def: test; don't need to build a string;
1498 just return a string that is not "" and not "0" if the header
1499 exists
1500 newsize return the size of memory block that was obtained; may be NULL
1501 if exists_only is TRUE
1502 want_raw TRUE if called for $rh_ or $rheader_ variables; no processing,
1503 other than concatenating, will be done on the header. Also used
1504 for $message_headers_raw.
1505 charset name of charset to translate MIME words to; used only if
1506 want_raw is false; if NULL, no translation is done (this is
1507 used for $bh_ and $bheader_)
1508
1509 Returns: NULL if the header does not exist, else a pointer to a new
1510 store block
1511 */
1512
1513 static uschar *
1514 find_header(uschar *name, BOOL exists_only, int *newsize, BOOL want_raw,
1515 uschar *charset)
1516 {
1517 BOOL found = name == NULL;
1518 int comma = 0;
1519 int len = found? 0 : Ustrlen(name);
1520 int i;
1521 uschar *yield = NULL;
1522 uschar *ptr = NULL;
1523
1524 /* Loop for two passes - saves code repetition */
1525
1526 for (i = 0; i < 2; i++)
1527 {
1528 int size = 0;
1529 header_line *h;
1530
1531 for (h = header_list; size < header_insert_maxlen && h != NULL; h = h->next)
1532 {
1533 if (h->type != htype_old && h->text != NULL) /* NULL => Received: placeholder */
1534 {
1535 if (name == NULL || (len <= h->slen && strncmpic(name, h->text, len) == 0))
1536 {
1537 int ilen;
1538 uschar *t;
1539
1540 if (exists_only) return US"1"; /* don't need actual string */
1541 found = TRUE;
1542 t = h->text + len; /* text to insert */
1543 if (!want_raw) /* unless wanted raw, */
1544 while (isspace(*t)) t++; /* remove leading white space */
1545 ilen = h->slen - (t - h->text); /* length to insert */
1546
1547 /* Unless wanted raw, remove trailing whitespace, including the
1548 newline. */
1549
1550 if (!want_raw)
1551 while (ilen > 0 && isspace(t[ilen-1])) ilen--;
1552
1553 /* Set comma = 1 if handling a single header and it's one of those
1554 that contains an address list, except when asked for raw headers. Only
1555 need to do this once. */
1556
1557 if (!want_raw && name != NULL && comma == 0 &&
1558 Ustrchr("BCFRST", h->type) != NULL)
1559 comma = 1;
1560
1561 /* First pass - compute total store needed; second pass - compute
1562 total store used, including this header. */
1563
1564 size += ilen + comma + 1; /* +1 for the newline */
1565
1566 /* Second pass - concatentate the data, up to a maximum. Note that
1567 the loop stops when size hits the limit. */
1568
1569 if (i != 0)
1570 {
1571 if (size > header_insert_maxlen)
1572 {
1573 ilen -= size - header_insert_maxlen - 1;
1574 comma = 0;
1575 }
1576 Ustrncpy(ptr, t, ilen);
1577 ptr += ilen;
1578
1579 /* For a non-raw header, put in the comma if needed, then add
1580 back the newline we removed above, provided there was some text in
1581 the header. */
1582
1583 if (!want_raw && ilen > 0)
1584 {
1585 if (comma != 0) *ptr++ = ',';
1586 *ptr++ = '\n';
1587 }
1588 }
1589 }
1590 }
1591 }
1592
1593 /* At end of first pass, return NULL if no header found. Then truncate size
1594 if necessary, and get the buffer to hold the data, returning the buffer size.
1595 */
1596
1597 if (i == 0)
1598 {
1599 if (!found) return NULL;
1600 if (size > header_insert_maxlen) size = header_insert_maxlen;
1601 *newsize = size + 1;
1602 ptr = yield = store_get(*newsize);
1603 }
1604 }
1605
1606 /* That's all we do for raw header expansion. */
1607
1608 if (want_raw)
1609 {
1610 *ptr = 0;
1611 }
1612
1613 /* Otherwise, remove a final newline and a redundant added comma. Then we do
1614 RFC 2047 decoding, translating the charset if requested. The rfc2047_decode2()
1615 function can return an error with decoded data if the charset translation
1616 fails. If decoding fails, it returns NULL. */
1617
1618 else
1619 {
1620 uschar *decoded, *error;
1621 if (ptr > yield && ptr[-1] == '\n') ptr--;
1622 if (ptr > yield && comma != 0 && ptr[-1] == ',') ptr--;
1623 *ptr = 0;
1624 decoded = rfc2047_decode2(yield, check_rfc2047_length, charset, '?', NULL,
1625 newsize, &error);
1626 if (error != NULL)
1627 {
1628 DEBUG(D_any) debug_printf("*** error in RFC 2047 decoding: %s\n"
1629 " input was: %s\n", error, yield);
1630 }
1631 if (decoded != NULL) yield = decoded;
1632 }
1633
1634 return yield;
1635 }
1636
1637
1638
1639
1640 /*************************************************
1641 * Return list of recipients *
1642 *************************************************/
1643 /* A recipients list is available only during system message filtering,
1644 during ACL processing after DATA, and while expanding pipe commands
1645 generated from a system filter, but not elsewhere. */
1646
1647 static uschar *
1648 fn_recipients(void)
1649 {
1650 if (!enable_dollar_recipients) return NULL; else
1651 {
1652 int size = 128;
1653 int ptr = 0;
1654 int i;
1655 uschar * s = store_get(size);
1656 for (i = 0; i < recipients_count; i++)
1657 {
1658 if (i != 0) s = string_cat(s, &size, &ptr, US", ", 2);
1659 s = string_cat(s, &size, &ptr, recipients_list[i].address,
1660 Ustrlen(recipients_list[i].address));
1661 }
1662 s[ptr] = 0; /* string_cat() leaves room */
1663 return s;
1664 }
1665 }
1666
1667
1668 /*************************************************
1669 * Find value of a variable *
1670 *************************************************/
1671
1672 /* The table of variables is kept in alphabetic order, so we can search it
1673 using a binary chop. The "choplen" variable is nothing to do with the binary
1674 chop.
1675
1676 Arguments:
1677 name the name of the variable being sought
1678 exists_only TRUE if this is a def: test; passed on to find_header()
1679 skipping TRUE => skip any processing evaluation; this is not the same as
1680 exists_only because def: may test for values that are first
1681 evaluated here
1682 newsize pointer to an int which is initially zero; if the answer is in
1683 a new memory buffer, *newsize is set to its size
1684
1685 Returns: NULL if the variable does not exist, or
1686 a pointer to the variable's contents, or
1687 something non-NULL if exists_only is TRUE
1688 */
1689
1690 static uschar *
1691 find_variable(uschar *name, BOOL exists_only, BOOL skipping, int *newsize)
1692 {
1693 var_entry * vp;
1694 uschar *s, *domain;
1695 uschar **ss;
1696 void * val;
1697
1698 /* Handle ACL variables, whose names are of the form acl_cxxx or acl_mxxx.
1699 Originally, xxx had to be a number in the range 0-9 (later 0-19), but from
1700 release 4.64 onwards arbitrary names are permitted, as long as the first 5
1701 characters are acl_c or acl_m and the sixth is either a digit or an underscore
1702 (this gave backwards compatibility at the changeover). There may be built-in
1703 variables whose names start acl_ but they should never start in this way. This
1704 slightly messy specification is a consequence of the history, needless to say.
1705
1706 If an ACL variable does not exist, treat it as empty, unless strict_acl_vars is
1707 set, in which case give an error. */
1708
1709 if ((Ustrncmp(name, "acl_c", 5) == 0 || Ustrncmp(name, "acl_m", 5) == 0) &&
1710 !isalpha(name[5]))
1711 {
1712 tree_node *node =
1713 tree_search((name[4] == 'c')? acl_var_c : acl_var_m, name + 4);
1714 return (node == NULL)? (strict_acl_vars? NULL : US"") : node->data.ptr;
1715 }
1716
1717 /* Handle $auth<n> variables. */
1718
1719 if (Ustrncmp(name, "auth", 4) == 0)
1720 {
1721 uschar *endptr;
1722 int n = Ustrtoul(name + 4, &endptr, 10);
1723 if (*endptr == 0 && n != 0 && n <= AUTH_VARS)
1724 return (auth_vars[n-1] == NULL)? US"" : auth_vars[n-1];
1725 }
1726
1727 /* For all other variables, search the table */
1728
1729 if (!(vp = find_var_ent(name)))
1730 return NULL; /* Unknown variable name */
1731
1732 /* Found an existing variable. If in skipping state, the value isn't needed,
1733 and we want to avoid processing (such as looking up the host name). */
1734
1735 if (skipping)
1736 return US"";
1737
1738 val = vp->value;
1739 switch (vp->type)
1740 {
1741 case vtype_filter_int:
1742 if (!filter_running) return NULL;
1743 /* Fall through */
1744 /* VVVVVVVVVVVV */
1745 case vtype_int:
1746 sprintf(CS var_buffer, "%d", *(int *)(val)); /* Integer */
1747 return var_buffer;
1748
1749 case vtype_ino:
1750 sprintf(CS var_buffer, "%ld", (long int)(*(ino_t *)(val))); /* Inode */
1751 return var_buffer;
1752
1753 case vtype_gid:
1754 sprintf(CS var_buffer, "%ld", (long int)(*(gid_t *)(val))); /* gid */
1755 return var_buffer;
1756
1757 case vtype_uid:
1758 sprintf(CS var_buffer, "%ld", (long int)(*(uid_t *)(val))); /* uid */
1759 return var_buffer;
1760
1761 case vtype_bool:
1762 sprintf(CS var_buffer, "%s", *(BOOL *)(val) ? "yes" : "no"); /* bool */
1763 return var_buffer;
1764
1765 case vtype_stringptr: /* Pointer to string */
1766 s = *((uschar **)(val));
1767 return (s == NULL)? US"" : s;
1768
1769 case vtype_pid:
1770 sprintf(CS var_buffer, "%d", (int)getpid()); /* pid */
1771 return var_buffer;
1772
1773 case vtype_load_avg:
1774 sprintf(CS var_buffer, "%d", OS_GETLOADAVG()); /* load_average */
1775 return var_buffer;
1776
1777 case vtype_host_lookup: /* Lookup if not done so */
1778 if (sender_host_name == NULL && sender_host_address != NULL &&
1779 !host_lookup_failed && host_name_lookup() == OK)
1780 host_build_sender_fullhost();
1781 return (sender_host_name == NULL)? US"" : sender_host_name;
1782
1783 case vtype_localpart: /* Get local part from address */
1784 s = *((uschar **)(val));
1785 if (s == NULL) return US"";
1786 domain = Ustrrchr(s, '@');
1787 if (domain == NULL) return s;
1788 if (domain - s > sizeof(var_buffer) - 1)
1789 log_write(0, LOG_MAIN|LOG_PANIC_DIE, "local part longer than " SIZE_T_FMT
1790 " in string expansion", sizeof(var_buffer));
1791 Ustrncpy(var_buffer, s, domain - s);
1792 var_buffer[domain - s] = 0;
1793 return var_buffer;
1794
1795 case vtype_domain: /* Get domain from address */
1796 s = *((uschar **)(val));
1797 if (s == NULL) return US"";
1798 domain = Ustrrchr(s, '@');
1799 return (domain == NULL)? US"" : domain + 1;
1800
1801 case vtype_msgheaders:
1802 return find_header(NULL, exists_only, newsize, FALSE, NULL);
1803
1804 case vtype_msgheaders_raw:
1805 return find_header(NULL, exists_only, newsize, TRUE, NULL);
1806
1807 case vtype_msgbody: /* Pointer to msgbody string */
1808 case vtype_msgbody_end: /* Ditto, the end of the msg */
1809 ss = (uschar **)(val);
1810 if (*ss == NULL && deliver_datafile >= 0) /* Read body when needed */
1811 {
1812 uschar *body;
1813 off_t start_offset = SPOOL_DATA_START_OFFSET;
1814 int len = message_body_visible;
1815 if (len > message_size) len = message_size;
1816 *ss = body = store_malloc(len+1);
1817 body[0] = 0;
1818 if (vp->type == vtype_msgbody_end)
1819 {
1820 struct stat statbuf;
1821 if (fstat(deliver_datafile, &statbuf) == 0)
1822 {
1823 start_offset = statbuf.st_size - len;
1824 if (start_offset < SPOOL_DATA_START_OFFSET)
1825 start_offset = SPOOL_DATA_START_OFFSET;
1826 }
1827 }
1828 lseek(deliver_datafile, start_offset, SEEK_SET);
1829 len = read(deliver_datafile, body, len);
1830 if (len > 0)
1831 {
1832 body[len] = 0;
1833 if (message_body_newlines) /* Separate loops for efficiency */
1834 {
1835 while (len > 0)
1836 { if (body[--len] == 0) body[len] = ' '; }
1837 }
1838 else
1839 {
1840 while (len > 0)
1841 { if (body[--len] == '\n' || body[len] == 0) body[len] = ' '; }
1842 }
1843 }
1844 }
1845 return (*ss == NULL)? US"" : *ss;
1846
1847 case vtype_todbsdin: /* BSD inbox time of day */
1848 return tod_stamp(tod_bsdin);
1849
1850 case vtype_tode: /* Unix epoch time of day */
1851 return tod_stamp(tod_epoch);
1852
1853 case vtype_todel: /* Unix epoch/usec time of day */
1854 return tod_stamp(tod_epoch_l);
1855
1856 case vtype_todf: /* Full time of day */
1857 return tod_stamp(tod_full);
1858
1859 case vtype_todl: /* Log format time of day */
1860 return tod_stamp(tod_log_bare); /* (without timezone) */
1861
1862 case vtype_todzone: /* Time zone offset only */
1863 return tod_stamp(tod_zone);
1864
1865 case vtype_todzulu: /* Zulu time */
1866 return tod_stamp(tod_zulu);
1867
1868 case vtype_todlf: /* Log file datestamp tod */
1869 return tod_stamp(tod_log_datestamp_daily);
1870
1871 case vtype_reply: /* Get reply address */
1872 s = find_header(US"reply-to:", exists_only, newsize, TRUE,
1873 headers_charset);
1874 if (s != NULL) while (isspace(*s)) s++;
1875 if (s == NULL || *s == 0)
1876 {
1877 *newsize = 0; /* For the *s==0 case */
1878 s = find_header(US"from:", exists_only, newsize, TRUE, headers_charset);
1879 }
1880 if (s != NULL)
1881 {
1882 uschar *t;
1883 while (isspace(*s)) s++;
1884 for (t = s; *t != 0; t++) if (*t == '\n') *t = ' ';
1885 while (t > s && isspace(t[-1])) t--;
1886 *t = 0;
1887 }
1888 return (s == NULL)? US"" : s;
1889
1890 case vtype_string_func:
1891 {
1892 uschar * (*fn)() = val;
1893 return fn();
1894 }
1895
1896 case vtype_pspace:
1897 {
1898 int inodes;
1899 sprintf(CS var_buffer, "%d",
1900 receive_statvfs(val == (void *)TRUE, &inodes));
1901 }
1902 return var_buffer;
1903
1904 case vtype_pinodes:
1905 {
1906 int inodes;
1907 (void) receive_statvfs(val == (void *)TRUE, &inodes);
1908 sprintf(CS var_buffer, "%d", inodes);
1909 }
1910 return var_buffer;
1911
1912 case vtype_cert:
1913 return *(void **)val ? US"<cert>" : US"";
1914
1915 #ifndef DISABLE_DKIM
1916 case vtype_dkim:
1917 return dkim_exim_expand_query((int)(long)val);
1918 #endif
1919
1920 }
1921
1922 return NULL; /* Unknown variable. Silences static checkers. */
1923 }
1924
1925
1926
1927
1928 void
1929 modify_variable(uschar *name, void * value)
1930 {
1931 var_entry * vp;
1932 if ((vp = find_var_ent(name))) vp->value = value;
1933 return; /* Unknown variable name, fail silently */
1934 }
1935
1936
1937
1938
1939
1940 /*************************************************
1941 * Read and expand substrings *
1942 *************************************************/
1943
1944 /* This function is called to read and expand argument substrings for various
1945 expansion items. Some have a minimum requirement that is less than the maximum;
1946 in these cases, the first non-present one is set to NULL.
1947
1948 Arguments:
1949 sub points to vector of pointers to set
1950 n maximum number of substrings
1951 m minimum required
1952 sptr points to current string pointer
1953 skipping the skipping flag
1954 check_end if TRUE, check for final '}'
1955 name name of item, for error message
1956 resetok if not NULL, pointer to flag - write FALSE if unsafe to reset
1957 the store.
1958
1959 Returns: 0 OK; string pointer updated
1960 1 curly bracketing error (too few arguments)
1961 2 too many arguments (only if check_end is set); message set
1962 3 other error (expansion failure)
1963 */
1964
1965 static int
1966 read_subs(uschar **sub, int n, int m, const uschar **sptr, BOOL skipping,
1967 BOOL check_end, uschar *name, BOOL *resetok)
1968 {
1969 int i;
1970 const uschar *s = *sptr;
1971
1972 while (isspace(*s)) s++;
1973 for (i = 0; i < n; i++)
1974 {
1975 if (*s != '{')
1976 {
1977 if (i < m) return 1;
1978 sub[i] = NULL;
1979 break;
1980 }
1981 sub[i] = expand_string_internal(s+1, TRUE, &s, skipping, TRUE, resetok);
1982 if (sub[i] == NULL) return 3;
1983 if (*s++ != '}') return 1;
1984 while (isspace(*s)) s++;
1985 }
1986 if (check_end && *s++ != '}')
1987 {
1988 if (s[-1] == '{')
1989 {
1990 expand_string_message = string_sprintf("Too many arguments for \"%s\" "
1991 "(max is %d)", name, n);
1992 return 2;
1993 }
1994 return 1;
1995 }
1996
1997 *sptr = s;
1998 return 0;
1999 }
2000
2001
2002
2003
2004 /*************************************************
2005 * Elaborate message for bad variable *
2006 *************************************************/
2007
2008 /* For the "unknown variable" message, take a look at the variable's name, and
2009 give additional information about possible ACL variables. The extra information
2010 is added on to expand_string_message.
2011
2012 Argument: the name of the variable
2013 Returns: nothing
2014 */
2015
2016 static void
2017 check_variable_error_message(uschar *name)
2018 {
2019 if (Ustrncmp(name, "acl_", 4) == 0)
2020 expand_string_message = string_sprintf("%s (%s)", expand_string_message,
2021 (name[4] == 'c' || name[4] == 'm')?
2022 (isalpha(name[5])?
2023 US"6th character of a user-defined ACL variable must be a digit or underscore" :
2024 US"strict_acl_vars is set" /* Syntax is OK, it has to be this */
2025 ) :
2026 US"user-defined ACL variables must start acl_c or acl_m");
2027 }
2028
2029
2030
2031 /*
2032 Load args from sub array to globals, and call acl_check().
2033 Sub array will be corrupted on return.
2034
2035 Returns: OK access is granted by an ACCEPT verb
2036 DISCARD access is granted by a DISCARD verb
2037 FAIL access is denied
2038 FAIL_DROP access is denied; drop the connection
2039 DEFER can't tell at the moment
2040 ERROR disaster
2041 */
2042 static int
2043 eval_acl(uschar ** sub, int nsub, uschar ** user_msgp)
2044 {
2045 int i;
2046 int sav_narg = acl_narg;
2047 int ret;
2048 uschar * dummy_logmsg;
2049 extern int acl_where;
2050
2051 if(--nsub > sizeof(acl_arg)/sizeof(*acl_arg)) nsub = sizeof(acl_arg)/sizeof(*acl_arg);
2052 for (i = 0; i < nsub && sub[i+1]; i++)
2053 {
2054 uschar * tmp = acl_arg[i];
2055 acl_arg[i] = sub[i+1]; /* place callers args in the globals */
2056 sub[i+1] = tmp; /* stash the old args using our caller's storage */
2057 }
2058 acl_narg = i;
2059 while (i < nsub)
2060 {
2061 sub[i+1] = acl_arg[i];
2062 acl_arg[i++] = NULL;
2063 }
2064
2065 DEBUG(D_expand)
2066 debug_printf("expanding: acl: %s arg: %s%s\n",
2067 sub[0],
2068 acl_narg>0 ? acl_arg[0] : US"<none>",
2069 acl_narg>1 ? " +more" : "");
2070
2071 ret = acl_eval(acl_where, sub[0], user_msgp, &dummy_logmsg);
2072
2073 for (i = 0; i < nsub; i++)
2074 acl_arg[i] = sub[i+1]; /* restore old args */
2075 acl_narg = sav_narg;
2076
2077 return ret;
2078 }
2079
2080
2081
2082
2083 /*************************************************
2084 * Read and evaluate a condition *
2085 *************************************************/
2086
2087 /*
2088 Arguments:
2089 s points to the start of the condition text
2090 resetok points to a BOOL which is written false if it is unsafe to
2091 free memory. Certain condition types (acl) may have side-effect
2092 allocation which must be preserved.
2093 yield points to a BOOL to hold the result of the condition test;
2094 if NULL, we are just reading through a condition that is
2095 part of an "or" combination to check syntax, or in a state
2096 where the answer isn't required
2097
2098 Returns: a pointer to the first character after the condition, or
2099 NULL after an error
2100 */
2101
2102 static const uschar *
2103 eval_condition(const uschar *s, BOOL *resetok, BOOL *yield)
2104 {
2105 BOOL testfor = TRUE;
2106 BOOL tempcond, combined_cond;
2107 BOOL *subcondptr;
2108 BOOL sub2_honour_dollar = TRUE;
2109 int i, rc, cond_type, roffset;
2110 int_eximarith_t num[2];
2111 struct stat statbuf;
2112 uschar name[256];
2113 const uschar *sub[10];
2114
2115 const pcre *re;
2116 const uschar *rerror;
2117
2118 for (;;)
2119 {
2120 while (isspace(*s)) s++;
2121 if (*s == '!') { testfor = !testfor; s++; } else break;
2122 }
2123
2124 /* Numeric comparisons are symbolic */
2125
2126 if (*s == '=' || *s == '>' || *s == '<')
2127 {
2128 int p = 0;
2129 name[p++] = *s++;
2130 if (*s == '=')
2131 {
2132 name[p++] = '=';
2133 s++;
2134 }
2135 name[p] = 0;
2136 }
2137
2138 /* All other conditions are named */
2139
2140 else s = read_name(name, 256, s, US"_");
2141
2142 /* If we haven't read a name, it means some non-alpha character is first. */
2143
2144 if (name[0] == 0)
2145 {
2146 expand_string_message = string_sprintf("condition name expected, "
2147 "but found \"%.16s\"", s);
2148 return NULL;
2149 }
2150
2151 /* Find which condition we are dealing with, and switch on it */
2152
2153 cond_type = chop_match(name, cond_table, sizeof(cond_table)/sizeof(uschar *));
2154 switch(cond_type)
2155 {
2156 /* def: tests for a non-empty variable, or for the existence of a header. If
2157 yield == NULL we are in a skipping state, and don't care about the answer. */
2158
2159 case ECOND_DEF:
2160 if (*s != ':')
2161 {
2162 expand_string_message = US"\":\" expected after \"def\"";
2163 return NULL;
2164 }
2165
2166 s = read_name(name, 256, s+1, US"_");
2167
2168 /* Test for a header's existence. If the name contains a closing brace
2169 character, this may be a user error where the terminating colon has been
2170 omitted. Set a flag to adjust a subsequent error message in this case. */
2171
2172 if (Ustrncmp(name, "h_", 2) == 0 ||
2173 Ustrncmp(name, "rh_", 3) == 0 ||
2174 Ustrncmp(name, "bh_", 3) == 0 ||
2175 Ustrncmp(name, "header_", 7) == 0 ||
2176 Ustrncmp(name, "rheader_", 8) == 0 ||
2177 Ustrncmp(name, "bheader_", 8) == 0)
2178 {
2179 s = read_header_name(name, 256, s);
2180 /* {-for-text-editors */
2181 if (Ustrchr(name, '}') != NULL) malformed_header = TRUE;
2182 if (yield != NULL) *yield =
2183 (find_header(name, TRUE, NULL, FALSE, NULL) != NULL) == testfor;
2184 }
2185
2186 /* Test for a variable's having a non-empty value. A non-existent variable
2187 causes an expansion failure. */
2188
2189 else
2190 {
2191 uschar *value = find_variable(name, TRUE, yield == NULL, NULL);
2192 if (value == NULL)
2193 {
2194 expand_string_message = (name[0] == 0)?
2195 string_sprintf("variable name omitted after \"def:\"") :
2196 string_sprintf("unknown variable \"%s\" after \"def:\"", name);
2197 check_variable_error_message(name);
2198 return NULL;
2199 }
2200 if (yield != NULL) *yield = (value[0] != 0) == testfor;
2201 }
2202
2203 return s;
2204
2205
2206 /* first_delivery tests for first delivery attempt */
2207
2208 case ECOND_FIRST_DELIVERY:
2209 if (yield != NULL) *yield = deliver_firsttime == testfor;
2210 return s;
2211
2212
2213 /* queue_running tests for any process started by a queue runner */
2214
2215 case ECOND_QUEUE_RUNNING:
2216 if (yield != NULL) *yield = (queue_run_pid != (pid_t)0) == testfor;
2217 return s;
2218
2219
2220 /* exists: tests for file existence
2221 isip: tests for any IP address
2222 isip4: tests for an IPv4 address
2223 isip6: tests for an IPv6 address
2224 pam: does PAM authentication
2225 radius: does RADIUS authentication
2226 ldapauth: does LDAP authentication
2227 pwcheck: does Cyrus SASL pwcheck authentication
2228 */
2229
2230 case ECOND_EXISTS:
2231 case ECOND_ISIP:
2232 case ECOND_ISIP4:
2233 case ECOND_ISIP6:
2234 case ECOND_PAM:
2235 case ECOND_RADIUS:
2236 case ECOND_LDAPAUTH:
2237 case ECOND_PWCHECK:
2238
2239 while (isspace(*s)) s++;
2240 if (*s != '{') goto COND_FAILED_CURLY_START; /* }-for-text-editors */
2241
2242 sub[0] = expand_string_internal(s+1, TRUE, &s, yield == NULL, TRUE, resetok);
2243 if (sub[0] == NULL) return NULL;
2244 /* {-for-text-editors */
2245 if (*s++ != '}') goto COND_FAILED_CURLY_END;
2246
2247 if (yield == NULL) return s; /* No need to run the test if skipping */
2248
2249 switch(cond_type)
2250 {
2251 case ECOND_EXISTS:
2252 if ((expand_forbid & RDO_EXISTS) != 0)
2253 {
2254 expand_string_message = US"File existence tests are not permitted";
2255 return NULL;
2256 }
2257 *yield = (Ustat(sub[0], &statbuf) == 0) == testfor;
2258 break;
2259
2260 case ECOND_ISIP:
2261 case ECOND_ISIP4:
2262 case ECOND_ISIP6:
2263 rc = string_is_ip_address(sub[0], NULL);
2264 *yield = ((cond_type == ECOND_ISIP)? (rc != 0) :
2265 (cond_type == ECOND_ISIP4)? (rc == 4) : (rc == 6)) == testfor;
2266 break;
2267
2268 /* Various authentication tests - all optionally compiled */
2269
2270 case ECOND_PAM:
2271 #ifdef SUPPORT_PAM
2272 rc = auth_call_pam(sub[0], &expand_string_message);
2273 goto END_AUTH;
2274 #else
2275 goto COND_FAILED_NOT_COMPILED;
2276 #endif /* SUPPORT_PAM */
2277
2278 case ECOND_RADIUS:
2279 #ifdef RADIUS_CONFIG_FILE
2280 rc = auth_call_radius(sub[0], &expand_string_message);
2281 goto END_AUTH;
2282 #else
2283 goto COND_FAILED_NOT_COMPILED;
2284 #endif /* RADIUS_CONFIG_FILE */
2285
2286 case ECOND_LDAPAUTH:
2287 #ifdef LOOKUP_LDAP
2288 {
2289 /* Just to keep the interface the same */
2290 BOOL do_cache;
2291 int old_pool = store_pool;
2292 store_pool = POOL_SEARCH;
2293 rc = eldapauth_find((void *)(-1), NULL, sub[0], Ustrlen(sub[0]), NULL,
2294 &expand_string_message, &do_cache);
2295 store_pool = old_pool;
2296 }
2297 goto END_AUTH;
2298 #else
2299 goto COND_FAILED_NOT_COMPILED;
2300 #endif /* LOOKUP_LDAP */
2301
2302 case ECOND_PWCHECK:
2303 #ifdef CYRUS_PWCHECK_SOCKET
2304 rc = auth_call_pwcheck(sub[0], &expand_string_message);
2305 goto END_AUTH;
2306 #else
2307 goto COND_FAILED_NOT_COMPILED;
2308 #endif /* CYRUS_PWCHECK_SOCKET */
2309
2310 #if defined(SUPPORT_PAM) || defined(RADIUS_CONFIG_FILE) || \
2311 defined(LOOKUP_LDAP) || defined(CYRUS_PWCHECK_SOCKET)
2312 END_AUTH:
2313 if (rc == ERROR || rc == DEFER) return NULL;
2314 *yield = (rc == OK) == testfor;
2315 #endif
2316 }
2317 return s;
2318
2319
2320 /* call ACL (in a conditional context). Accept true, deny false.
2321 Defer is a forced-fail. Anything set by message= goes to $value.
2322 Up to ten parameters are used; we use the braces round the name+args
2323 like the saslauthd condition does, to permit a variable number of args.
2324 See also the expansion-item version EITEM_ACL and the traditional
2325 acl modifier ACLC_ACL.
2326 Since the ACL may allocate new global variables, tell our caller to not
2327 reclaim memory.
2328 */
2329
2330 case ECOND_ACL:
2331 /* ${if acl {{name}{arg1}{arg2}...} {yes}{no}} */
2332 {
2333 uschar *sub[10];
2334 uschar *user_msg;
2335 BOOL cond = FALSE;
2336 int size = 0;
2337 int ptr = 0;
2338
2339 while (isspace(*s)) s++;
2340 if (*s++ != '{') goto COND_FAILED_CURLY_START; /*}*/
2341
2342 switch(read_subs(sub, sizeof(sub)/sizeof(*sub), 1,
2343 &s, yield == NULL, TRUE, US"acl", resetok))
2344 {
2345 case 1: expand_string_message = US"too few arguments or bracketing "
2346 "error for acl";
2347 case 2:
2348 case 3: return NULL;
2349 }
2350
2351 *resetok = FALSE;
2352 if (yield != NULL) switch(eval_acl(sub, sizeof(sub)/sizeof(*sub), &user_msg))
2353 {
2354 case OK:
2355 cond = TRUE;
2356 case FAIL:
2357 lookup_value = NULL;
2358 if (user_msg)
2359 {
2360 lookup_value = string_cat(NULL, &size, &ptr, user_msg, Ustrlen(user_msg));
2361 lookup_value[ptr] = '\0';
2362 }
2363 *yield = cond == testfor;
2364 break;
2365
2366 case DEFER:
2367 expand_string_forcedfail = TRUE;
2368 default:
2369 expand_string_message = string_sprintf("error from acl \"%s\"", sub[0]);
2370 return NULL;
2371 }
2372 return s;
2373 }
2374
2375
2376 /* saslauthd: does Cyrus saslauthd authentication. Four parameters are used:
2377
2378 ${if saslauthd {{username}{password}{service}{realm}} {yes}{no}}
2379
2380 However, the last two are optional. That is why the whole set is enclosed
2381 in their own set of braces. */
2382
2383 case ECOND_SASLAUTHD:
2384 #ifndef CYRUS_SASLAUTHD_SOCKET
2385 goto COND_FAILED_NOT_COMPILED;
2386 #else
2387 while (isspace(*s)) s++;
2388 if (*s++ != '{') goto COND_FAILED_CURLY_START; /* }-for-text-editors */
2389 switch(read_subs(sub, 4, 2, &s, yield == NULL, TRUE, US"saslauthd", resetok))
2390 {
2391 case 1: expand_string_message = US"too few arguments or bracketing "
2392 "error for saslauthd";
2393 case 2:
2394 case 3: return NULL;
2395 }
2396 if (sub[2] == NULL) sub[3] = NULL; /* realm if no service */
2397 if (yield != NULL)
2398 {
2399 int rc;
2400 rc = auth_call_saslauthd(sub[0], sub[1], sub[2], sub[3],
2401 &expand_string_message);
2402 if (rc == ERROR || rc == DEFER) return NULL;
2403 *yield = (rc == OK) == testfor;
2404 }
2405 return s;
2406 #endif /* CYRUS_SASLAUTHD_SOCKET */
2407
2408
2409 /* symbolic operators for numeric and string comparison, and a number of
2410 other operators, all requiring two arguments.
2411
2412 crypteq: encrypts plaintext and compares against an encrypted text,
2413 using crypt(), crypt16(), MD5 or SHA-1
2414 inlist/inlisti: checks if first argument is in the list of the second
2415 match: does a regular expression match and sets up the numerical
2416 variables if it succeeds
2417 match_address: matches in an address list
2418 match_domain: matches in a domain list
2419 match_ip: matches a host list that is restricted to IP addresses
2420 match_local_part: matches in a local part list
2421 */
2422
2423 case ECOND_MATCH_ADDRESS:
2424 case ECOND_MATCH_DOMAIN:
2425 case ECOND_MATCH_IP:
2426 case ECOND_MATCH_LOCAL_PART:
2427 #ifndef EXPAND_LISTMATCH_RHS
2428 sub2_honour_dollar = FALSE;
2429 #endif
2430 /* FALLTHROUGH */
2431
2432 case ECOND_CRYPTEQ:
2433 case ECOND_INLIST:
2434 case ECOND_INLISTI:
2435 case ECOND_MATCH:
2436
2437 case ECOND_NUM_L: /* Numerical comparisons */
2438 case ECOND_NUM_LE:
2439 case ECOND_NUM_E:
2440 case ECOND_NUM_EE:
2441 case ECOND_NUM_G:
2442 case ECOND_NUM_GE:
2443
2444 case ECOND_STR_LT: /* String comparisons */
2445 case ECOND_STR_LTI:
2446 case ECOND_STR_LE:
2447 case ECOND_STR_LEI:
2448 case ECOND_STR_EQ:
2449 case ECOND_STR_EQI:
2450 case ECOND_STR_GT:
2451 case ECOND_STR_GTI:
2452 case ECOND_STR_GE:
2453 case ECOND_STR_GEI:
2454
2455 for (i = 0; i < 2; i++)
2456 {
2457 /* Sometimes, we don't expand substrings; too many insecure configurations
2458 created using match_address{}{} and friends, where the second param
2459 includes information from untrustworthy sources. */
2460 BOOL honour_dollar = TRUE;
2461 if ((i > 0) && !sub2_honour_dollar)
2462 honour_dollar = FALSE;
2463
2464 while (isspace(*s)) s++;
2465 if (*s != '{')
2466 {
2467 if (i == 0) goto COND_FAILED_CURLY_START;
2468 expand_string_message = string_sprintf("missing 2nd string in {} "
2469 "after \"%s\"", name);
2470 return NULL;
2471 }
2472 sub[i] = expand_string_internal(s+1, TRUE, &s, yield == NULL,
2473 honour_dollar, resetok);
2474 if (sub[i] == NULL) return NULL;
2475 if (*s++ != '}') goto COND_FAILED_CURLY_END;
2476
2477 /* Convert to numerical if required; we know that the names of all the
2478 conditions that compare numbers do not start with a letter. This just saves
2479 checking for them individually. */
2480
2481 if (!isalpha(name[0]) && yield != NULL)
2482 {
2483 if (sub[i][0] == 0)
2484 {
2485 num[i] = 0;
2486 DEBUG(D_expand)
2487 debug_printf("empty string cast to zero for numerical comparison\n");
2488 }
2489 else
2490 {
2491 num[i] = expanded_string_integer(sub[i], FALSE);
2492 if (expand_string_message != NULL) return NULL;
2493 }
2494 }
2495 }
2496
2497 /* Result not required */
2498
2499 if (yield == NULL) return s;
2500
2501 /* Do an appropriate comparison */
2502
2503 switch(cond_type)
2504 {
2505 case ECOND_NUM_E:
2506 case ECOND_NUM_EE:
2507 tempcond = (num[0] == num[1]);
2508 break;
2509
2510 case ECOND_NUM_G:
2511 tempcond = (num[0] > num[1]);
2512 break;
2513
2514 case ECOND_NUM_GE:
2515 tempcond = (num[0] >= num[1]);
2516 break;
2517
2518 case ECOND_NUM_L:
2519 tempcond = (num[0] < num[1]);
2520 break;
2521
2522 case ECOND_NUM_LE:
2523 tempcond = (num[0] <= num[1]);
2524 break;
2525
2526 case ECOND_STR_LT:
2527 tempcond = (Ustrcmp(sub[0], sub[1]) < 0);
2528 break;
2529
2530 case ECOND_STR_LTI:
2531 tempcond = (strcmpic(sub[0], sub[1]) < 0);
2532 break;
2533
2534 case ECOND_STR_LE:
2535 tempcond = (Ustrcmp(sub[0], sub[1]) <= 0);
2536 break;
2537
2538 case ECOND_STR_LEI:
2539 tempcond = (strcmpic(sub[0], sub[1]) <= 0);
2540 break;
2541
2542 case ECOND_STR_EQ:
2543 tempcond = (Ustrcmp(sub[0], sub[1]) == 0);
2544 break;
2545
2546 case ECOND_STR_EQI:
2547 tempcond = (strcmpic(sub[0], sub[1]) == 0);
2548 break;
2549
2550 case ECOND_STR_GT:
2551 tempcond = (Ustrcmp(sub[0], sub[1]) > 0);
2552 break;
2553
2554 case ECOND_STR_GTI:
2555 tempcond = (strcmpic(sub[0], sub[1]) > 0);
2556 break;
2557
2558 case ECOND_STR_GE:
2559 tempcond = (Ustrcmp(sub[0], sub[1]) >= 0);
2560 break;
2561
2562 case ECOND_STR_GEI:
2563 tempcond = (strcmpic(sub[0], sub[1]) >= 0);
2564 break;
2565
2566 case ECOND_MATCH: /* Regular expression match */
2567 re = pcre_compile(CS sub[1], PCRE_COPT, (const char **)&rerror, &roffset,
2568 NULL);
2569 if (re == NULL)
2570 {
2571 expand_string_message = string_sprintf("regular expression error in "
2572 "\"%s\": %s at offset %d", sub[1], rerror, roffset);
2573 return NULL;
2574 }
2575 tempcond = regex_match_and_setup(re, sub[0], 0, -1);
2576 break;
2577
2578 case ECOND_MATCH_ADDRESS: /* Match in an address list */
2579 rc = match_address_list(sub[0], TRUE, FALSE, &(sub[1]), NULL, -1, 0, NULL);
2580 goto MATCHED_SOMETHING;
2581
2582 case ECOND_MATCH_DOMAIN: /* Match in a domain list */
2583 rc = match_isinlist(sub[0], &(sub[1]), 0, &domainlist_anchor, NULL,
2584 MCL_DOMAIN + MCL_NOEXPAND, TRUE, NULL);
2585 goto MATCHED_SOMETHING;
2586
2587 case ECOND_MATCH_IP: /* Match IP address in a host list */
2588 if (sub[0][0] != 0 && string_is_ip_address(sub[0], NULL) == 0)
2589 {
2590 expand_string_message = string_sprintf("\"%s\" is not an IP address",
2591 sub[0]);
2592 return NULL;
2593 }
2594 else
2595 {
2596 unsigned int *nullcache = NULL;
2597 check_host_block cb;
2598
2599 cb.host_name = US"";
2600 cb.host_address = sub[0];
2601
2602 /* If the host address starts off ::ffff: it is an IPv6 address in
2603 IPv4-compatible mode. Find the IPv4 part for checking against IPv4
2604 addresses. */
2605
2606 cb.host_ipv4 = (Ustrncmp(cb.host_address, "::ffff:", 7) == 0)?
2607 cb.host_address + 7 : cb.host_address;
2608
2609 rc = match_check_list(
2610 &sub[1], /* the list */
2611 0, /* separator character */
2612 &hostlist_anchor, /* anchor pointer */
2613 &nullcache, /* cache pointer */
2614 check_host, /* function for testing */
2615 &cb, /* argument for function */
2616 MCL_HOST, /* type of check */
2617 sub[0], /* text for debugging */
2618 NULL); /* where to pass back data */
2619 }
2620 goto MATCHED_SOMETHING;
2621
2622 case ECOND_MATCH_LOCAL_PART:
2623 rc = match_isinlist(sub[0], &(sub[1]), 0, &localpartlist_anchor, NULL,
2624 MCL_LOCALPART + MCL_NOEXPAND, TRUE, NULL);
2625 /* Fall through */
2626 /* VVVVVVVVVVVV */
2627 MATCHED_SOMETHING:
2628 switch(rc)
2629 {
2630 case OK:
2631 tempcond = TRUE;
2632 break;
2633
2634 case FAIL:
2635 tempcond = FALSE;
2636 break;
2637
2638 case DEFER:
2639 expand_string_message = string_sprintf("unable to complete match "
2640 "against \"%s\": %s", sub[1], search_error_message);
2641 return NULL;
2642 }
2643
2644 break;
2645
2646 /* Various "encrypted" comparisons. If the second string starts with
2647 "{" then an encryption type is given. Default to crypt() or crypt16()
2648 (build-time choice). */
2649 /* }-for-text-editors */
2650
2651 case ECOND_CRYPTEQ:
2652 #ifndef SUPPORT_CRYPTEQ
2653 goto COND_FAILED_NOT_COMPILED;
2654 #else
2655 if (strncmpic(sub[1], US"{md5}", 5) == 0)
2656 {
2657 int sublen = Ustrlen(sub[1]+5);
2658 md5 base;
2659 uschar digest[16];
2660
2661 md5_start(&base);
2662 md5_end(&base, (uschar *)sub[0], Ustrlen(sub[0]), digest);
2663
2664 /* If the length that we are comparing against is 24, the MD5 digest
2665 is expressed as a base64 string. This is the way LDAP does it. However,
2666 some other software uses a straightforward hex representation. We assume
2667 this if the length is 32. Other lengths fail. */
2668
2669 if (sublen == 24)
2670 {
2671 uschar *coded = auth_b64encode((uschar *)digest, 16);
2672 DEBUG(D_auth) debug_printf("crypteq: using MD5+B64 hashing\n"
2673 " subject=%s\n crypted=%s\n", coded, sub[1]+5);
2674 tempcond = (Ustrcmp(coded, sub[1]+5) == 0);
2675 }
2676 else if (sublen == 32)
2677 {
2678 int i;
2679 uschar coded[36];
2680 for (i = 0; i < 16; i++) sprintf(CS (coded+2*i), "%02X", digest[i]);
2681 coded[32] = 0;
2682 DEBUG(D_auth) debug_printf("crypteq: using MD5+hex hashing\n"
2683 " subject=%s\n crypted=%s\n", coded, sub[1]+5);
2684 tempcond = (strcmpic(coded, sub[1]+5) == 0);
2685 }
2686 else
2687 {
2688 DEBUG(D_auth) debug_printf("crypteq: length for MD5 not 24 or 32: "
2689 "fail\n crypted=%s\n", sub[1]+5);
2690 tempcond = FALSE;
2691 }
2692 }
2693
2694 else if (strncmpic(sub[1], US"{sha1}", 6) == 0)
2695 {
2696 int sublen = Ustrlen(sub[1]+6);
2697 sha1 base;
2698 uschar digest[20];
2699
2700 sha1_start(&base);
2701 sha1_end(&base, (uschar *)sub[0], Ustrlen(sub[0]), digest);
2702
2703 /* If the length that we are comparing against is 28, assume the SHA1
2704 digest is expressed as a base64 string. If the length is 40, assume a
2705 straightforward hex representation. Other lengths fail. */
2706
2707 if (sublen == 28)
2708 {
2709 uschar *coded = auth_b64encode((uschar *)digest, 20);
2710 DEBUG(D_auth) debug_printf("crypteq: using SHA1+B64 hashing\n"
2711 " subject=%s\n crypted=%s\n", coded, sub[1]+6);
2712 tempcond = (Ustrcmp(coded, sub[1]+6) == 0);
2713 }
2714 else if (sublen == 40)
2715 {
2716 int i;
2717 uschar coded[44];
2718 for (i = 0; i < 20; i++) sprintf(CS (coded+2*i), "%02X", digest[i]);
2719 coded[40] = 0;
2720 DEBUG(D_auth) debug_printf("crypteq: using SHA1+hex hashing\n"
2721 " subject=%s\n crypted=%s\n", coded, sub[1]+6);
2722 tempcond = (strcmpic(coded, sub[1]+6) == 0);
2723 }
2724 else
2725 {
2726 DEBUG(D_auth) debug_printf("crypteq: length for SHA-1 not 28 or 40: "
2727 "fail\n crypted=%s\n", sub[1]+6);
2728 tempcond = FALSE;
2729 }
2730 }
2731
2732 else /* {crypt} or {crypt16} and non-{ at start */
2733 /* }-for-text-editors */
2734 {
2735 int which = 0;
2736 uschar *coded;
2737
2738 if (strncmpic(sub[1], US"{crypt}", 7) == 0)
2739 {
2740 sub[1] += 7;
2741 which = 1;
2742 }
2743 else if (strncmpic(sub[1], US"{crypt16}", 9) == 0)
2744 {
2745 sub[1] += 9;
2746 which = 2;
2747 }
2748 else if (sub[1][0] == '{') /* }-for-text-editors */
2749 {
2750 expand_string_message = string_sprintf("unknown encryption mechanism "
2751 "in \"%s\"", sub[1]);
2752 return NULL;
2753 }
2754
2755 switch(which)
2756 {
2757 case 0: coded = US DEFAULT_CRYPT(CS sub[0], CS sub[1]); break;
2758 case 1: coded = US crypt(CS sub[0], CS sub[1]); break;
2759 default: coded = US crypt16(CS sub[0], CS sub[1]); break;
2760 }
2761
2762 #define STR(s) # s
2763 #define XSTR(s) STR(s)
2764 DEBUG(D_auth) debug_printf("crypteq: using %s()\n"
2765 " subject=%s\n crypted=%s\n",
2766 (which == 0)? XSTR(DEFAULT_CRYPT) : (which == 1)? "crypt" : "crypt16",
2767 coded, sub[1]);
2768 #undef STR
2769 #undef XSTR
2770
2771 /* If the encrypted string contains fewer than two characters (for the
2772 salt), force failure. Otherwise we get false positives: with an empty
2773 string the yield of crypt() is an empty string! */
2774
2775 tempcond = (Ustrlen(sub[1]) < 2)? FALSE :
2776 (Ustrcmp(coded, sub[1]) == 0);
2777 }
2778 break;
2779 #endif /* SUPPORT_CRYPTEQ */
2780
2781 case ECOND_INLIST:
2782 case ECOND_INLISTI:
2783 {
2784 const uschar * list = sub[1];
2785 int sep = 0;
2786 uschar *save_iterate_item = iterate_item;
2787 int (*compare)(const uschar *, const uschar *);
2788
2789 DEBUG(D_expand) debug_printf("condition: %s\n", name);
2790
2791 tempcond = FALSE;
2792 compare = cond_type == ECOND_INLISTI
2793 ? strcmpic : (int (*)(const uschar *, const uschar *)) strcmp;
2794
2795 while ((iterate_item = string_nextinlist(&list, &sep, NULL, 0)))
2796 if (compare(sub[0], iterate_item) == 0)
2797 {
2798 tempcond = TRUE;
2799 break;
2800 }
2801 iterate_item = save_iterate_item;
2802 }
2803
2804 } /* Switch for comparison conditions */
2805
2806 *yield = tempcond == testfor;
2807 return s; /* End of comparison conditions */
2808
2809
2810 /* and/or: computes logical and/or of several conditions */
2811
2812 case ECOND_AND:
2813 case ECOND_OR:
2814 subcondptr = (yield == NULL)? NULL : &tempcond;
2815 combined_cond = (cond_type == ECOND_AND);
2816
2817 while (isspace(*s)) s++;
2818 if (*s++ != '{') goto COND_FAILED_CURLY_START; /* }-for-text-editors */
2819
2820 for (;;)
2821 {
2822 while (isspace(*s)) s++;
2823 /* {-for-text-editors */
2824 if (*s == '}') break;
2825 if (*s != '{') /* }-for-text-editors */
2826 {
2827 expand_string_message = string_sprintf("each subcondition "
2828 "inside an \"%s{...}\" condition must be in its own {}", name);
2829 return NULL;
2830 }
2831
2832 if (!(s = eval_condition(s+1, resetok, subcondptr)))
2833 {
2834 expand_string_message = string_sprintf("%s inside \"%s{...}\" condition",
2835 expand_string_message, name);
2836 return NULL;
2837 }
2838 while (isspace(*s)) s++;
2839
2840 /* {-for-text-editors */
2841 if (*s++ != '}')
2842 {
2843 /* {-for-text-editors */
2844 expand_string_message = string_sprintf("missing } at end of condition "
2845 "inside \"%s\" group", name);
2846 return NULL;
2847 }
2848
2849 if (yield != NULL)
2850 {
2851 if (cond_type == ECOND_AND)
2852 {
2853 combined_cond &= tempcond;
2854 if (!combined_cond) subcondptr = NULL; /* once false, don't */
2855 } /* evaluate any more */
2856 else
2857 {
2858 combined_cond |= tempcond;
2859 if (combined_cond) subcondptr = NULL; /* once true, don't */
2860 } /* evaluate any more */
2861 }
2862 }
2863
2864 if (yield != NULL) *yield = (combined_cond == testfor);
2865 return ++s;
2866
2867
2868 /* forall/forany: iterates a condition with different values */
2869
2870 case ECOND_FORALL:
2871 case ECOND_FORANY:
2872 {
2873 const uschar * list;
2874 int sep = 0;
2875 uschar *save_iterate_item = iterate_item;
2876
2877 DEBUG(D_expand) debug_printf("condition: %s\n", name);
2878
2879 while (isspace(*s)) s++;
2880 if (*s++ != '{') goto COND_FAILED_CURLY_START; /* }-for-text-editors */
2881 sub[0] = expand_string_internal(s, TRUE, &s, (yield == NULL), TRUE, resetok);
2882 if (sub[0] == NULL) return NULL;
2883 /* {-for-text-editors */
2884 if (*s++ != '}') goto COND_FAILED_CURLY_END;
2885
2886 while (isspace(*s)) s++;
2887 if (*s++ != '{') goto COND_FAILED_CURLY_START; /* }-for-text-editors */
2888
2889 sub[1] = s;
2890
2891 /* Call eval_condition once, with result discarded (as if scanning a
2892 "false" part). This allows us to find the end of the condition, because if
2893 the list it empty, we won't actually evaluate the condition for real. */
2894
2895 if (!(s = eval_condition(sub[1], resetok, NULL)))
2896 {
2897 expand_string_message = string_sprintf("%s inside \"%s\" condition",
2898 expand_string_message, name);
2899 return NULL;
2900 }
2901 while (isspace(*s)) s++;
2902
2903 /* {-for-text-editors */
2904 if (*s++ != '}')
2905 {
2906 /* {-for-text-editors */
2907 expand_string_message = string_sprintf("missing } at end of condition "
2908 "inside \"%s\"", name);
2909 return NULL;
2910 }
2911
2912 if (yield != NULL) *yield = !testfor;
2913 list = sub[0];
2914 while ((iterate_item = string_nextinlist(&list, &sep, NULL, 0)) != NULL)
2915 {
2916 DEBUG(D_expand) debug_printf("%s: $item = \"%s\"\n", name, iterate_item);
2917 if (!eval_condition(sub[1], resetok, &tempcond))
2918 {
2919 expand_string_message = string_sprintf("%s inside \"%s\" condition",
2920 expand_string_message, name);
2921 iterate_item = save_iterate_item;
2922 return NULL;
2923 }
2924 DEBUG(D_expand) debug_printf("%s: condition evaluated to %s\n", name,
2925 tempcond? "true":"false");
2926
2927 if (yield != NULL) *yield = (tempcond == testfor);
2928 if (tempcond == (cond_type == ECOND_FORANY)) break;
2929 }
2930
2931 iterate_item = save_iterate_item;
2932 return s;
2933 }
2934
2935
2936 /* The bool{} expansion condition maps a string to boolean.
2937 The values supported should match those supported by the ACL condition
2938 (acl.c, ACLC_CONDITION) so that we keep to a minimum the different ideas
2939 of true/false. Note that Router "condition" rules have a different
2940 interpretation, where general data can be used and only a few values
2941 map to FALSE.
2942 Note that readconf.c boolean matching, for boolean configuration options,
2943 only matches true/yes/false/no.
2944 The bool_lax{} condition matches the Router logic, which is much more
2945 liberal. */
2946 case ECOND_BOOL:
2947 case ECOND_BOOL_LAX:
2948 {
2949 uschar *sub_arg[1];
2950 uschar *t, *t2;
2951 uschar *ourname;
2952 size_t len;
2953 BOOL boolvalue = FALSE;
2954 while (isspace(*s)) s++;
2955 if (*s != '{') goto COND_FAILED_CURLY_START; /* }-for-text-editors */
2956 ourname = cond_type == ECOND_BOOL_LAX ? US"bool_lax" : US"bool";
2957 switch(read_subs(sub_arg, 1, 1, &s, yield == NULL, FALSE, ourname, resetok))
2958 {
2959 case 1: expand_string_message = string_sprintf(
2960 "too few arguments or bracketing error for %s",
2961 ourname);
2962 /*FALLTHROUGH*/
2963 case 2:
2964 case 3: return NULL;
2965 }
2966 t = sub_arg[0];
2967 while (isspace(*t)) t++;
2968 len = Ustrlen(t);
2969 if (len)
2970 {
2971 /* trailing whitespace: seems like a good idea to ignore it too */
2972 t2 = t + len - 1;
2973 while (isspace(*t2)) t2--;
2974 if (t2 != (t + len))
2975 {
2976 *++t2 = '\0';
2977 len = t2 - t;
2978 }
2979 }
2980 DEBUG(D_expand)
2981 debug_printf("considering %s: %s\n", ourname, len ? t : US"<empty>");
2982 /* logic for the lax case from expand_check_condition(), which also does
2983 expands, and the logic is both short and stable enough that there should
2984 be no maintenance burden from replicating it. */
2985 if (len == 0)
2986 boolvalue = FALSE;
2987 else if (*t == '-'
2988 ? Ustrspn(t+1, "0123456789") == len-1
2989 : Ustrspn(t, "0123456789") == len)
2990 {
2991 boolvalue = (Uatoi(t) == 0) ? FALSE : TRUE;
2992 /* expand_check_condition only does a literal string "0" check */
2993 if ((cond_type == ECOND_BOOL_LAX) && (len > 1))
2994 boolvalue = TRUE;
2995 }
2996 else if (strcmpic(t, US"true") == 0 || strcmpic(t, US"yes") == 0)
2997 boolvalue = TRUE;
2998 else if (strcmpic(t, US"false") == 0 || strcmpic(t, US"no") == 0)
2999 boolvalue = FALSE;
3000 else if (cond_type == ECOND_BOOL_LAX)
3001 boolvalue = TRUE;
3002 else
3003 {
3004 expand_string_message = string_sprintf("unrecognised boolean "
3005 "value \"%s\"", t);
3006 return NULL;
3007 }
3008 if (yield != NULL) *yield = (boolvalue == testfor);
3009 return s;
3010 }
3011
3012 /* Unknown condition */
3013
3014 default:
3015 expand_string_message = string_sprintf("unknown condition \"%s\"", name);
3016 return NULL;
3017 } /* End switch on condition type */
3018
3019 /* Missing braces at start and end of data */
3020
3021 COND_FAILED_CURLY_START:
3022 expand_string_message = string_sprintf("missing { after \"%s\"", name);
3023 return NULL;
3024
3025 COND_FAILED_CURLY_END:
3026 expand_string_message = string_sprintf("missing } at end of \"%s\" condition",
3027 name);
3028 return NULL;
3029
3030 /* A condition requires code that is not compiled */
3031
3032 #if !defined(SUPPORT_PAM) || !defined(RADIUS_CONFIG_FILE) || \
3033 !defined(LOOKUP_LDAP) || !defined(CYRUS_PWCHECK_SOCKET) || \
3034 !defined(SUPPORT_CRYPTEQ) || !defined(CYRUS_SASLAUTHD_SOCKET)
3035 COND_FAILED_NOT_COMPILED:
3036 expand_string_message = string_sprintf("support for \"%s\" not compiled",
3037 name);
3038 return NULL;
3039 #endif
3040 }
3041
3042
3043
3044
3045 /*************************************************
3046 * Save numerical variables *
3047 *************************************************/
3048
3049 /* This function is called from items such as "if" that want to preserve and
3050 restore the numbered variables.
3051
3052 Arguments:
3053 save_expand_string points to an array of pointers to set
3054 save_expand_nlength points to an array of ints for the lengths
3055
3056 Returns: the value of expand max to save
3057 */
3058
3059 static int
3060 save_expand_strings(uschar **save_expand_nstring, int *save_expand_nlength)
3061 {
3062 int i;
3063 for (i = 0; i <= expand_nmax; i++)
3064 {
3065 save_expand_nstring[i] = expand_nstring[i];
3066 save_expand_nlength[i] = expand_nlength[i];
3067 }
3068 return expand_nmax;
3069 }
3070
3071
3072
3073 /*************************************************
3074 * Restore numerical variables *
3075 *************************************************/
3076
3077 /* This function restored saved values of numerical strings.
3078
3079 Arguments:
3080 save_expand_nmax the number of strings to restore
3081 save_expand_string points to an array of pointers
3082 save_expand_nlength points to an array of ints
3083
3084 Returns: nothing
3085 */
3086
3087 static void
3088 restore_expand_strings(int save_expand_nmax, uschar **save_expand_nstring,
3089 int *save_expand_nlength)
3090 {
3091 int i;
3092 expand_nmax = save_expand_nmax;
3093 for (i = 0; i <= expand_nmax; i++)
3094 {
3095 expand_nstring[i] = save_expand_nstring[i];
3096 expand_nlength[i] = save_expand_nlength[i];
3097 }
3098 }
3099
3100
3101
3102
3103
3104 /*************************************************
3105 * Handle yes/no substrings *
3106 *************************************************/
3107
3108 /* This function is used by ${if}, ${lookup} and ${extract} to handle the
3109 alternative substrings that depend on whether or not the condition was true,
3110 or the lookup or extraction succeeded. The substrings always have to be
3111 expanded, to check their syntax, but "skipping" is set when the result is not
3112 needed - this avoids unnecessary nested lookups.
3113
3114 Arguments:
3115 skipping TRUE if we were skipping when this item was reached
3116 yes TRUE if the first string is to be used, else use the second
3117 save_lookup a value to put back into lookup_value before the 2nd expansion
3118 sptr points to the input string pointer
3119 yieldptr points to the output string pointer
3120 sizeptr points to the output string size
3121 ptrptr points to the output string pointer
3122 type "lookup" or "if" or "extract" or "run", for error message
3123 resetok if not NULL, pointer to flag - write FALSE if unsafe to reset
3124 the store.
3125
3126 Returns: 0 OK; lookup_value has been reset to save_lookup
3127 1 expansion failed
3128 2 expansion failed because of bracketing error
3129 */
3130
3131 static int
3132 process_yesno(BOOL skipping, BOOL yes, uschar *save_lookup, const uschar **sptr,
3133 uschar **yieldptr, int *sizeptr, int *ptrptr, uschar *type, BOOL *resetok)
3134 {
3135 int rc = 0;
3136 const uschar *s = *sptr; /* Local value */
3137 uschar *sub1, *sub2;
3138
3139 /* If there are no following strings, we substitute the contents of $value for
3140 lookups and for extractions in the success case. For the ${if item, the string
3141 "true" is substituted. In the fail case, nothing is substituted for all three
3142 items. */
3143
3144 while (isspace(*s)) s++;
3145 if (*s == '}')
3146 {
3147 if (type[0] == 'i')
3148 {
3149 if (yes) *yieldptr = string_cat(*yieldptr, sizeptr, ptrptr, US"true", 4);
3150 }
3151 else
3152 {
3153 if (yes && lookup_value != NULL)
3154 *yieldptr = string_cat(*yieldptr, sizeptr, ptrptr, lookup_value,
3155 Ustrlen(lookup_value));
3156 lookup_value = save_lookup;
3157 }
3158 s++;
3159 goto RETURN;
3160 }
3161
3162 /* The first following string must be braced. */
3163
3164 if (*s++ != '{') goto FAILED_CURLY;
3165
3166 /* Expand the first substring. Forced failures are noticed only if we actually
3167 want this string. Set skipping in the call in the fail case (this will always
3168 be the case if we were already skipping). */
3169
3170 sub1 = expand_string_internal(s, TRUE, &s, !yes, TRUE, resetok);
3171 if (sub1 == NULL && (yes || !expand_string_forcedfail)) goto FAILED;
3172 expand_string_forcedfail = FALSE;
3173 if (*s++ != '}') goto FAILED_CURLY;
3174
3175 /* If we want the first string, add it to the output */
3176
3177 if (yes)
3178 *yieldptr = string_cat(*yieldptr, sizeptr, ptrptr, sub1, Ustrlen(sub1));
3179
3180 /* If this is called from a lookup or an extract, we want to restore $value to
3181 what it was at the start of the item, so that it has this value during the
3182 second string expansion. For the call from "if" or "run" to this function,
3183 save_lookup is set to lookup_value, so that this statement does nothing. */
3184
3185 lookup_value = save_lookup;
3186
3187 /* There now follows either another substring, or "fail", or nothing. This
3188 time, forced failures are noticed only if we want the second string. We must
3189 set skipping in the nested call if we don't want this string, or if we were
3190 already skipping. */
3191
3192 while (isspace(*s)) s++;
3193 if (*s == '{')
3194 {
3195 sub2 = expand_string_internal(s+1, TRUE, &s, yes || skipping, TRUE, resetok);
3196 if (sub2 == NULL && (!yes || !expand_string_forcedfail)) goto FAILED;
3197 expand_string_forcedfail = FALSE;
3198 if (*s++ != '}') goto FAILED_CURLY;
3199
3200 /* If we want the second string, add it to the output */
3201
3202 if (!yes)
3203 *yieldptr = string_cat(*yieldptr, sizeptr, ptrptr, sub2, Ustrlen(sub2));
3204 }
3205
3206 /* If there is no second string, but the word "fail" is present when the use of
3207 the second string is wanted, set a flag indicating it was a forced failure
3208 rather than a syntactic error. Swallow the terminating } in case this is nested
3209 inside another lookup or if or extract. */
3210
3211 else if (*s != '}')
3212 {
3213 uschar name[256];
3214 /* deconst cast ok here as source is s anyway */
3215 s = US read_name(name, sizeof(name), s, US"_");
3216 if (Ustrcmp(name, "fail") == 0)
3217 {
3218 if (!yes && !skipping)
3219 {
3220 while (isspace(*s)) s++;
3221 if (*s++ != '}') goto FAILED_CURLY;
3222 expand_string_message =
3223 string_sprintf("\"%s\" failed and \"fail\" requested", type);
3224 expand_string_forcedfail = TRUE;
3225 goto FAILED;
3226 }
3227 }
3228 else
3229 {
3230 expand_string_message =
3231 string_sprintf("syntax error in \"%s\" item - \"fail\" expected", type);
3232 goto FAILED;
3233 }
3234 }
3235
3236 /* All we have to do now is to check on the final closing brace. */
3237
3238 while (isspace(*s)) s++;
3239 if (*s++ == '}') goto RETURN;
3240
3241 /* Get here if there is a bracketing failure */
3242
3243 FAILED_CURLY:
3244 rc++;
3245
3246 /* Get here for other failures */
3247
3248 FAILED:
3249 rc++;
3250
3251 /* Update the input pointer value before returning */
3252
3253 RETURN:
3254 *sptr = s;
3255 return rc;
3256 }
3257
3258
3259
3260
3261 /*************************************************
3262 * Handle MD5 or SHA-1 computation for HMAC *
3263 *************************************************/
3264
3265 /* These are some wrapping functions that enable the HMAC code to be a bit
3266 cleaner. A good compiler will spot the tail recursion.
3267
3268 Arguments:
3269 type HMAC_MD5 or HMAC_SHA1
3270 remaining are as for the cryptographic hash functions
3271
3272 Returns: nothing
3273 */
3274
3275 static void
3276 chash_start(int type, void *base)
3277 {
3278 if (type == HMAC_MD5)
3279 md5_start((md5 *)base);
3280 else
3281 sha1_start((sha1 *)base);
3282 }
3283
3284 static void
3285 chash_mid(int type, void *base, uschar *string)
3286 {
3287 if (type == HMAC_MD5)
3288 md5_mid((md5 *)base, string);
3289 else
3290 sha1_mid((sha1 *)base, string);
3291 }
3292
3293 static void
3294 chash_end(int type, void *base, uschar *string, int length, uschar *digest)
3295 {
3296 if (type == HMAC_MD5)
3297 md5_end((md5 *)base, string, length, digest);
3298 else
3299 sha1_end((sha1 *)base, string, length, digest);
3300 }
3301
3302
3303
3304
3305
3306 /********************************************************
3307 * prvs: Get last three digits of days since Jan 1, 1970 *
3308 ********************************************************/
3309
3310 /* This is needed to implement the "prvs" BATV reverse
3311 path signing scheme
3312
3313 Argument: integer "days" offset to add or substract to
3314 or from the current number of days.
3315
3316 Returns: pointer to string containing the last three
3317 digits of the number of days since Jan 1, 1970,
3318 modified by the offset argument, NULL if there
3319 was an error in the conversion.
3320
3321 */
3322
3323 static uschar *
3324 prvs_daystamp(int day_offset)
3325 {
3326 uschar *days = store_get(32); /* Need at least 24 for cases */
3327 (void)string_format(days, 32, TIME_T_FMT, /* where TIME_T_FMT is %lld */
3328 (time(NULL) + day_offset*86400)/86400);
3329 return (Ustrlen(days) >= 3) ? &days[Ustrlen(days)-3] : US"100";
3330 }
3331
3332
3333
3334 /********************************************************
3335 * prvs: perform HMAC-SHA1 computation of prvs bits *
3336 ********************************************************/
3337
3338 /* This is needed to implement the "prvs" BATV reverse
3339 path signing scheme
3340
3341 Arguments:
3342 address RFC2821 Address to use
3343 key The key to use (must be less than 64 characters
3344 in size)
3345 key_num Single-digit key number to use. Defaults to
3346 '0' when NULL.
3347
3348 Returns: pointer to string containing the first three
3349 bytes of the final hash in hex format, NULL if
3350 there was an error in the process.
3351 */
3352
3353 static uschar *
3354 prvs_hmac_sha1(uschar *address, uschar *key, uschar *key_num, uschar *daystamp)
3355 {
3356 uschar *hash_source, *p;
3357 int size = 0,offset = 0,i;
3358 sha1 sha1_base;
3359 void *use_base = &sha1_base;
3360 uschar innerhash[20];
3361 uschar finalhash[20];
3362 uschar innerkey[64];
3363 uschar outerkey[64];
3364 uschar *finalhash_hex = store_get(40);
3365
3366 if (key_num == NULL)
3367 key_num = US"0";
3368
3369 if (Ustrlen(key) > 64)
3370 return NULL;
3371
3372 hash_source = string_cat(NULL,&size,&offset,key_num,1);
3373 string_cat(hash_source,&size,&offset,daystamp,3);
3374 string_cat(hash_source,&size,&offset,address,Ustrlen(address));
3375 hash_source[offset] = '\0';
3376
3377 DEBUG(D_expand) debug_printf("prvs: hash source is '%s'\n", hash_source);
3378
3379 memset(innerkey, 0x36, 64);
3380 memset(outerkey, 0x5c, 64);
3381
3382 for (i = 0; i < Ustrlen(key); i++)
3383 {
3384 innerkey[i] ^= key[i];
3385 outerkey[i] ^= key[i];
3386 }
3387
3388 chash_start(HMAC_SHA1, use_base);
3389 chash_mid(HMAC_SHA1, use_base, innerkey);
3390 chash_end(HMAC_SHA1, use_base, hash_source, offset, innerhash);
3391
3392 chash_start(HMAC_SHA1, use_base);
3393 chash_mid(HMAC_SHA1, use_base, outerkey);
3394 chash_end(HMAC_SHA1, use_base, innerhash, 20, finalhash);
3395
3396 p = finalhash_hex;
3397 for (i = 0; i < 3; i++)
3398 {
3399 *p++ = hex_digits[(finalhash[i] & 0xf0) >> 4];
3400 *p++ = hex_digits[finalhash[i] & 0x0f];
3401 }
3402 *p = '\0';
3403
3404 return finalhash_hex;
3405 }
3406
3407
3408
3409
3410 /*************************************************
3411 * Join a file onto the output string *
3412 *************************************************/
3413
3414 /* This is used for readfile and after a run expansion. It joins the contents
3415 of a file onto the output string, globally replacing newlines with a given
3416 string (optionally). The file is closed at the end.
3417
3418 Arguments:
3419 f the FILE
3420 yield pointer to the expandable string
3421 sizep pointer to the current size
3422 ptrp pointer to the current position
3423 eol newline replacement string, or NULL
3424
3425 Returns: new value of string pointer
3426 */
3427
3428 static uschar *
3429 cat_file(FILE *f, uschar *yield, int *sizep, int *ptrp, uschar *eol)
3430 {
3431 int eollen;
3432 uschar buffer[1024];
3433
3434 eollen = (eol == NULL)? 0 : Ustrlen(eol);
3435
3436 while (Ufgets(buffer, sizeof(buffer), f) != NULL)
3437 {
3438 int len = Ustrlen(buffer);
3439 if (eol != NULL && buffer[len-1] == '\n') len--;
3440 yield = string_cat(yield, sizep, ptrp, buffer, len);
3441 if (buffer[len] != 0)
3442 yield = string_cat(yield, sizep, ptrp, eol, eollen);
3443 }
3444
3445 if (yield != NULL) yield[*ptrp] = 0;
3446
3447 return yield;
3448 }
3449
3450
3451
3452
3453 /*************************************************
3454 * Evaluate numeric expression *
3455 *************************************************/
3456
3457 /* This is a set of mutually recursive functions that evaluate an arithmetic
3458 expression involving + - * / % & | ^ ~ << >> and parentheses. The only one of
3459 these functions that is called from elsewhere is eval_expr, whose interface is:
3460
3461 Arguments:
3462 sptr pointer to the pointer to the string - gets updated
3463 decimal TRUE if numbers are to be assumed decimal
3464 error pointer to where to put an error message - must be NULL on input
3465 endket TRUE if ')' must terminate - FALSE for external call
3466
3467 Returns: on success: the value of the expression, with *error still NULL
3468 on failure: an undefined value, with *error = a message
3469 */
3470
3471 static int_eximarith_t eval_op_or(uschar **, BOOL, uschar **);
3472
3473
3474 static int_eximarith_t
3475 eval_expr(uschar **sptr, BOOL decimal, uschar **error, BOOL endket)
3476 {
3477 uschar *s = *sptr;
3478 int_eximarith_t x = eval_op_or(&s, decimal, error);
3479 if (*error == NULL)
3480 {
3481 if (endket)
3482 {
3483 if (*s != ')')
3484 *error = US"expecting closing parenthesis";
3485 else
3486 while (isspace(*(++s)));
3487 }
3488 else if (*s != 0) *error = US"expecting operator";
3489 }
3490 *sptr = s;
3491 return x;
3492 }
3493
3494
3495 static int_eximarith_t
3496 eval_number(uschar **sptr, BOOL decimal, uschar **error)
3497 {
3498 register int c;
3499 int_eximarith_t n;
3500 uschar *s = *sptr;
3501 while (isspace(*s)) s++;
3502 c = *s;
3503 if (isdigit(c))
3504 {
3505 int count;
3506 (void)sscanf(CS s, (decimal? SC_EXIM_DEC "%n" : SC_EXIM_ARITH "%n"), &n, &count);
3507 s += count;
3508 switch (tolower(*s))
3509 {
3510 default: break;
3511 case 'k': n *= 1024; s++; break;
3512 case 'm': n *= 1024*1024; s++; break;
3513 case 'g': n *= 1024*1024*1024; s++; break;
3514 }
3515 while (isspace (*s)) s++;
3516 }
3517 else if (c == '(')
3518 {
3519 s++;
3520 n = eval_expr(&s, decimal, error, 1);
3521 }
3522 else
3523 {
3524 *error = US"expecting number or opening parenthesis";
3525 n = 0;
3526 }
3527 *sptr = s;
3528 return n;
3529 }
3530
3531
3532 static int_eximarith_t
3533 eval_op_unary(uschar **sptr, BOOL decimal, uschar **error)
3534 {
3535 uschar *s = *sptr;
3536 int_eximarith_t x;
3537 while (isspace(*s)) s++;
3538 if (*s == '+' || *s == '-' || *s == '~')
3539 {
3540 int op = *s++;
3541 x = eval_op_unary(&s, decimal, error);
3542 if (op == '-') x = -x;
3543 else if (op == '~') x = ~x;
3544 }
3545 else
3546 {
3547 x = eval_number(&s, decimal, error);
3548 }
3549 *sptr = s;
3550 return x;
3551 }
3552
3553
3554 static int_eximarith_t
3555 eval_op_mult(uschar **sptr, BOOL decimal, uschar **error)
3556 {
3557 uschar *s = *sptr;
3558 int_eximarith_t x = eval_op_unary(&s, decimal, error);
3559 if (*error == NULL)
3560 {
3561 while (*s == '*' || *s == '/' || *s == '%')
3562 {
3563 int op = *s++;
3564 int_eximarith_t y = eval_op_unary(&s, decimal, error);
3565 if (*error != NULL) break;
3566 /* SIGFPE both on div/mod by zero and on INT_MIN / -1, which would give
3567 * a value of INT_MAX+1. Note that INT_MIN * -1 gives INT_MIN for me, which
3568 * is a bug somewhere in [gcc 4.2.1, FreeBSD, amd64]. In fact, -N*-M where
3569 * -N*M is INT_MIN will yielf INT_MIN.
3570 * Since we don't support floating point, this is somewhat simpler.
3571 * Ideally, we'd return an error, but since we overflow for all other
3572 * arithmetic, consistency suggests otherwise, but what's the correct value
3573 * to use? There is none.
3574 * The C standard guarantees overflow for unsigned arithmetic but signed
3575 * overflow invokes undefined behaviour; in practice, this is overflow
3576 * except for converting INT_MIN to INT_MAX+1. We also can't guarantee
3577 * that long/longlong larger than int are available, or we could just work
3578 * with larger types. We should consider whether to guarantee 32bit eval
3579 * and 64-bit working variables, with errors returned. For now ...
3580 * So, the only SIGFPEs occur with a non-shrinking div/mod, thus -1; we
3581 * can just let the other invalid results occur otherwise, as they have
3582 * until now. For this one case, we can coerce.
3583 */
3584 if (y == -1 && x == EXIM_ARITH_MIN && op != '*')
3585 {
3586 DEBUG(D_expand)
3587 debug_printf("Integer exception dodging: " PR_EXIM_ARITH "%c-1 coerced to " PR_EXIM_ARITH "\n",
3588 EXIM_ARITH_MIN, op, EXIM_ARITH_MAX);
3589 x = EXIM_ARITH_MAX;
3590 continue;
3591 }
3592 if (op == '*')
3593 x *= y;
3594 else
3595 {
3596 if (y == 0)
3597 {
3598 *error = (op == '/') ? US"divide by zero" : US"modulo by zero";
3599 x = 0;
3600 break;
3601 }
3602 if (op == '/')
3603 x /= y;
3604 else
3605 x %= y;
3606 }
3607 }
3608 }
3609 *sptr = s;
3610 return x;
3611 }
3612
3613
3614 static int_eximarith_t
3615 eval_op_sum(uschar **sptr, BOOL decimal, uschar **error)
3616 {
3617 uschar *s = *sptr;
3618 int_eximarith_t x = eval_op_mult(&s, decimal, error);
3619 if (*error == NULL)
3620 {
3621 while (*s == '+' || *s == '-')
3622 {
3623 int op = *s++;
3624 int_eximarith_t y = eval_op_mult(&s, decimal, error);
3625 if (*error != NULL) break;
3626 if (op == '+') x += y; else x -= y;
3627 }
3628 }
3629 *sptr = s;
3630 return x;
3631 }
3632
3633
3634 static int_eximarith_t
3635 eval_op_shift(uschar **sptr, BOOL decimal, uschar **error)
3636 {
3637 uschar *s = *sptr;
3638 int_eximarith_t x = eval_op_sum(&s, decimal, error);
3639 if (*error == NULL)
3640 {
3641 while ((*s == '<' || *s == '>') && s[1] == s[0])
3642 {
3643 int_eximarith_t y;
3644 int op = *s++;
3645 s++;
3646 y = eval_op_sum(&s, decimal, error);
3647 if (*error != NULL) break;
3648 if (op == '<') x <<= y; else x >>= y;
3649 }
3650 }
3651 *sptr = s;
3652 return x;
3653 }
3654
3655
3656 static int_eximarith_t
3657 eval_op_and(uschar **sptr, BOOL decimal, uschar **error)
3658 {
3659 uschar *s = *sptr;
3660 int_eximarith_t x = eval_op_shift(&s, decimal, error);
3661 if (*error == NULL)
3662 {
3663 while (*s == '&')
3664 {
3665 int_eximarith_t y;
3666 s++;
3667 y = eval_op_shift(&s, decimal, error);
3668 if (*error != NULL) break;
3669 x &= y;
3670 }
3671 }
3672 *sptr = s;
3673 return x;
3674 }
3675
3676
3677 static int_eximarith_t
3678 eval_op_xor(uschar **sptr, BOOL decimal, uschar **error)
3679 {
3680 uschar *s = *sptr;
3681 int_eximarith_t x = eval_op_and(&s, decimal, error);
3682 if (*error == NULL)
3683 {
3684 while (*s == '^')
3685 {
3686 int_eximarith_t y;
3687 s++;
3688 y = eval_op_and(&s, decimal, error);
3689 if (*error != NULL) break;
3690 x ^= y;
3691 }
3692 }
3693 *sptr = s;
3694 return x;
3695 }
3696
3697
3698 static int_eximarith_t
3699 eval_op_or(uschar **sptr, BOOL decimal, uschar **error)
3700 {
3701 uschar *s = *sptr;
3702 int_eximarith_t x = eval_op_xor(&s, decimal, error);
3703 if (*error == NULL)
3704 {
3705 while (*s == '|')
3706 {
3707 int_eximarith_t y;
3708 s++;
3709 y = eval_op_xor(&s, decimal, error);
3710 if (*error != NULL) break;
3711 x |= y;
3712 }
3713 }
3714 *sptr = s;
3715 return x;
3716 }
3717
3718
3719
3720 /*************************************************
3721 * Expand string *
3722 *************************************************/
3723
3724 /* Returns either an unchanged string, or the expanded string in stacking pool
3725 store. Interpreted sequences are:
3726
3727 \... normal escaping rules
3728 $name substitutes the variable
3729 ${name} ditto
3730 ${op:string} operates on the expanded string value
3731 ${item{arg1}{arg2}...} expands the args and then does the business
3732 some literal args are not enclosed in {}
3733
3734 There are now far too many operators and item types to make it worth listing
3735 them here in detail any more.
3736
3737 We use an internal routine recursively to handle embedded substrings. The
3738 external function follows. The yield is NULL if the expansion failed, and there
3739 are two cases: if something collapsed syntactically, or if "fail" was given
3740 as the action on a lookup failure. These can be distinguised by looking at the
3741 variable expand_string_forcedfail, which is TRUE in the latter case.
3742
3743 The skipping flag is set true when expanding a substring that isn't actually
3744 going to be used (after "if" or "lookup") and it prevents lookups from
3745 happening lower down.
3746
3747 Store usage: At start, a store block of the length of the input plus 64
3748 is obtained. This is expanded as necessary by string_cat(), which might have to
3749 get a new block, or might be able to expand the original. At the end of the
3750 function we can release any store above that portion of the yield block that
3751 was actually used. In many cases this will be optimal.
3752
3753 However: if the first item in the expansion is a variable name or header name,
3754 we reset the store before processing it; if the result is in fresh store, we
3755 use that without copying. This is helpful for expanding strings like
3756 $message_headers which can get very long.
3757
3758 There's a problem if a ${dlfunc item has side-effects that cause allocation,
3759 since resetting the store at the end of the expansion will free store that was
3760 allocated by the plugin code as well as the slop after the expanded string. So
3761 we skip any resets if ${dlfunc } has been used. The same applies for ${acl }
3762 and, given the acl condition, ${if }. This is an unfortunate consequence of
3763 string expansion becoming too powerful.
3764
3765 Arguments:
3766 string the string to be expanded
3767 ket_ends true if expansion is to stop at }
3768 left if not NULL, a pointer to the first character after the
3769 expansion is placed here (typically used with ket_ends)
3770 skipping TRUE for recursive calls when the value isn't actually going
3771 to be used (to allow for optimisation)
3772 honour_dollar TRUE if $ is to be expanded,
3773 FALSE if it's just another character
3774 resetok_p if not NULL, pointer to flag - write FALSE if unsafe to reset
3775 the store.
3776
3777 Returns: NULL if expansion fails:
3778 expand_string_forcedfail is set TRUE if failure was forced
3779 expand_string_message contains a textual error message
3780 a pointer to the expanded string on success
3781 */
3782
3783 static uschar *
3784 expand_string_internal(const uschar *string, BOOL ket_ends, const uschar **left,
3785 BOOL skipping, BOOL honour_dollar, BOOL *resetok_p)
3786 {
3787 int ptr = 0;
3788 int size = Ustrlen(string)+ 64;
3789 int item_type;
3790 uschar *yield = store_get(size);
3791 const uschar *s = string;
3792 uschar *save_expand_nstring[EXPAND_MAXN+1];
3793 int save_expand_nlength[EXPAND_MAXN+1];
3794 BOOL resetok = TRUE;
3795
3796 expand_string_forcedfail = FALSE;
3797 expand_string_message = US"";
3798
3799 while (*s != 0)
3800 {
3801 uschar *value;
3802 uschar name[256];
3803
3804 /* \ escapes the next character, which must exist, or else
3805 the expansion fails. There's a special escape, \N, which causes
3806 copying of the subject verbatim up to the next \N. Otherwise,
3807 the escapes are the standard set. */
3808
3809 if (*s == '\\')
3810 {
3811 if (s[1] == 0)
3812 {
3813 expand_string_message = US"\\ at end of string";
3814 goto EXPAND_FAILED;
3815 }
3816
3817 if (s[1] == 'N')
3818 {
3819 const uschar * t = s + 2;
3820 for (s = t; *s != 0; s++) if (*s == '\\' && s[1] == 'N') break;
3821 yield = string_cat(yield, &size, &ptr, t, s - t);
3822 if (*s != 0) s += 2;
3823 }
3824
3825 else
3826 {
3827 uschar ch[1];
3828 ch[0] = string_interpret_escape(&s);
3829 s++;
3830 yield = string_cat(yield, &size, &ptr, ch, 1);
3831 }
3832
3833 continue;
3834 }
3835
3836 /*{*/
3837 /* Anything other than $ is just copied verbatim, unless we are
3838 looking for a terminating } character. */
3839
3840 /*{*/
3841 if (ket_ends && *s == '}') break;
3842
3843 if (*s != '$' || !honour_dollar)
3844 {
3845 yield = string_cat(yield, &size, &ptr, s++, 1);
3846 continue;
3847 }
3848
3849 /* No { after the $ - must be a plain name or a number for string
3850 match variable. There has to be a fudge for variables that are the
3851 names of header fields preceded by "$header_" because header field
3852 names can contain any printing characters except space and colon.
3853 For those that don't like typing this much, "$h_" is a synonym for
3854 "$header_". A non-existent header yields a NULL value; nothing is
3855 inserted. */ /*}*/
3856
3857 if (isalpha((*(++s))))
3858 {
3859 int len;
3860 int newsize = 0;
3861
3862 s = read_name(name, sizeof(name), s, US"_");
3863
3864 /* If this is the first thing to be expanded, release the pre-allocated
3865 buffer. */
3866
3867 if (ptr == 0 && yield != NULL)
3868 {
3869 if (resetok) store_reset(yield);
3870 yield = NULL;
3871 size = 0;
3872 }
3873
3874 /* Header */
3875
3876 if (Ustrncmp(name, "h_", 2) == 0 ||
3877 Ustrncmp(name, "rh_", 3) == 0 ||
3878 Ustrncmp(name, "bh_", 3) == 0 ||
3879 Ustrncmp(name, "header_", 7) == 0 ||
3880 Ustrncmp(name, "rheader_", 8) == 0 ||
3881 Ustrncmp(name, "bheader_", 8) == 0)
3882 {
3883 BOOL want_raw = (name[0] == 'r')? TRUE : FALSE;
3884 uschar *charset = (name[0] == 'b')? NULL : headers_charset;
3885 s = read_header_name(name, sizeof(name), s);
3886 value = find_header(name, FALSE, &newsize, want_raw, charset);
3887
3888 /* If we didn't find the header, and the header contains a closing brace
3889 character, this may be a user error where the terminating colon
3890 has been omitted. Set a flag to adjust the error message in this case.
3891 But there is no error here - nothing gets inserted. */
3892
3893 if (value == NULL)
3894 {
3895 if (Ustrchr(name, '}') != NULL) malformed_header = TRUE;
3896 continue;
3897 }
3898 }
3899
3900 /* Variable */
3901
3902 else
3903 {
3904 value = find_variable(name, FALSE, skipping, &newsize);
3905 if (value == NULL)
3906 {
3907 expand_string_message =
3908 string_sprintf("unknown variable name \"%s\"", name);
3909 check_variable_error_message(name);
3910 goto EXPAND_FAILED;
3911 }
3912 }
3913
3914 /* If the data is known to be in a new buffer, newsize will be set to the
3915 size of that buffer. If this is the first thing in an expansion string,
3916 yield will be NULL; just point it at the new store instead of copying. Many
3917 expansion strings contain just one reference, so this is a useful
3918 optimization, especially for humungous headers. */
3919
3920 len = Ustrlen(value);
3921 if (yield == NULL && newsize != 0)
3922 {
3923 yield = value;
3924 size = newsize;
3925 ptr = len;
3926 }
3927 else yield = string_cat(yield, &size, &ptr, value, len);
3928
3929 continue;
3930 }
3931
3932 if (isdigit(*s))
3933 {
3934 int n;
3935 s = read_cnumber(&n, s);
3936 if (n >= 0 && n <= expand_nmax)
3937 yield = string_cat(yield, &size, &ptr, expand_nstring[n],
3938 expand_nlength[n]);
3939 continue;
3940 }
3941
3942 /* Otherwise, if there's no '{' after $ it's an error. */ /*}*/