1 /* 2 * Copyright (c) 1999-2004, 2006, 2008 Sendmail, Inc. and its suppliers. 3 * All rights reserved. 4 * 5 * By using this file, you agree to the terms and conditions set 6 * forth in the LICENSE file which can be found at the top level of 7 * the sendmail distribution. 8 * 9 * 10 * $Id: mfapi.h,v 8.80 2009/11/06 00:57:08 ca Exp $ 11 */ 12 13 /* 14 ** MFAPI.H -- Global definitions for mail filter library and mail filters. 15 */ 16 17 #ifndef _LIBMILTER_MFAPI_H 18 # define _LIBMILTER_MFAPI_H 1 19 20 #ifndef SMFI_VERSION 21 # if _FFR_MDS_NEGOTIATE 22 # define SMFI_VERSION 0x01000002 /* libmilter version number */ 23 24 /* first libmilter version that has MDS support */ 25 # define SMFI_VERSION_MDS 0x01000002 26 # else /* _FFR_MDS_NEGOTIATE */ 27 # define SMFI_VERSION 0x01000001 /* libmilter version number */ 28 # endif /* _FFR_MDS_NEGOTIATE */ 29 #endif /* ! SMFI_VERSION */ 30 31 #define SM_LM_VRS_MAJOR(v) (((v) & 0x7f000000) >> 24) 32 #define SM_LM_VRS_MINOR(v) (((v) & 0x007fff00) >> 8) 33 #define SM_LM_VRS_PLVL(v) ((v) & 0x0000007f) 34 35 # include <sys/types.h> 36 # include <sys/socket.h> 37 38 #include "libmilter/mfdef.h" 39 40 # define LIBMILTER_API extern 41 42 43 /* Only need to export C interface if used by C++ source code */ 44 #ifdef __cplusplus 45 extern "C" { 46 #endif /* __cplusplus */ 47 48 #ifndef _SOCK_ADDR 49 # define _SOCK_ADDR struct sockaddr 50 #endif /* ! _SOCK_ADDR */ 51 52 /* 53 ** libmilter functions return one of the following to indicate 54 ** success/failure(/continue): 55 */ 56 57 #define MI_SUCCESS 0 58 #define MI_FAILURE (-1) 59 #if _FFR_WORKERS_POOL 60 # define MI_CONTINUE 1 61 #endif /* _FFR_WORKERS_POOL */ 62 63 /* "forward" declarations */ 64 typedef struct smfi_str SMFICTX; 65 typedef struct smfi_str *SMFICTX_PTR; 66 67 typedef struct smfiDesc smfiDesc_str; 68 typedef struct smfiDesc *smfiDesc_ptr; 69 70 /* 71 ** Type which callbacks should return to indicate message status. 72 ** This may take on one of the SMFIS_* values listed below. 73 */ 74 75 typedef int sfsistat; 76 77 #if defined(__linux__) && defined(__GNUC__) && defined(__cplusplus) && __GNUC_MINOR__ >= 8 78 # define SM__P(X) __PMT(X) 79 #else /* __linux__ && __GNUC__ && __cplusplus && _GNUC_MINOR__ >= 8 */ 80 # define SM__P(X) __P(X) 81 #endif /* __linux__ && __GNUC__ && __cplusplus && _GNUC_MINOR__ >= 8 */ 82 83 /* Some platforms don't define __P -- do it for them here: */ 84 #ifndef __P 85 # ifdef __STDC__ 86 # define __P(X) X 87 # else /* __STDC__ */ 88 # define __P(X) () 89 # endif /* __STDC__ */ 90 #endif /* __P */ 91 92 #if SM_CONF_STDBOOL_H 93 # include <stdbool.h> 94 #else /* SM_CONF_STDBOOL_H */ 95 # ifndef __cplusplus 96 # ifndef bool 97 # ifndef __bool_true_false_are_defined 98 typedef int bool; 99 # define __bool_true_false_are_defined 1 100 # endif /* ! __bool_true_false_are_defined */ 101 # endif /* bool */ 102 # endif /* ! __cplusplus */ 103 #endif /* SM_CONF_STDBOOL_H */ 104 105 /* 106 ** structure describing one milter 107 */ 108 109 struct smfiDesc 110 { 111 char *xxfi_name; /* filter name */ 112 int xxfi_version; /* version code -- do not change */ 113 unsigned long xxfi_flags; /* flags */ 114 115 /* connection info filter */ 116 sfsistat (*xxfi_connect) SM__P((SMFICTX *, char *, _SOCK_ADDR *)); 117 118 /* SMTP HELO command filter */ 119 sfsistat (*xxfi_helo) SM__P((SMFICTX *, char *)); 120 121 /* envelope sender filter */ 122 sfsistat (*xxfi_envfrom) SM__P((SMFICTX *, char **)); 123 124 /* envelope recipient filter */ 125 sfsistat (*xxfi_envrcpt) SM__P((SMFICTX *, char **)); 126 127 /* header filter */ 128 sfsistat (*xxfi_header) SM__P((SMFICTX *, char *, char *)); 129 130 /* end of header */ 131 sfsistat (*xxfi_eoh) SM__P((SMFICTX *)); 132 133 /* body block */ 134 sfsistat (*xxfi_body) SM__P((SMFICTX *, unsigned char *, size_t)); 135 136 /* end of message */ 137 sfsistat (*xxfi_eom) SM__P((SMFICTX *)); 138 139 /* message aborted */ 140 sfsistat (*xxfi_abort) SM__P((SMFICTX *)); 141 142 /* connection cleanup */ 143 sfsistat (*xxfi_close) SM__P((SMFICTX *)); 144 145 /* any unrecognized or unimplemented command filter */ 146 sfsistat (*xxfi_unknown) SM__P((SMFICTX *, const char *)); 147 148 /* SMTP DATA command filter */ 149 sfsistat (*xxfi_data) SM__P((SMFICTX *)); 150 151 /* negotiation callback */ 152 sfsistat (*xxfi_negotiate) SM__P((SMFICTX *, 153 unsigned long, unsigned long, 154 unsigned long, unsigned long, 155 unsigned long *, unsigned long *, 156 unsigned long *, unsigned long *)); 157 158 #if 0 159 /* signal handler callback, not yet implemented. */ 160 int (*xxfi_signal) SM__P((int)); 161 #endif 162 163 }; 164 165 LIBMILTER_API int smfi_opensocket __P((bool)); 166 LIBMILTER_API int smfi_register __P((struct smfiDesc)); 167 LIBMILTER_API int smfi_main __P((void)); 168 LIBMILTER_API int smfi_setbacklog __P((int)); 169 LIBMILTER_API int smfi_setdbg __P((int)); 170 LIBMILTER_API int smfi_settimeout __P((int)); 171 LIBMILTER_API int smfi_setconn __P((char *)); 172 LIBMILTER_API int smfi_stop __P((void)); 173 LIBMILTER_API size_t smfi_setmaxdatasize __P((size_t)); 174 LIBMILTER_API int smfi_version __P((unsigned int *, unsigned int *, unsigned int *)); 175 176 /* 177 ** What the filter might do -- values to be ORed together for 178 ** smfiDesc.xxfi_flags. 179 */ 180 181 #define SMFIF_NONE 0x00000000L /* no flags */ 182 #define SMFIF_ADDHDRS 0x00000001L /* filter may add headers */ 183 #define SMFIF_CHGBODY 0x00000002L /* filter may replace body */ 184 #define SMFIF_MODBODY SMFIF_CHGBODY /* backwards compatible */ 185 #define SMFIF_ADDRCPT 0x00000004L /* filter may add recipients */ 186 #define SMFIF_DELRCPT 0x00000008L /* filter may delete recipients */ 187 #define SMFIF_CHGHDRS 0x00000010L /* filter may change/delete headers */ 188 #define SMFIF_QUARANTINE 0x00000020L /* filter may quarantine envelope */ 189 190 /* filter may change "from" (envelope sender) */ 191 #define SMFIF_CHGFROM 0x00000040L 192 #define SMFIF_ADDRCPT_PAR 0x00000080L /* add recipients incl. args */ 193 194 /* filter can send set of symbols (macros) that it wants */ 195 #define SMFIF_SETSYMLIST 0x00000100L 196 197 198 /* 199 ** Macro "places"; 200 ** Notes: 201 ** - must be coordinated with libmilter/engine.c and sendmail/milter.c 202 ** - the order MUST NOT be changed as it would break compatibility between 203 ** different versions. It's ok to append new entries however 204 ** (hence the list is not sorted by the SMT protocol steps). 205 */ 206 207 #define SMFIM_FIRST 0 /* Do NOT use, internal marker only */ 208 #define SMFIM_CONNECT 0 /* connect */ 209 #define SMFIM_HELO 1 /* HELO/EHLO */ 210 #define SMFIM_ENVFROM 2 /* MAIL From */ 211 #define SMFIM_ENVRCPT 3 /* RCPT To */ 212 #define SMFIM_DATA 4 /* DATA */ 213 #define SMFIM_EOM 5 /* end of message (final dot) */ 214 #define SMFIM_EOH 6 /* end of header */ 215 #define SMFIM_LAST 6 /* Do NOT use, internal marker only */ 216 217 /* 218 ** Continue processing message/connection. 219 */ 220 221 #define SMFIS_CONTINUE 0 222 223 /* 224 ** Reject the message/connection. 225 ** No further routines will be called for this message 226 ** (or connection, if returned from a connection-oriented routine). 227 */ 228 229 #define SMFIS_REJECT 1 230 231 /* 232 ** Accept the message, 233 ** but silently discard the message. 234 ** No further routines will be called for this message. 235 ** This is only meaningful from message-oriented routines. 236 */ 237 238 #define SMFIS_DISCARD 2 239 240 /* 241 ** Accept the message/connection. 242 ** No further routines will be called for this message 243 ** (or connection, if returned from a connection-oriented routine; 244 ** in this case, it causes all messages on this connection 245 ** to be accepted without filtering). 246 */ 247 248 #define SMFIS_ACCEPT 3 249 250 /* 251 ** Return a temporary failure, i.e., 252 ** the corresponding SMTP command will return a 4xx status code. 253 ** In some cases this may prevent further routines from 254 ** being called on this message or connection, 255 ** although in other cases (e.g., when processing an envelope 256 ** recipient) processing of the message will continue. 257 */ 258 259 #define SMFIS_TEMPFAIL 4 260 261 /* 262 ** Do not send a reply to the MTA 263 */ 264 265 #define SMFIS_NOREPLY 7 266 267 /* 268 ** Skip over rest of same callbacks, e.g., body. 269 */ 270 271 #define SMFIS_SKIP 8 272 273 /* xxfi_negotiate: use all existing protocol options/actions */ 274 #define SMFIS_ALL_OPTS 10 275 276 #if 0 277 /* 278 ** Filter Routine Details 279 */ 280 281 /* connection info filter */ 282 extern sfsistat xxfi_connect __P((SMFICTX *, char *, _SOCK_ADDR *)); 283 284 /* 285 ** xxfi_connect(ctx, hostname, hostaddr) Invoked on each connection 286 ** 287 ** char *hostname; Host domain name, as determined by a reverse lookup 288 ** on the host address. 289 ** _SOCK_ADDR *hostaddr; Host address, as determined by a getpeername 290 ** call on the SMTP socket. 291 */ 292 293 /* SMTP HELO command filter */ 294 extern sfsistat xxfi_helo __P((SMFICTX *, char *)); 295 296 /* 297 ** xxfi_helo(ctx, helohost) Invoked on SMTP HELO/EHLO command 298 ** 299 ** char *helohost; Value passed to HELO/EHLO command, which should be 300 ** the domain name of the sending host (but is, in practice, 301 ** anything the sending host wants to send). 302 */ 303 304 /* envelope sender filter */ 305 extern sfsistat xxfi_envfrom __P((SMFICTX *, char **)); 306 307 /* 308 ** xxfi_envfrom(ctx, argv) Invoked on envelope from 309 ** 310 ** char **argv; Null-terminated SMTP command arguments; 311 ** argv[0] is guaranteed to be the sender address. 312 ** Later arguments are the ESMTP arguments. 313 */ 314 315 /* envelope recipient filter */ 316 extern sfsistat xxfi_envrcpt __P((SMFICTX *, char **)); 317 318 /* 319 ** xxfi_envrcpt(ctx, argv) Invoked on each envelope recipient 320 ** 321 ** char **argv; Null-terminated SMTP command arguments; 322 ** argv[0] is guaranteed to be the recipient address. 323 ** Later arguments are the ESMTP arguments. 324 */ 325 326 /* unknown command filter */ 327 328 extern sfsistat *xxfi_unknown __P((SMFICTX *, const char *)); 329 330 /* 331 ** xxfi_unknown(ctx, arg) Invoked when SMTP command is not recognized or not 332 ** implemented. 333 ** const char *arg; Null-terminated SMTP command 334 */ 335 336 /* header filter */ 337 extern sfsistat xxfi_header __P((SMFICTX *, char *, char *)); 338 339 /* 340 ** xxfi_header(ctx, headerf, headerv) Invoked on each message header. The 341 ** content of the header may have folded white space (that is, multiple 342 ** lines with following white space) included. 343 ** 344 ** char *headerf; Header field name 345 ** char *headerv; Header field value 346 */ 347 348 /* end of header */ 349 extern sfsistat xxfi_eoh __P((SMFICTX *)); 350 351 /* 352 ** xxfi_eoh(ctx) Invoked at end of header 353 */ 354 355 /* body block */ 356 extern sfsistat xxfi_body __P((SMFICTX *, unsigned char *, size_t)); 357 358 /* 359 ** xxfi_body(ctx, bodyp, bodylen) Invoked for each body chunk. There may 360 ** be multiple body chunks passed to the filter. End-of-lines are 361 ** represented as received from SMTP (normally Carriage-Return/Line-Feed). 362 ** 363 ** unsigned char *bodyp; Pointer to body data 364 ** size_t bodylen; Length of body data 365 */ 366 367 /* end of message */ 368 extern sfsistat xxfi_eom __P((SMFICTX *)); 369 370 /* 371 ** xxfi_eom(ctx) Invoked at end of message. This routine can perform 372 ** special operations such as modifying the message header, body, or 373 ** envelope. 374 */ 375 376 /* message aborted */ 377 extern sfsistat xxfi_abort __P((SMFICTX *)); 378 379 /* 380 ** xxfi_abort(ctx) Invoked if message is aborted outside of the control of 381 ** the filter, for example, if the SMTP sender issues an RSET command. If 382 ** xxfi_abort is called, xxfi_eom will not be called and vice versa. 383 */ 384 385 /* connection cleanup */ 386 extern sfsistat xxfi_close __P((SMFICTX *)); 387 388 /* 389 ** xxfi_close(ctx) Invoked at end of the connection. This is called on 390 ** close even if the previous mail transaction was aborted. 391 */ 392 #endif /* 0 */ 393 394 /* 395 ** Additional information is passed in to the vendor filter routines using 396 ** symbols. Symbols correspond closely to sendmail macros. The symbols 397 ** defined depend on the context. The value of a symbol is accessed using: 398 */ 399 400 /* Return the value of a symbol. */ 401 LIBMILTER_API char * smfi_getsymval __P((SMFICTX *, char *)); 402 403 /* 404 ** Return the value of a symbol. 405 ** 406 ** SMFICTX *ctx; Opaque context structure 407 ** char *symname; The name of the symbol to access. 408 */ 409 410 /* 411 ** Vendor filter routines that want to pass additional information back to 412 ** the MTA for use in SMTP replies may call smfi_setreply before returning. 413 */ 414 415 LIBMILTER_API int smfi_setreply __P((SMFICTX *, char *, char *, char *)); 416 417 /* 418 ** Alternatively, smfi_setmlreply can be called if a multi-line SMTP reply 419 ** is needed. 420 */ 421 422 LIBMILTER_API int smfi_setmlreply __P((SMFICTX *, const char *, const char *, ...)); 423 424 /* 425 ** Set the specific reply code to be used in response to the active 426 ** command. If not specified, a generic reply code is used. 427 ** 428 ** SMFICTX *ctx; Opaque context structure 429 ** char *rcode; The three-digit (RFC 821) SMTP reply code to be 430 ** returned, e.g., ``551''. 431 ** char *xcode; The extended (RFC 2034) reply code, e.g., ``5.7.6''. 432 ** char *message; The text part of the SMTP reply. 433 */ 434 435 /* 436 ** The xxfi_eom routine is called at the end of a message (essentially, 437 ** after the final DATA dot). This routine can call some special routines 438 ** to modify the envelope, header, or body of the message before the 439 ** message is enqueued. These routines must not be called from any vendor 440 ** routine other than xxfi_eom. 441 */ 442 443 LIBMILTER_API int smfi_addheader __P((SMFICTX *, char *, char *)); 444 445 /* 446 ** Add a header to the message. It is not checked for standards 447 ** compliance; the mail filter must ensure that no protocols are violated 448 ** as a result of adding this header. 449 ** 450 ** SMFICTX *ctx; Opaque context structure 451 ** char *headerf; Header field name 452 ** char *headerv; Header field value 453 */ 454 455 LIBMILTER_API int smfi_chgheader __P((SMFICTX *, char *, int, char *)); 456 457 /* 458 ** Change/delete a header in the message. It is not checked for standards 459 ** compliance; the mail filter must ensure that no protocols are violated 460 ** as a result of adding this header. 461 ** 462 ** SMFICTX *ctx; Opaque context structure 463 ** char *headerf; Header field name 464 ** int index; The Nth occurence of header field name 465 ** char *headerv; New header field value (empty for delete header) 466 */ 467 468 LIBMILTER_API int smfi_insheader __P((SMFICTX *, int, char *, char *)); 469 470 /* 471 ** Insert a header into the message. It is not checked for standards 472 ** compliance; the mail filter must ensure that no protocols are violated 473 ** as a result of adding this header. 474 ** 475 ** SMFICTX *ctx; Opaque context structure 476 ** int idx; index into the header list where the insertion should happen 477 ** char *headerh; Header field name 478 ** char *headerv; Header field value 479 */ 480 481 LIBMILTER_API int smfi_chgfrom __P((SMFICTX *, char *, char *)); 482 483 /* 484 ** Modify envelope sender address 485 ** 486 ** SMFICTX *ctx; Opaque context structure 487 ** char *mail; New envelope sender address 488 ** char *args; ESMTP arguments 489 */ 490 491 492 LIBMILTER_API int smfi_addrcpt __P((SMFICTX *, char *)); 493 494 /* 495 ** Add a recipient to the envelope 496 ** 497 ** SMFICTX *ctx; Opaque context structure 498 ** char *rcpt; Recipient to be added 499 */ 500 501 LIBMILTER_API int smfi_addrcpt_par __P((SMFICTX *, char *, char *)); 502 503 /* 504 ** Add a recipient to the envelope 505 ** 506 ** SMFICTX *ctx; Opaque context structure 507 ** char *rcpt; Recipient to be added 508 ** char *args; ESMTP arguments 509 */ 510 511 512 LIBMILTER_API int smfi_delrcpt __P((SMFICTX *, char *)); 513 514 /* 515 ** Send a "no-op" up to the MTA to tell it we're still alive, so long 516 ** milter-side operations don't time out. 517 ** 518 ** SMFICTX *ctx; Opaque context structure 519 */ 520 521 LIBMILTER_API int smfi_progress __P((SMFICTX *)); 522 523 /* 524 ** Delete a recipient from the envelope 525 ** 526 ** SMFICTX *ctx; Opaque context structure 527 ** char *rcpt; Envelope recipient to be deleted. This should be in 528 ** exactly the form passed to xxfi_envrcpt or the address may 529 ** not be deleted. 530 */ 531 532 LIBMILTER_API int smfi_replacebody __P((SMFICTX *, unsigned char *, int)); 533 534 /* 535 ** Replace the body of the message. This routine may be called multiple 536 ** times if the body is longer than convenient to send in one call. End of 537 ** line should be represented as Carriage-Return/Line Feed. 538 ** 539 ** char *bodyp; Pointer to block of body information to insert 540 ** int bodylen; Length of data pointed at by bodyp 541 */ 542 543 /* 544 ** If the message is aborted (for example, if the SMTP sender sends the 545 ** envelope but then does a QUIT or RSET before the data is sent), 546 ** xxfi_abort is called. This can be used to reset state. 547 */ 548 549 /* 550 ** Quarantine an envelope 551 ** 552 ** SMFICTX *ctx; Opaque context structure 553 ** char *reason: explanation 554 */ 555 556 LIBMILTER_API int smfi_quarantine __P((SMFICTX *ctx, char *reason)); 557 558 /* 559 ** Connection-private data (specific to an SMTP connection) can be 560 ** allocated using the smfi_setpriv routine; routines can access private 561 ** data using smfi_getpriv. 562 */ 563 564 LIBMILTER_API int smfi_setpriv __P((SMFICTX *, void *)); 565 566 /* 567 ** Set the private data pointer 568 ** 569 ** SMFICTX *ctx; Opaque context structure 570 ** void *privatedata; Pointer to private data area 571 */ 572 573 LIBMILTER_API void *smfi_getpriv __P((SMFICTX *)); 574 575 /* 576 ** Get the private data pointer 577 ** 578 ** SMFICTX *ctx; Opaque context structure 579 ** void *privatedata; Pointer to private data area 580 */ 581 582 LIBMILTER_API int smfi_setsymlist __P((SMFICTX *, int, char *)); 583 584 /* 585 ** Set list of symbols (macros) to receive 586 ** 587 ** SMFICTX *ctx; Opaque context structure 588 ** int where; where in the SMTP dialogue should the macros be sent 589 ** char *macros; list of macros (space separated) 590 */ 591 592 #if _FFR_THREAD_MONITOR 593 LIBMILTER_API int smfi_set_max_exec_time __P((unsigned int)); 594 #endif /* _FFR_THREAD_MONITOR */ 595 596 #ifdef __cplusplus 597 } 598 #endif /* __cplusplus */ 599 600 #endif /* ! _LIBMILTER_MFAPI_H */ 601