1/*++ 2/* NAME 3/* cleanup 3h 4/* SUMMARY 5/* canonicalize and enqueue message 6/* SYNOPSIS 7/* #include "cleanup.h" 8/* DESCRIPTION 9/* .nf 10 11 /* 12 * System library. 13 */ 14#include <sys/time.h> 15 16 /* 17 * Utility library. 18 */ 19#include <vstring.h> 20#include <vstream.h> 21#include <argv.h> 22#include <nvtable.h> 23 24 /* 25 * Global library. 26 */ 27#include <maps.h> 28#include <tok822.h> 29#include <been_here.h> 30#include <mail_stream.h> 31#include <mail_conf.h> 32#include <mime_state.h> 33#include <string_list.h> 34#include <cleanup_user.h> 35#include <header_body_checks.h> 36#include <dsn_mask.h> 37 38 /* 39 * Milter library. 40 */ 41#include <milter.h> 42 43 /* 44 * These state variables are accessed by many functions, and there is only 45 * one instance of each per message. 46 */ 47typedef struct CLEANUP_STATE { 48 VSTRING *attr_buf; /* storage for named attribute */ 49 VSTRING *temp1; /* scratch buffer, local use only */ 50 VSTRING *temp2; /* scratch buffer, local use only */ 51 VSTRING *stripped_buf; /* character stripped input */ 52 VSTREAM *src; /* current input stream */ 53 VSTREAM *dst; /* current output stream */ 54 MAIL_STREAM *handle; /* mail stream handle */ 55 char *queue_name; /* queue name */ 56 char *queue_id; /* queue file basename */ 57 struct timeval arrival_time; /* arrival time */ 58 char *fullname; /* envelope sender full name */ 59 char *sender; /* envelope sender address */ 60 char *recip; /* envelope recipient address */ 61 char *orig_rcpt; /* original recipient address */ 62 char *return_receipt; /* return-receipt address */ 63 char *errors_to; /* errors-to address */ 64 int flags; /* processing options, status flags */ 65 int qmgr_opts; /* qmgr processing options */ 66 int errs; /* any badness experienced */ 67 int err_mask; /* allowed badness */ 68 int headers_seen; /* which headers were seen */ 69 int hop_count; /* count of received: headers */ 70 char *resent; /* any resent- header seen */ 71 BH_TABLE *dups; /* recipient dup filter */ 72 void (*action) (struct CLEANUP_STATE *, int, const char *, ssize_t); 73 off_t data_offset; /* start of message content */ 74 off_t body_offset; /* start of body content */ 75 off_t xtra_offset; /* start of extra segment */ 76 off_t cont_length; /* length including Milter edits */ 77 off_t sender_pt_offset; /* replace sender here */ 78 off_t sender_pt_target; /* record after sender address */ 79 off_t append_rcpt_pt_offset; /* append recipient here */ 80 off_t append_rcpt_pt_target; /* target of above record */ 81 off_t append_hdr_pt_offset; /* append header here */ 82 off_t append_hdr_pt_target; /* target of above record */ 83 off_t append_meta_pt_offset; /* append meta record here */ 84 off_t append_meta_pt_target; /* target of above record */ 85 ssize_t rcpt_count; /* recipient count */ 86 char *reason; /* failure reason */ 87 char *smtp_reply; /* failure reason, SMTP-style */ 88 NVTABLE *attr; /* queue file attribute list */ 89 MIME_STATE *mime_state; /* MIME state engine */ 90 int mime_errs; /* MIME error flags */ 91 char *hdr_rewrite_context; /* header rewrite context */ 92 char *filter; /* from header/body patterns */ 93 char *redirect; /* from header/body patterns */ 94 char *dsn_envid; /* DSN envelope ID */ 95 int dsn_ret; /* DSN full/hdrs */ 96 int dsn_notify; /* DSN never/delay/fail/success */ 97 char *dsn_orcpt; /* DSN original recipient */ 98 char *verp_delims; /* VERP delimiters (optional) */ 99#ifdef DELAY_ACTION 100 int defer_delay; /* deferred delivery */ 101#endif 102 103 /* 104 * Miscellaneous Milter support. 105 */ 106 MILTERS *milters; /* mail filters */ 107 const char *client_name; /* real or ersatz client */ 108 const char *reverse_name; /* real or ersatz client */ 109 const char *client_addr; /* real or ersatz client */ 110 int client_af; /* real or ersatz client */ 111 const char *client_port; /* real or ersatz client */ 112 VSTRING *milter_ext_from; /* externalized sender */ 113 VSTRING *milter_ext_rcpt; /* externalized recipient */ 114 VSTRING *milter_err_text; /* milter call-back reply */ 115 HBC_CHECKS *milter_hbc_checks; /* Milter header checks */ 116 VSTRING *milter_hbc_reply; /* Milter header checks reply */ 117 VSTRING *milter_orcpt_buf; /* add_rcpt_par() orcpt */ 118 119 /* 120 * Support for Milter body replacement requests. 121 */ 122 struct CLEANUP_REGION *free_regions;/* unused regions */ 123 struct CLEANUP_REGION *body_regions;/* regions with body content */ 124 struct CLEANUP_REGION *curr_body_region; 125} CLEANUP_STATE; 126 127 /* 128 * Status flags. Flags 0-15 are reserved for cleanup_user.h. 129 */ 130#define CLEANUP_FLAG_INRCPT (1<<16) /* Processing recipient records */ 131#define CLEANUP_FLAG_WARN_SEEN (1<<17) /* REC_TYPE_WARN record seen */ 132#define CLEANUP_FLAG_END_SEEN (1<<18) /* REC_TYPE_END record seen */ 133 134 /* 135 * Mappings. 136 */ 137extern MAPS *cleanup_comm_canon_maps; 138extern MAPS *cleanup_send_canon_maps; 139extern MAPS *cleanup_rcpt_canon_maps; 140extern int cleanup_comm_canon_flags; 141extern int cleanup_send_canon_flags; 142extern int cleanup_rcpt_canon_flags; 143extern MAPS *cleanup_header_checks; 144extern MAPS *cleanup_mimehdr_checks; 145extern MAPS *cleanup_nesthdr_checks; 146extern MAPS *cleanup_body_checks; 147extern MAPS *cleanup_virt_alias_maps; 148extern ARGV *cleanup_masq_domains; 149extern STRING_LIST *cleanup_masq_exceptions; 150extern int cleanup_masq_flags; 151extern MAPS *cleanup_send_bcc_maps; 152extern MAPS *cleanup_rcpt_bcc_maps; 153 154 /* 155 * Character filters. 156 */ 157extern VSTRING *cleanup_reject_chars; 158extern VSTRING *cleanup_strip_chars; 159 160 /* 161 * Milters. 162 */ 163extern MILTERS *cleanup_milters; 164 165 /* 166 * Address canonicalization fine control. 167 */ 168#define CLEANUP_CANON_FLAG_ENV_FROM (1<<0) /* envelope sender */ 169#define CLEANUP_CANON_FLAG_ENV_RCPT (1<<1) /* envelope recipient */ 170#define CLEANUP_CANON_FLAG_HDR_FROM (1<<2) /* header sender */ 171#define CLEANUP_CANON_FLAG_HDR_RCPT (1<<3) /* header recipient */ 172 173 /* 174 * Address masquerading fine control. 175 */ 176#define CLEANUP_MASQ_FLAG_ENV_FROM (1<<0) /* envelope sender */ 177#define CLEANUP_MASQ_FLAG_ENV_RCPT (1<<1) /* envelope recipient */ 178#define CLEANUP_MASQ_FLAG_HDR_FROM (1<<2) /* header sender */ 179#define CLEANUP_MASQ_FLAG_HDR_RCPT (1<<3) /* header recipient */ 180 181 /* 182 * Restrictions on extension propagation. 183 */ 184extern int cleanup_ext_prop_mask; 185 186 /* 187 * Saved queue file names, so the files can be removed in case of a fatal 188 * run-time error. 189 */ 190extern char *cleanup_path; 191extern VSTRING *cleanup_trace_path; 192extern VSTRING *cleanup_bounce_path; 193 194 /* 195 * cleanup_state.c 196 */ 197extern CLEANUP_STATE *cleanup_state_alloc(VSTREAM *); 198extern void cleanup_state_free(CLEANUP_STATE *); 199 200 /* 201 * cleanup_api.c 202 */ 203extern CLEANUP_STATE *cleanup_open(VSTREAM *); 204extern void cleanup_control(CLEANUP_STATE *, int); 205extern int cleanup_flush(CLEANUP_STATE *); 206extern void cleanup_free(CLEANUP_STATE *); 207extern void cleanup_all(void); 208extern void cleanup_sig(int); 209extern void cleanup_pre_jail(char *, char **); 210extern void cleanup_post_jail(char *, char **); 211extern CONFIG_INT_TABLE cleanup_int_table[]; 212extern CONFIG_BOOL_TABLE cleanup_bool_table[]; 213extern CONFIG_STR_TABLE cleanup_str_table[]; 214extern CONFIG_TIME_TABLE cleanup_time_table[]; 215 216#define CLEANUP_RECORD(s, t, b, l) ((s)->action((s), (t), (b), (l))) 217 218 /* 219 * cleanup_out.c 220 */ 221extern void cleanup_out(CLEANUP_STATE *, int, const char *, ssize_t); 222extern void cleanup_out_string(CLEANUP_STATE *, int, const char *); 223extern void PRINTFLIKE(3, 4) cleanup_out_format(CLEANUP_STATE *, int, const char *,...); 224extern void cleanup_out_header(CLEANUP_STATE *, VSTRING *); 225 226#define CLEANUP_OUT_BUF(s, t, b) \ 227 cleanup_out((s), (t), vstring_str((b)), VSTRING_LEN((b))) 228 229#define CLEANUP_OUT_OK(s) \ 230 (!((s)->errs & (s)->err_mask) && !((s)->flags & CLEANUP_FLAG_DISCARD)) 231 232 /* 233 * cleanup_envelope.c 234 */ 235extern void cleanup_envelope(CLEANUP_STATE *, int, const char *, ssize_t); 236 237 /* 238 * cleanup_message.c 239 */ 240extern void cleanup_message(CLEANUP_STATE *, int, const char *, ssize_t); 241 242 /* 243 * cleanup_extracted.c 244 */ 245extern void cleanup_extracted(CLEANUP_STATE *, int, const char *, ssize_t); 246 247 /* 248 * cleanup_final.c 249 */ 250extern void cleanup_final(CLEANUP_STATE *); 251 252 /* 253 * cleanup_rewrite.c 254 */ 255extern int cleanup_rewrite_external(const char *, VSTRING *, const char *); 256extern int cleanup_rewrite_internal(const char *, VSTRING *, const char *); 257extern int cleanup_rewrite_tree(const char *, TOK822 *); 258 259 /* 260 * cleanup_map11.c 261 */ 262extern int cleanup_map11_external(CLEANUP_STATE *, VSTRING *, MAPS *, int); 263extern int cleanup_map11_internal(CLEANUP_STATE *, VSTRING *, MAPS *, int); 264extern int cleanup_map11_tree(CLEANUP_STATE *, TOK822 *, MAPS *, int); 265 266 /* 267 * cleanup_map1n.c 268 */ 269ARGV *cleanup_map1n_internal(CLEANUP_STATE *, const char *, MAPS *, int); 270 271 /* 272 * cleanup_masquerade.c 273 */ 274extern int cleanup_masquerade_external(CLEANUP_STATE *, VSTRING *, ARGV *); 275extern int cleanup_masquerade_internal(CLEANUP_STATE *, VSTRING *, ARGV *); 276extern int cleanup_masquerade_tree(CLEANUP_STATE *, TOK822 *, ARGV *); 277 278 /* 279 * cleanup_recipient.c 280 */ 281extern void cleanup_out_recipient(CLEANUP_STATE *, const char *, int, const char *, const char *); 282 283 /* 284 * cleanup_addr.c. 285 */ 286extern void cleanup_addr_sender(CLEANUP_STATE *, const char *); 287extern void cleanup_addr_recipient(CLEANUP_STATE *, const char *); 288extern void cleanup_addr_bcc_dsn(CLEANUP_STATE *, const char *, const char *, int); 289 290#define NO_DSN_ORCPT ((char *) 0) 291#define NO_DSN_NOTIFY DSN_NOTIFY_NEVER 292#define DEF_DSN_NOTIFY (0) 293 294#define cleanup_addr_bcc(state, addr) \ 295 cleanup_addr_bcc_dsn((state), (addr), NO_DSN_ORCPT, NO_DSN_NOTIFY) 296 297 /* 298 * cleanup_bounce.c. 299 */ 300extern int cleanup_bounce(CLEANUP_STATE *); 301 302 /* 303 * MSG_STATS compatibility. 304 */ 305#define CLEANUP_MSG_STATS(stats, state) \ 306 MSG_STATS_INIT1(stats, incoming_arrival, state->arrival_time) 307 308 /* 309 * cleanup_milter.c. 310 */ 311extern void cleanup_milter_receive(CLEANUP_STATE *, int); 312extern void cleanup_milter_inspect(CLEANUP_STATE *, MILTERS *); 313extern void cleanup_milter_emul_mail(CLEANUP_STATE *, MILTERS *, const char *); 314extern void cleanup_milter_emul_rcpt(CLEANUP_STATE *, MILTERS *, const char *); 315extern void cleanup_milter_emul_data(CLEANUP_STATE *, MILTERS *); 316 317#define CLEANUP_MILTER_OK(s) \ 318 (((s)->flags & CLEANUP_FLAG_MILTER) != 0 \ 319 && (s)->errs == 0 && ((s)->flags & CLEANUP_FLAG_DISCARD) == 0) 320 321 /* 322 * cleanup_body_edit.c 323 */ 324typedef struct CLEANUP_REGION { 325 off_t start; /* start of region */ 326 off_t len; /* length or zero (open-ended) */ 327 off_t write_offs; /* write offset */ 328 struct CLEANUP_REGION *next; /* linkage */ 329} CLEANUP_REGION; 330 331extern void cleanup_region_init(CLEANUP_STATE *); 332extern CLEANUP_REGION *cleanup_region_open(CLEANUP_STATE *, ssize_t); 333extern void cleanup_region_close(CLEANUP_STATE *, CLEANUP_REGION *); 334extern CLEANUP_REGION *cleanup_region_return(CLEANUP_STATE *, CLEANUP_REGION *); 335extern void cleanup_region_done(CLEANUP_STATE *); 336 337extern int cleanup_body_edit_start(CLEANUP_STATE *); 338extern int cleanup_body_edit_write(CLEANUP_STATE *, int, VSTRING *); 339extern int cleanup_body_edit_finish(CLEANUP_STATE *); 340extern void cleanup_body_edit_free(CLEANUP_STATE *); 341 342/* LICENSE 343/* .ad 344/* .fi 345/* The Secure Mailer license must be distributed with this software. 346/* AUTHOR(S) 347/* Wietse Venema 348/* IBM T.J. Watson Research 349/* P.O. Box 704 350/* Yorktown Heights, NY 10598, USA 351/*--*/ 352