1 /* $NetBSD: postscreen.h,v 1.4 2022/10/08 16:12:48 christos Exp $ */ 2 3 /*++ 4 /* NAME 5 /* postscreen 3h 6 /* SUMMARY 7 /* postscreen internal interfaces 8 /* SYNOPSIS 9 /* #include <postscreen.h> 10 /* DESCRIPTION 11 /* .nf 12 13 /* 14 * System library. 15 */ 16 17 /* 18 * Utility library. 19 */ 20 #include <dict_cache.h> 21 #include <vstream.h> 22 #include <vstring.h> 23 #include <events.h> 24 #include <htable.h> 25 #include <myaddrinfo.h> 26 27 /* 28 * Global library. 29 */ 30 #include <addr_match_list.h> 31 #include <string_list.h> 32 #include <maps.h> 33 #include <server_acl.h> 34 35 /* 36 * Preliminary stuff, to be fixed. 37 */ 38 #define PSC_READ_BUF_SIZE 1024 39 40 /* 41 * Numeric indices and symbolic names for tests whose time stamps and status 42 * flags can be accessed by numeric index. 43 */ 44 #define PSC_TINDX_PREGR 0 /* pregreet */ 45 #define PSC_TINDX_DNSBL 1 /* dnsbl */ 46 #define PSC_TINDX_PIPEL 2 /* pipelining */ 47 #define PSC_TINDX_NSMTP 3 /* non-smtp command */ 48 #define PSC_TINDX_BARLF 4 /* bare newline */ 49 #define PSC_TINDX_COUNT 5 /* number of tests */ 50 51 #define PSC_TNAME_PREGR "pregreet" 52 #define PSC_TNAME_DNSBL "dnsbl" 53 #define PSC_TNAME_PIPEL "pipelining" 54 #define PSC_TNAME_NSMTP "non-smtp command" 55 #define PSC_TNAME_BARLF "bare newline" 56 57 #define PSC_TINDX_BYTNAME(tname) (PSC_TINDX_ ## tname) 58 59 /* 60 * Per-client shared state. 61 */ 62 typedef struct { 63 int concurrency; /* per-client */ 64 int pass_new_count; /* per-client */ 65 time_t expire_time[PSC_TINDX_COUNT]; /* per-test expiration */ 66 } PSC_CLIENT_INFO; 67 68 /* 69 * Per-session state. 70 */ 71 typedef struct { 72 int flags; /* see below */ 73 /* Socket state. */ 74 VSTREAM *smtp_client_stream; /* remote SMTP client */ 75 int smtp_server_fd; /* real SMTP server */ 76 char *smtp_client_addr; /* client address */ 77 char *smtp_client_port; /* client port */ 78 char *smtp_server_addr; /* server address */ 79 char *smtp_server_port; /* server port */ 80 const char *final_reply; /* cause for hanging up */ 81 VSTRING *send_buf; /* pending output */ 82 /* Test context. */ 83 struct timeval start_time; /* start of current test */ 84 const char *test_name; /* name of current test */ 85 PSC_CLIENT_INFO *client_info; /* shared client state */ 86 VSTRING *dnsbl_reply; /* dnsbl reject text */ 87 int dnsbl_score; /* saved DNSBL score */ 88 int dnsbl_ttl; /* saved DNSBL TTL */ 89 const char *dnsbl_name; /* DNSBL name with largest weight */ 90 int dnsbl_index; /* dnsbl request index */ 91 const char *rcpt_reply; /* how to reject recipients */ 92 int command_count; /* error + junk command count */ 93 const char *protocol; /* SMTP or ESMTP */ 94 char *helo_name; /* SMTP helo/ehlo */ 95 char *sender; /* MAIL FROM */ 96 VSTRING *cmd_buffer; /* command read buffer */ 97 int read_state; /* command read state machine */ 98 /* smtpd(8) compatibility */ 99 int ehlo_discard_mask; /* EHLO filter */ 100 VSTRING *expand_buf; /* macro expansion */ 101 const char *where; /* SMTP protocol state */ 102 } PSC_STATE; 103 104 /* 105 * Special expiration time values. 106 */ 107 #define PSC_TIME_STAMP_NEW (0) /* test was never passed */ 108 #define PSC_TIME_STAMP_DISABLED (1) /* never passed but disabled */ 109 #define PSC_TIME_STAMP_INVALID (-1) /* must not be cached */ 110 111 /* 112 * Status flags. 113 */ 114 #define PSC_STATE_FLAG_NOFORWARD (1<<0) /* don't forward this session */ 115 #define PSC_STATE_FLAG_USING_TLS (1<<1) /* using the TLS proxy */ 116 #define PSC_STATE_FLAG_UNUSED2 (1<<2) /* use me! */ 117 #define PSC_STATE_FLAG_NEW (1<<3) /* some test was never passed */ 118 #define PSC_STATE_FLAG_DNLIST_FAIL (1<<4) /* denylisted */ 119 #define PSC_STATE_FLAG_HANGUP (1<<5) /* NOT a test failure */ 120 #define PSC_STATE_FLAG_SMTPD_X21 (1<<6) /* hang up after command */ 121 #define PSC_STATE_FLAG_ALLIST_FAIL (1<<7) /* do not allowlist */ 122 #define PSC_STATE_FLAG_TEST_BASE (8) /* start of indexable flags */ 123 124 /* 125 * Tests whose flags and expiration time can be accessed by numerical index. 126 * 127 * Important: every MUMBLE_TODO flag must have a MUMBLE_PASS flag, such that 128 * MUMBLE_PASS == PSC_STATE_FLAGS_TODO_TO_PASS(MUMBLE_TODO). 129 * 130 * MUMBLE_TODO flags must not be cleared once raised. The _TODO_TO_PASS and 131 * _TODO_TO_DONE macros depend on this to decide that a group of tests is 132 * passed or completed. 133 * 134 * MUMBLE_DONE flags are used for "early" tests that have final results. 135 * 136 * MUMBLE_SKIP flags are used for "deep" tests where the client messed up. 137 * These flags look like MUMBLE_DONE but they are different. Deep tests can 138 * tentatively pass, but can still fail later in a session. The "ignore" 139 * action introduces an additional complication. MUMBLE_PASS indicates 140 * either that a deep test passed tentatively, or that the test failed but 141 * the result was ignored. MUMBLE_FAIL, on the other hand, is always final. 142 * We use MUMBLE_SKIP to indicate that a decision was either "fail" or 143 * forced "pass". 144 * 145 * The difference between DONE and SKIP is in the beholder's eye. These flags 146 * share the same bit. 147 */ 148 #define PSC_STATE_FLAGS_TODO_TO_PASS(todo_flags) ((todo_flags) >> 1) 149 #define PSC_STATE_FLAGS_TODO_TO_DONE(todo_flags) ((todo_flags) << 1) 150 151 #define PSC_STATE_FLAG_SHIFT_FAIL (0) /* failed test */ 152 #define PSC_STATE_FLAG_SHIFT_PASS (1) /* passed test */ 153 #define PSC_STATE_FLAG_SHIFT_TODO (2) /* expired test */ 154 #define PSC_STATE_FLAG_SHIFT_DONE (3) /* decision is final */ 155 #define PSC_STATE_FLAG_SHIFT_SKIP (3) /* action is already logged */ 156 #define PSC_STATE_FLAG_SHIFT_STRIDE (4) /* nr of flags per test */ 157 158 #define PSC_STATE_FLAG_SHIFT_BYFNAME(fname) (PSC_STATE_FLAG_SHIFT_ ## fname) 159 160 /* 161 * Indexable per-test flags. These are used for DNS allowlisting multiple 162 * tests, without needing per-test ad-hoc code. 163 */ 164 #define PSC_STATE_FLAG_BYTINDX_FNAME(tindx, fname) \ 165 (1U << (PSC_STATE_FLAG_TEST_BASE \ 166 + PSC_STATE_FLAG_SHIFT_STRIDE * (tindx) \ 167 + PSC_STATE_FLAG_SHIFT_BYFNAME(fname))) 168 169 #define PSC_STATE_FLAG_BYTINDX_FAIL(tindx) \ 170 PSC_STATE_FLAG_BYTINDX_FNAME((tindx), FAIL) 171 #define PSC_STATE_FLAG_BYTINDX_PASS(tindx) \ 172 PSC_STATE_FLAG_BYTINDX_FNAME((tindx), PASS) 173 #define PSC_STATE_FLAG_BYTINDX_TODO(tindx) \ 174 PSC_STATE_FLAG_BYTINDX_FNAME((tindx), TODO) 175 #define PSC_STATE_FLAG_BYTINDX_DONE(tindx) \ 176 PSC_STATE_FLAG_BYTINDX_FNAME((tindx), DONE) 177 #define PSC_STATE_FLAG_BYTINDX_SKIP(tindx) \ 178 PSC_STATE_FLAG_BYTINDX_FNAME((tindx), SKIP) 179 180 /* 181 * Flags with distinct names. These are used in the per-test ad-hoc code. 182 */ 183 #define PSC_STATE_FLAG_BYTNAME_FNAME(tname, fname) \ 184 (1U << (PSC_STATE_FLAG_TEST_BASE \ 185 + PSC_STATE_FLAG_SHIFT_STRIDE * PSC_TINDX_BYTNAME(tname) \ 186 + PSC_STATE_FLAG_SHIFT_BYFNAME(fname))) 187 188 #define PSC_STATE_FLAG_PREGR_FAIL PSC_STATE_FLAG_BYTNAME_FNAME(PREGR, FAIL) 189 #define PSC_STATE_FLAG_PREGR_PASS PSC_STATE_FLAG_BYTNAME_FNAME(PREGR, PASS) 190 #define PSC_STATE_FLAG_PREGR_TODO PSC_STATE_FLAG_BYTNAME_FNAME(PREGR, TODO) 191 #define PSC_STATE_FLAG_PREGR_DONE PSC_STATE_FLAG_BYTNAME_FNAME(PREGR, DONE) 192 193 #define PSC_STATE_FLAG_DNSBL_FAIL PSC_STATE_FLAG_BYTNAME_FNAME(DNSBL, FAIL) 194 #define PSC_STATE_FLAG_DNSBL_PASS PSC_STATE_FLAG_BYTNAME_FNAME(DNSBL, PASS) 195 #define PSC_STATE_FLAG_DNSBL_TODO PSC_STATE_FLAG_BYTNAME_FNAME(DNSBL, TODO) 196 #define PSC_STATE_FLAG_DNSBL_DONE PSC_STATE_FLAG_BYTNAME_FNAME(DNSBL, DONE) 197 198 #define PSC_STATE_FLAG_PIPEL_FAIL PSC_STATE_FLAG_BYTNAME_FNAME(PIPEL, FAIL) 199 #define PSC_STATE_FLAG_PIPEL_PASS PSC_STATE_FLAG_BYTNAME_FNAME(PIPEL, PASS) 200 #define PSC_STATE_FLAG_PIPEL_TODO PSC_STATE_FLAG_BYTNAME_FNAME(PIPEL, TODO) 201 #define PSC_STATE_FLAG_PIPEL_SKIP PSC_STATE_FLAG_BYTNAME_FNAME(PIPEL, SKIP) 202 203 #define PSC_STATE_FLAG_NSMTP_FAIL PSC_STATE_FLAG_BYTNAME_FNAME(NSMTP, FAIL) 204 #define PSC_STATE_FLAG_NSMTP_PASS PSC_STATE_FLAG_BYTNAME_FNAME(NSMTP, PASS) 205 #define PSC_STATE_FLAG_NSMTP_TODO PSC_STATE_FLAG_BYTNAME_FNAME(NSMTP, TODO) 206 #define PSC_STATE_FLAG_NSMTP_SKIP PSC_STATE_FLAG_BYTNAME_FNAME(NSMTP, SKIP) 207 208 #define PSC_STATE_FLAG_BARLF_FAIL PSC_STATE_FLAG_BYTNAME_FNAME(BARLF, FAIL) 209 #define PSC_STATE_FLAG_BARLF_PASS PSC_STATE_FLAG_BYTNAME_FNAME(BARLF, PASS) 210 #define PSC_STATE_FLAG_BARLF_TODO PSC_STATE_FLAG_BYTNAME_FNAME(BARLF, TODO) 211 #define PSC_STATE_FLAG_BARLF_SKIP PSC_STATE_FLAG_BYTNAME_FNAME(BARLF, SKIP) 212 213 /* 214 * Aggregates for individual tests. 215 */ 216 #define PSC_STATE_MASK_PREGR_TODO_FAIL \ 217 (PSC_STATE_FLAG_PREGR_TODO | PSC_STATE_FLAG_PREGR_FAIL) 218 #define PSC_STATE_MASK_DNSBL_TODO_FAIL \ 219 (PSC_STATE_FLAG_DNSBL_TODO | PSC_STATE_FLAG_DNSBL_FAIL) 220 #define PSC_STATE_MASK_PIPEL_TODO_FAIL \ 221 (PSC_STATE_FLAG_PIPEL_TODO | PSC_STATE_FLAG_PIPEL_FAIL) 222 #define PSC_STATE_MASK_NSMTP_TODO_FAIL \ 223 (PSC_STATE_FLAG_NSMTP_TODO | PSC_STATE_FLAG_NSMTP_FAIL) 224 #define PSC_STATE_MASK_BARLF_TODO_FAIL \ 225 (PSC_STATE_FLAG_BARLF_TODO | PSC_STATE_FLAG_BARLF_FAIL) 226 227 #define PSC_STATE_MASK_PREGR_TODO_DONE \ 228 (PSC_STATE_FLAG_PREGR_TODO | PSC_STATE_FLAG_PREGR_DONE) 229 #define PSC_STATE_MASK_PIPEL_TODO_SKIP \ 230 (PSC_STATE_FLAG_PIPEL_TODO | PSC_STATE_FLAG_PIPEL_SKIP) 231 #define PSC_STATE_MASK_NSMTP_TODO_SKIP \ 232 (PSC_STATE_FLAG_NSMTP_TODO | PSC_STATE_FLAG_NSMTP_SKIP) 233 #define PSC_STATE_MASK_BARLF_TODO_SKIP \ 234 (PSC_STATE_FLAG_BARLF_TODO | PSC_STATE_FLAG_BARLF_SKIP) 235 236 #define PSC_STATE_MASK_PREGR_FAIL_DONE \ 237 (PSC_STATE_FLAG_PREGR_FAIL | PSC_STATE_FLAG_PREGR_DONE) 238 239 #define PSC_STATE_MASK_PIPEL_TODO_PASS_FAIL \ 240 (PSC_STATE_MASK_PIPEL_TODO_FAIL | PSC_STATE_FLAG_PIPEL_PASS) 241 #define PSC_STATE_MASK_NSMTP_TODO_PASS_FAIL \ 242 (PSC_STATE_MASK_NSMTP_TODO_FAIL | PSC_STATE_FLAG_NSMTP_PASS) 243 #define PSC_STATE_MASK_BARLF_TODO_PASS_FAIL \ 244 (PSC_STATE_MASK_BARLF_TODO_FAIL | PSC_STATE_FLAG_BARLF_PASS) 245 246 /* 247 * Separate aggregates for early tests and deep tests. 248 */ 249 #define PSC_STATE_MASK_EARLY_DONE \ 250 (PSC_STATE_FLAG_PREGR_DONE | PSC_STATE_FLAG_DNSBL_DONE) 251 #define PSC_STATE_MASK_EARLY_TODO \ 252 (PSC_STATE_FLAG_PREGR_TODO | PSC_STATE_FLAG_DNSBL_TODO) 253 #define PSC_STATE_MASK_EARLY_PASS \ 254 (PSC_STATE_FLAG_PREGR_PASS | PSC_STATE_FLAG_DNSBL_PASS) 255 #define PSC_STATE_MASK_EARLY_FAIL \ 256 (PSC_STATE_FLAG_PREGR_FAIL | PSC_STATE_FLAG_DNSBL_FAIL) 257 258 #define PSC_STATE_MASK_SMTPD_TODO \ 259 (PSC_STATE_FLAG_PIPEL_TODO | PSC_STATE_FLAG_NSMTP_TODO | \ 260 PSC_STATE_FLAG_BARLF_TODO) 261 #define PSC_STATE_MASK_SMTPD_PASS \ 262 (PSC_STATE_FLAG_PIPEL_PASS | PSC_STATE_FLAG_NSMTP_PASS | \ 263 PSC_STATE_FLAG_BARLF_PASS) 264 #define PSC_STATE_MASK_SMTPD_FAIL \ 265 (PSC_STATE_FLAG_PIPEL_FAIL | PSC_STATE_FLAG_NSMTP_FAIL | \ 266 PSC_STATE_FLAG_BARLF_FAIL) 267 268 /* 269 * Super-aggregates for all tests combined. 270 */ 271 #define PSC_STATE_MASK_ANY_FAIL \ 272 (PSC_STATE_FLAG_DNLIST_FAIL | \ 273 PSC_STATE_MASK_EARLY_FAIL | PSC_STATE_MASK_SMTPD_FAIL | \ 274 PSC_STATE_FLAG_ALLIST_FAIL) 275 276 #define PSC_STATE_MASK_ANY_PASS \ 277 (PSC_STATE_MASK_EARLY_PASS | PSC_STATE_MASK_SMTPD_PASS) 278 279 #define PSC_STATE_MASK_ANY_TODO \ 280 (PSC_STATE_MASK_EARLY_TODO | PSC_STATE_MASK_SMTPD_TODO) 281 282 #define PSC_STATE_MASK_ANY_TODO_FAIL \ 283 (PSC_STATE_MASK_ANY_TODO | PSC_STATE_MASK_ANY_FAIL) 284 285 #define PSC_STATE_MASK_ANY_UPDATE \ 286 (PSC_STATE_MASK_ANY_PASS) 287 288 /* 289 * Meta-commands for state->where that reflect the initial command processor 290 * state and commands that aren't implemented. 291 */ 292 #define PSC_SMTPD_CMD_CONNECT "CONNECT" 293 #define PSC_SMTPD_CMD_UNIMPL "UNIMPLEMENTED" 294 295 /* 296 * See log_adhoc.c for discussion. 297 */ 298 typedef struct { 299 int dt_sec; /* make sure it's signed */ 300 int dt_usec; /* make sure it's signed */ 301 } DELTA_TIME; 302 303 #define PSC_CALC_DELTA(x, y, z) \ 304 do { \ 305 (x).dt_sec = (y).tv_sec - (z).tv_sec; \ 306 (x).dt_usec = (y).tv_usec - (z).tv_usec; \ 307 while ((x).dt_usec < 0) { \ 308 (x).dt_usec += 1000000; \ 309 (x).dt_sec -= 1; \ 310 } \ 311 while ((x).dt_usec >= 1000000) { \ 312 (x).dt_usec -= 1000000; \ 313 (x).dt_sec += 1; \ 314 } \ 315 if ((x).dt_sec < 0) \ 316 (x).dt_sec = (x).dt_usec = 0; \ 317 } while (0) 318 319 #define SIG_DIGS 2 320 321 /* 322 * Event management. 323 */ 324 325 /* PSC_READ_EVENT_REQUEST - prepare for transition to next state */ 326 327 #define PSC_READ_EVENT_REQUEST(fd, action, context, timeout) do { \ 328 if (msg_verbose > 1) \ 329 msg_info("%s: read-request fd=%d", myname, (fd)); \ 330 event_enable_read((fd), (action), (context)); \ 331 event_request_timer((action), (context), (timeout)); \ 332 } while (0) 333 334 #define PSC_READ_EVENT_REQUEST2(fd, read_act, time_act, context, timeout) do { \ 335 if (msg_verbose > 1) \ 336 msg_info("%s: read-request fd=%d", myname, (fd)); \ 337 event_enable_read((fd), (read_act), (context)); \ 338 event_request_timer((time_act), (context), (timeout)); \ 339 } while (0) 340 341 /* PSC_CLEAR_EVENT_REQUEST - complete state transition */ 342 343 #define PSC_CLEAR_EVENT_REQUEST(fd, time_act, context) do { \ 344 if (msg_verbose > 1) \ 345 msg_info("%s: clear-request fd=%d", myname, (fd)); \ 346 event_disable_readwrite(fd); \ 347 event_cancel_timer((time_act), (context)); \ 348 } while (0) 349 350 /* 351 * Failure enforcement policies. 352 */ 353 #define PSC_NAME_ACT_DROP "drop" 354 #define PSC_NAME_ACT_ENFORCE "enforce" 355 #define PSC_NAME_ACT_IGNORE "ignore" 356 #define PSC_NAME_ACT_CONT "continue" 357 358 #define PSC_ACT_DROP 1 359 #define PSC_ACT_ENFORCE 2 360 #define PSC_ACT_IGNORE 3 361 362 /* 363 * Global variables. 364 */ 365 extern int psc_check_queue_length; /* connections being checked */ 366 extern int psc_post_queue_length; /* being sent to real SMTPD */ 367 extern DICT_CACHE *psc_cache_map; /* cache table handle */ 368 extern VSTRING *psc_temp; /* scratchpad */ 369 extern char *psc_smtpd_service_name; /* path to real SMTPD */ 370 extern int psc_pregr_action; /* PSC_ACT_DROP etc. */ 371 extern int psc_dnsbl_action; /* PSC_ACT_DROP etc. */ 372 extern int psc_pipel_action; /* PSC_ACT_DROP etc. */ 373 extern int psc_nsmtp_action; /* PSC_ACT_DROP etc. */ 374 extern int psc_barlf_action; /* PSC_ACT_DROP etc. */ 375 extern int psc_min_ttl; /* Update with new tests! */ 376 extern STRING_LIST *psc_forbid_cmds; /* CONNECT GET POST */ 377 extern int psc_stress_greet_wait; /* stressed greet wait */ 378 extern int psc_normal_greet_wait; /* stressed greet wait */ 379 extern int psc_stress_cmd_time_limit; /* stressed command limit */ 380 extern int psc_normal_cmd_time_limit; /* normal command time limit */ 381 extern int psc_stress; /* stress level */ 382 extern int psc_lowat_check_queue_length;/* stress low-water mark */ 383 extern int psc_hiwat_check_queue_length;/* stress high-water mark */ 384 extern DICT *psc_dnsbl_reply; /* DNSBL name mapper */ 385 extern HTABLE *psc_client_concurrency; /* per-client concurrency */ 386 387 #define PSC_EFF_GREET_WAIT \ 388 (psc_stress ? psc_stress_greet_wait : psc_normal_greet_wait) 389 #define PSC_EFF_CMD_TIME_LIMIT \ 390 (psc_stress ? psc_stress_cmd_time_limit : psc_normal_cmd_time_limit) 391 392 /* 393 * String plumbing macros. 394 */ 395 #define PSC_STRING_UPDATE(str, text) do { \ 396 if (str) myfree(str); \ 397 (str) = ((text) ? mystrdup(text) : 0); \ 398 } while (0) 399 400 #define PSC_STRING_RESET(str) do { \ 401 if (str) { \ 402 myfree(str); \ 403 (str) = 0; \ 404 } \ 405 } while (0) 406 407 /* 408 * SLMs. 409 */ 410 #define STR(x) vstring_str(x) 411 #define LEN(x) VSTRING_LEN(x) 412 413 /* 414 * postscreen_state.c 415 */ 416 #define PSC_CLIENT_ADDR_PORT(state) \ 417 (state)->smtp_client_addr, (state)->smtp_client_port 418 419 #define PSC_PASS_SESSION_STATE(state, what, bits) do { \ 420 if (msg_verbose) \ 421 msg_info("PASS %s [%s]:%s", (what), PSC_CLIENT_ADDR_PORT(state)); \ 422 (state)->flags |= (bits); \ 423 } while (0) 424 #define PSC_FAIL_SESSION_STATE(state, bits) do { \ 425 if (msg_verbose) \ 426 msg_info("FAIL [%s]:%s", PSC_CLIENT_ADDR_PORT(state)); \ 427 (state)->flags |= (bits); \ 428 } while (0) 429 #define PSC_SKIP_SESSION_STATE(state, what, bits) do { \ 430 if (msg_verbose) \ 431 msg_info("SKIP %s [%s]:%s", (what), PSC_CLIENT_ADDR_PORT(state)); \ 432 (state)->flags |= (bits); \ 433 } while (0) 434 #define PSC_DROP_SESSION_STATE(state, reply) do { \ 435 if (msg_verbose) \ 436 msg_info("DROP [%s]:%s", PSC_CLIENT_ADDR_PORT(state)); \ 437 (state)->flags |= PSC_STATE_FLAG_NOFORWARD; \ 438 (state)->final_reply = (reply); \ 439 psc_conclude(state); \ 440 } while (0) 441 #define PSC_ENFORCE_SESSION_STATE(state, reply) do { \ 442 if (msg_verbose) \ 443 msg_info("ENFORCE [%s]:%s", PSC_CLIENT_ADDR_PORT(state)); \ 444 (state)->rcpt_reply = (reply); \ 445 (state)->flags |= PSC_STATE_FLAG_NOFORWARD; \ 446 } while (0) 447 #define PSC_UNPASS_SESSION_STATE(state, bits) do { \ 448 if (msg_verbose) \ 449 msg_info("UNPASS [%s]:%s", PSC_CLIENT_ADDR_PORT(state)); \ 450 (state)->flags &= ~(bits); \ 451 } while (0) 452 #define PSC_UNFAIL_SESSION_STATE(state, bits) do { \ 453 if (msg_verbose) \ 454 msg_info("UNFAIL [%s]:%s", PSC_CLIENT_ADDR_PORT(state)); \ 455 (state)->flags &= ~(bits); \ 456 } while (0) 457 #define PSC_ADD_SERVER_STATE(state, fd) do { \ 458 (state)->smtp_server_fd = (fd); \ 459 psc_post_queue_length++; \ 460 } while (0) 461 #define PSC_DEL_SERVER_STATE(state) do { \ 462 close((state)->smtp_server_fd); \ 463 (state)->smtp_server_fd = (-1); \ 464 psc_post_queue_length--; \ 465 } while (0) 466 #define PSC_DEL_CLIENT_STATE(state) do { \ 467 event_server_disconnect((state)->smtp_client_stream); \ 468 (state)->smtp_client_stream = 0; \ 469 psc_check_queue_length--; \ 470 } while (0) 471 extern PSC_STATE *psc_new_session_state(VSTREAM *, const char *, const char *, const char *, const char *); 472 extern void psc_free_session_state(PSC_STATE *); 473 extern const char *psc_print_state_flags(int, const char *); 474 475 /* 476 * postscreen_dict.c 477 */ 478 extern int psc_addr_match_list_match(ADDR_MATCH_LIST *, const char *); 479 extern const char *psc_cache_lookup(DICT_CACHE *, const char *); 480 extern void psc_cache_update(DICT_CACHE *, const char *, const char *); 481 const char *psc_dict_get(DICT *, const char *); 482 const char *psc_maps_find(MAPS *, const char *, int); 483 484 /* 485 * postscreen_dnsbl.c 486 */ 487 extern void psc_dnsbl_init(void); 488 extern int psc_dnsbl_retrieve(const char *, const char **, int, int *); 489 extern int psc_dnsbl_request(const char *, void (*) (int, void *), void *); 490 491 /* 492 * postscreen_tests.c 493 */ 494 #define PSC_INIT_TESTS(dst) do { \ 495 time_t *_it_stamp_p; \ 496 (dst)->flags = 0; \ 497 for (_it_stamp_p = (dst)->client_info->expire_time; \ 498 _it_stamp_p < (dst)->client_info->expire_time + PSC_TINDX_COUNT; \ 499 _it_stamp_p++) \ 500 *_it_stamp_p = PSC_TIME_STAMP_INVALID; \ 501 } while (0) 502 #define PSC_INIT_TEST_FLAGS_ONLY(dst) do { \ 503 (dst)->flags = 0; \ 504 } while (0) 505 #define PSC_BEGIN_TESTS(state, name) do { \ 506 (state)->test_name = (name); \ 507 GETTIMEOFDAY(&(state)->start_time); \ 508 } while (0) 509 extern void psc_new_tests(PSC_STATE *); 510 extern void psc_parse_tests(PSC_STATE *, const char *, time_t); 511 extern void psc_todo_tests(PSC_STATE *, time_t); 512 extern char *psc_print_tests(VSTRING *, PSC_STATE *); 513 extern char *psc_print_grey_key(VSTRING *, const char *, const char *, 514 const char *, const char *); 515 extern const char *psc_test_name(int); 516 517 #define PSC_MIN(x, y) ((x) < (y) ? (x) : (y)) 518 #define PSC_MAX(x, y) ((x) > (y) ? (x) : (y)) 519 520 /* 521 * postscreen_early.c 522 */ 523 extern void psc_early_tests(PSC_STATE *); 524 extern void psc_early_init(void); 525 526 /* 527 * postscreen_smtpd.c 528 */ 529 extern void psc_smtpd_tests(PSC_STATE *); 530 extern void psc_smtpd_init(void); 531 extern void psc_smtpd_pre_jail_init(void); 532 533 #define PSC_SMTPD_X21(state, reply) do { \ 534 (state)->flags |= PSC_STATE_FLAG_SMTPD_X21; \ 535 (state)->final_reply = (reply); \ 536 psc_smtpd_tests(state); \ 537 } while (0) 538 539 /* 540 * postscreen_misc.c 541 */ 542 extern char *psc_format_delta_time(VSTRING *, struct timeval, DELTA_TIME *); 543 extern void psc_conclude(PSC_STATE *); 544 extern void psc_hangup_event(PSC_STATE *); 545 546 /* 547 * postscreen_send.c 548 */ 549 #define PSC_SEND_REPLY psc_send_reply /* legacy macro */ 550 extern void pcs_send_pre_jail_init(void); 551 extern int psc_send_reply(PSC_STATE *, const char *); 552 extern void psc_send_socket(PSC_STATE *); 553 554 /* 555 * postscreen_starttls.c 556 */ 557 extern void psc_starttls_open(PSC_STATE *, EVENT_NOTIFY_FN); 558 559 /* 560 * postscreen_expand.c 561 */ 562 extern VSTRING *psc_expand_filter; 563 extern void psc_expand_init(void); 564 extern const char *psc_expand_lookup(const char *, int, void *); 565 566 /* 567 * postscreen_endpt.c 568 */ 569 typedef void (*PSC_ENDPT_LOOKUP_FN) (int, VSTREAM *, 570 MAI_HOSTADDR_STR *, MAI_SERVPORT_STR *, 571 MAI_HOSTADDR_STR *, MAI_SERVPORT_STR *); 572 extern void psc_endpt_lookup(VSTREAM *, PSC_ENDPT_LOOKUP_FN); 573 extern void psc_endpt_local_lookup(VSTREAM *, PSC_ENDPT_LOOKUP_FN); 574 575 /* 576 * postscreen_access emulation. 577 */ 578 #define PSC_ACL_ACT_ALLOWLIST SERVER_ACL_ACT_PERMIT 579 #define PSC_ACL_ACT_DUNNO SERVER_ACL_ACT_DUNNO 580 #define PSC_ACL_ACT_DENYLIST SERVER_ACL_ACT_REJECT 581 #define PSC_ACL_ACT_ERROR SERVER_ACL_ACT_ERROR 582 583 #define psc_acl_pre_jail_init server_acl_pre_jail_init 584 #define psc_acl_parse server_acl_parse 585 #define psc_acl_eval(s,a,p) server_acl_eval((s)->smtp_client_addr, (a), (p)) 586 587 /* LICENSE 588 /* .ad 589 /* .fi 590 /* The Secure Mailer license must be distributed with this software. 591 /* AUTHOR(S) 592 /* Wietse Venema 593 /* IBM T.J. Watson Research 594 /* P.O. Box 704 595 /* Yorktown Heights, NY 10598, USA 596 /* 597 /* Wietse Venema 598 /* Google, Inc. 599 /* 111 8th Avenue 600 /* New York, NY 10011, USA 601 /*--*/ 602