#ifndef _SENDMAIL_H
# define _SENDMAIL_H 1
#ifndef MILTER
# define MILTER 1
#endif
#ifdef _DEFINE
# define EXTERN
#else
# define EXTERN extern
#endif
#include <unistd.h>
#include <stddef.h>
#include <stdlib.h>
#include <stdio.h>
#include <ctype.h>
#include <setjmp.h>
#include <string.h>
#include <time.h>
# ifdef EX_OK
# undef EX_OK
# endif
#include "sendmail/sendmail.h"
#if MONCONTROL
# define SM_PROF(x) moncontrol(x)
#else
# define SM_PROF(x)
#endif
#ifdef _DEFINE
# ifndef lint
SM_UNUSED(static char SmailId[]) = "@(#)$Id: sendmail.h,v 8.1068 2009/12/18 17:08:01 ca Exp $";
# endif
#endif
#include "bf.h"
#include "timers.h"
#include <sm/exc.h>
#include <sm/heap.h>
#include <sm/debug.h>
#include <sm/rpool.h>
#include <sm/io.h>
#include <sm/path.h>
#include <sm/signal.h>
#include <sm/clock.h>
#include <sm/mbdb.h>
#include <sm/errstring.h>
#include <sm/sysexits.h>
#include <sm/shm.h>
#include <sm/misc.h>
#ifdef LOG
# include <syslog.h>
#endif
# if NETINET || NETINET6 || NETUNIX || NETISO || NETNS || NETX25
# include <sys/socket.h>
# endif
# if NETUNIX
# include <sys/un.h>
# endif
# if NETINET || NETINET6
# include <netinet/in.h>
# endif
# if NETINET6
# endif
# if NETISO
# include <netiso/iso.h>
# endif
# if NETNS
# include <netns/ns.h>
# endif
# if NETX25
# include <netccitt/x25.h>
# endif
# if NAMED_BIND
# include <arpa/nameser.h>
# ifdef NOERROR
# undef NOERROR
# endif
# include <resolv.h>
# else
# undef SM_SET_H_ERRNO
# define SM_SET_H_ERRNO(err)
# endif
# if HESIOD
# include <hesiod.h>
# if !defined(HES_ER_OK) || defined(HESIOD_INTERFACES)
# define HESIOD_INIT
# endif
# endif
#if STARTTLS
# include <openssl/ssl.h>
# if !TLS_NO_RSA
# define RSA_KEYLENGTH 512
# endif
#endif
#if SASL
# if SASL == 2 || SASL >= 20000
# include <sasl/sasl.h>
# include <sasl/saslutil.h>
# else
# include <sasl.h>
# include <saslutil.h>
# endif
# if defined(SASL_VERSION_MAJOR) && defined(SASL_VERSION_MINOR) && defined(SASL_VERSION_STEP)
# define SASL_VERSION (SASL_VERSION_MAJOR * 10000) + (SASL_VERSION_MINOR * 100) + SASL_VERSION_STEP
# if SASL == 1 || SASL == 2
# undef SASL
# define SASL SASL_VERSION
# else
# if SASL != SASL_VERSION
ERROR README: -DSASL (SASL) does not agree with the version of the CYRUS_SASL library (SASL_VERSION)
ERROR README: see README!
# endif
# endif
# else
# if SASL == 1
ERROR README: please set -DSASL to the version of the CYRUS_SASL library
ERROR README: see README!
# endif
# endif
#endif
#ifndef INADDRSZ
# define INADDRSZ 4
#endif
#ifndef IN6ADDRSZ
# define IN6ADDRSZ 16
#endif
#ifndef INT16SZ
# define INT16SZ 2
#endif
#ifndef INT32SZ
# define INT32SZ 4
#endif
#ifndef INADDR_LOOPBACK
# define INADDR_LOOPBACK 0x7f000001
#endif
#ifndef INADDR_NONE
# define INADDR_NONE 0xffffffff
#endif
# define QF_O_EXTRA 0
typedef enum
{
A_HEAP,
A_TEMP,
A_PERM
} ARGCLASS_T;
typedef struct envelope ENVELOPE;
typedef struct mailer MAILER;
typedef struct queuegrp QUEUEGRP;
struct address
{
char *q_paddr;
char *q_user;
char *q_ruser;
char *q_host;
struct mailer *q_mailer;
unsigned long q_flags;
uid_t q_uid;
gid_t q_gid;
char *q_home;
char *q_fullname;
struct address *q_next;
struct address *q_alias;
char *q_owner;
struct address *q_tchain;
#if PIPELINING
struct address *q_pchain;
#endif
char *q_finalrcpt;
char *q_orcpt;
char *q_status;
char *q_rstatus;
time_t q_statdate;
char *q_statmta;
short q_state;
char *q_signature;
int q_qgrp;
int q_qdir;
char *q_message;
};
typedef struct address ADDRESS;
#define QGOODUID 0x00000001
#define QPRIMARY 0x00000002
#define QNOTREMOTE 0x00000004
#define QSELFREF 0x00000008
#define QBOGUSSHELL 0x00000010
#define QUNSAFEADDR 0x00000020
#define QPINGONSUCCESS 0x00000040
#define QPINGONFAILURE 0x00000080
#define QPINGONDELAY 0x00000100
#define QHASNOTIFY 0x00000200
#define QRELAYED 0x00000400
#define QEXPANDED 0x00000800
#define QDELIVERED 0x00001000
#define QDELAYED 0x00002000
#define QALIAS 0x00004000
#define QBYTRACE 0x00008000
#define QBYNDELAY 0x00010000
#define QBYNRELAY 0x00020000
#define QTHISPASS 0x40000000
#define QRCPTOK 0x80000000
#define Q_PINGFLAGS (QPINGONSUCCESS|QPINGONFAILURE|QPINGONDELAY)
#define QS_OK 0
#define QS_SENT 1
#define QS_BADADDR 2
#define QS_QUEUEUP 3
#define QS_RETRY 4
#define QS_VERIFIED 5
#define QS_DONTSEND 6
#define QS_EXPANDED 7
#define QS_SENDER 8
#define QS_CLONED 9
#define QS_DISCARDED 10
#define QS_REPLACED 11
#define QS_REMOVED 12
#define QS_DUPLICATE 13
#define QS_INCLUDED 14
#define QS_FATALERR 15
#define QS_IS_OK(s) ((s) == QS_OK)
#define QS_IS_SENT(s) ((s) == QS_SENT)
#define QS_IS_BADADDR(s) ((s) == QS_BADADDR)
#define QS_IS_QUEUEUP(s) ((s) == QS_QUEUEUP)
#define QS_IS_RETRY(s) ((s) == QS_RETRY)
#define QS_IS_VERIFIED(s) ((s) == QS_VERIFIED)
#define QS_IS_EXPANDED(s) ((s) == QS_EXPANDED)
#define QS_IS_REMOVED(s) ((s) == QS_REMOVED)
#define QS_IS_UNDELIVERED(s) ((s) == QS_OK || \
(s) == QS_QUEUEUP || \
(s) == QS_RETRY || \
(s) == QS_VERIFIED)
#define QS_IS_UNMARKED(s) ((s) == QS_OK || \
(s) == QS_RETRY)
#define QS_IS_SENDABLE(s) ((s) == QS_OK || \
(s) == QS_QUEUEUP || \
(s) == QS_RETRY)
#define QS_IS_ATTEMPTED(s) ((s) == QS_QUEUEUP || \
(s) == QS_RETRY || \
(s) == QS_SENT || \
(s) == QS_DISCARDED)
#define QS_IS_DEAD(s) ((s) >= QS_DONTSEND)
#define NULLADDR ((ADDRESS *) NULL)
extern ADDRESS NullAddress;
extern void cataddr __P((char **, char **, char *, int, int, bool));
extern char *crackaddr __P((char *, ENVELOPE *));
extern bool emptyaddr __P((ADDRESS *));
extern ADDRESS *getctladdr __P((ADDRESS *));
extern int include __P((char *, bool, ADDRESS *, ADDRESS **, int, ENVELOPE *));
extern bool invalidaddr __P((char *, char *, bool));
extern ADDRESS *parseaddr __P((char *, ADDRESS *, int, int, char **,
ENVELOPE *, bool));
extern char **prescan __P((char *, int, char[], int, char **, unsigned char *, bool));
extern void printaddr __P((SM_FILE_T *, ADDRESS *, bool));
extern ADDRESS *recipient __P((ADDRESS *, ADDRESS **, int, ENVELOPE *));
extern char *remotename __P((char *, MAILER *, int, int *, ENVELOPE *));
extern int rewrite __P((char **, int, int, ENVELOPE *, int));
extern bool sameaddr __P((ADDRESS *, ADDRESS *));
extern int sendtolist __P((char *, ADDRESS *, ADDRESS **, int, ENVELOPE *));
#if MILTER
extern int removefromlist __P((char *, ADDRESS **, ENVELOPE *));
#endif
extern void setsender __P((char *, ENVELOPE *, char **, int, bool));
typedef void esmtp_args_F __P((ADDRESS *, char *, char *, ENVELOPE *));
extern void parse_esmtp_args __P((ENVELOPE *, ADDRESS *, char *, char *,
char *, char *args[], esmtp_args_F));
extern esmtp_args_F mail_esmtp_args;
extern esmtp_args_F rcpt_esmtp_args;
extern void reset_mail_esmtp_args __P((ENVELOPE *));
#define REWRITE(pvp, rs, env) rewrite(pvp, rs, 0, env, MAXATOM)
extern unsigned char ExtTokenTab[256];
extern unsigned char IntTokenTab[256];
struct mailer
{
char *m_name;
char *m_mailer;
char *m_mtatype;
char *m_addrtype;
char *m_diagtype;
BITMAP256 m_flags;
short m_mno;
short m_nice;
char **m_argv;
short m_sh_rwset;
short m_se_rwset;
short m_rh_rwset;
short m_re_rwset;
char *m_eol;
long m_maxsize;
int m_linelimit;
int m_maxdeliveries;
char *m_execdir;
char *m_rootdir;
uid_t m_uid;
gid_t m_gid;
char *m_defcharset;
time_t m_wait;
int m_maxrcpt;
short m_qgrp;
};
#define M_ESMTP 'a'
#define M_ALIASABLE 'A'
#define M_BLANKEND 'b'
#define M_STRIPBACKSL 'B'
#define M_NOCOMMENT 'c'
#define M_CANONICAL 'C'
#define M_NOBRACKET 'd'
#define M_EXPENSIVE 'e'
#define M_ESCFROM 'E'
#define M_FOPT 'f'
#define M_NO_NULL_FROM 'g'
#define M_HST_UPPER 'h'
#define M_PREHEAD 'H'
#define M_UDBENVELOPE 'i'
#define M_INTERNAL 'I'
#define M_UDBRECIPIENT 'j'
#define M_NOLOOPCHECK 'k'
#define M_CHUNKING 'K'
#define M_LOCALMAILER 'l'
#define M_LIMITS 'L'
#define M_MUSER 'm'
#define M_NHDR 'n'
#define M_MANYSTATUS 'N'
#define M_RUNASRCPT 'o'
#define M_FROMPATH 'p'
#define M_VRFY250 'q'
#define M_ROPT 'r'
#define M_SECURE_PORT 'R'
#define M_STRIPQ 's'
#define M_SPECIFIC_UID 'S'
#define M_USR_UPPER 'u'
#define M_UGLYUUCP 'U'
#define M_CONTENT_LEN 'v'
#define M_HASPWENT 'w'
#define M_NOHOSTSTAT 'W'
#define M_XDOT 'X'
#define M_LMTP 'z'
#define M_DIALDELAY 'Z'
#define M_NOMX '0'
#define M_NONULLS '1'
#define M_FSMTP '2'
#define M_EBCDIC '3'
#define M_TRYRULESET5 '5'
#define M_7BITHDRS '6'
#define M_7BITS '7'
#define M_8BITS '8'
#define M_MAKE8BIT '9'
#define M_CHECKINCLUDE ':'
#define M_CHECKPROG '|'
#define M_CHECKFILE '/'
#define M_CHECKUDB '@'
#define M_CHECKHDIR '~'
#define M_HOLD '%'
#define M_PLUS '+'
#define M_MINUS '-'
extern void initerrmailers __P((void));
extern void makemailer __P((char *));
extern void makequeue __P((char *, bool));
extern void runqueueevent __P((int));
#if _FFR_QUEUE_RUN_PARANOIA
extern bool checkqueuerunner __P((void));
#endif
EXTERN MAILER *FileMailer;
EXTERN MAILER *InclMailer;
EXTERN MAILER *LocalMailer;
EXTERN MAILER *ProgMailer;
EXTERN MAILER *Mailer[MAXMAILERS + 1];
struct qpaths_s
{
char *qp_name;
short qp_subdirs;
short qp_fsysidx;
# if SM_CONF_SHM
int qp_idx;
# endif
};
typedef struct qpaths_s QPATHS;
struct queuegrp
{
char *qg_name;
char *qg_qdir;
short qg_index;
int qg_maxqrun;
int qg_numqueues;
time_t qg_queueintvl;
QPATHS *qg_qpaths;
BITMAP256 qg_flags;
short qg_nice;
int qg_wgrp;
int qg_maxlist;
int qg_curnum;
int qg_maxrcpt;
time_t qg_nextrun;
#if _FFR_QUEUE_GROUP_SORTORDER
short qg_sortorder;
#endif
#if 0
long qg_wkrcptfact;
long qg_qfactor;
bool qg_doqueuerun;
#endif
};
#define QD_DEFINED ((char) 1)
#define QD_FORK 'f'
extern void filesys_update __P((void));
#if _FFR_ANY_FREE_FS
extern bool filesys_free __P((long));
#endif
#if SASL
# define SASL_WRONG (-1)
# define SASL_USER 0
# define SASL_AUTHID 1
# define SASL_PASSWORD 2
# define SASL_DEFREALM 3
# define SASL_MECHLIST 4
# define SASL_ID_REALM 5
# define SASL_MECH 6
# define SASL_ENTRIES 7
# define SASL_USER_BIT (1 << SASL_USER)
# define SASL_AUTHID_BIT (1 << SASL_AUTHID)
# define SASL_PASSWORD_BIT (1 << SASL_PASSWORD)
# define SASL_DEFREALM_BIT (1 << SASL_DEFREALM)
# define SASL_MECHLIST_BIT (1 << SASL_MECHLIST)
# define SASL_NOT_AUTH 0
# define SASL_PROC_AUTH 1
# define SASL_IS_AUTH 2
# define SASL_AUTH_AUTH 0x1000
# if SASL >= 20101
# define SASL_SEC_MASK SASL_SEC_MAXIMUM
# else
# define SASL_SEC_MASK 0x0fff
# if (SASL_SEC_NOPLAINTEXT & SASL_SEC_MASK) == 0 || \
(SASL_SEC_NOACTIVE & SASL_SEC_MASK) == 0 || \
(SASL_SEC_NODICTIONARY & SASL_SEC_MASK) == 0 || \
(SASL_SEC_FORWARD_SECRECY & SASL_SEC_MASK) == 0 || \
(SASL_SEC_NOANONYMOUS & SASL_SEC_MASK) == 0 || \
(SASL_SEC_PASS_CREDENTIALS & SASL_SEC_MASK) == 0
ERROR: change SASL_SEC_MASK_ notify sendmail.org!
# endif
# endif
# define MAXOUTLEN 8192
extern char *intersect __P((char *, char *, SM_RPOOL_T *));
extern char *iteminlist __P((char *, char *, char *));
# if SASL >= 20000
extern int proxy_policy __P((sasl_conn_t *, void *, const char *, unsigned, const char *, unsigned, const char *, unsigned, struct propctx *));
extern int safesaslfile __P((void *, const char *, sasl_verify_type_t));
# else
extern int proxy_policy __P((void *, const char *, const char *, const char **, const char **));
# if SASL > 10515
extern int safesaslfile __P((void *, char *, int));
# else
extern int safesaslfile __P((void *, char *));
# endif
# endif
extern void stop_sasl_client __P((void));
typedef char *SASL_AI_T[SASL_ENTRIES];
EXTERN char *AuthMechanisms;
EXTERN char *AuthRealm;
EXTERN char *SASLInfo;
EXTERN int SASLOpts;
EXTERN int MaxSLBits;
#endif
typedef struct
{
SM_RPOOL_T *mac_rpool;
BITMAP256 mac_allocated;
char *mac_table[MAXMACROID + 1];
} MACROS_T;
EXTERN MACROS_T GlobalMacros;
#define MCI struct mailer_con_info
MCI
{
unsigned long mci_flags;
short mci_errno;
short mci_herrno;
short mci_exitstat;
short mci_state;
int mci_deliveries;
long mci_maxsize;
SM_FILE_T *mci_in;
SM_FILE_T *mci_out;
pid_t mci_pid;
char *mci_phase;
struct mailer *mci_mailer;
char *mci_host;
char *mci_status;
char *mci_rstatus;
time_t mci_lastuse;
SM_FILE_T *mci_statfile;
char *mci_heloname;
long mci_min_by;
bool mci_retryrcpt;
char *mci_tolist;
SM_RPOOL_T *mci_rpool;
#if PIPELINING
int mci_okrcpts;
ADDRESS *mci_nextaddr;
#endif
#if SASL
SASL_AI_T mci_sai;
bool mci_sasl_auth;
int mci_sasl_string_len;
char *mci_sasl_string;
char *mci_saslcap;
sasl_conn_t *mci_conn;
#endif
#if STARTTLS
SSL *mci_ssl;
#endif
MACROS_T mci_macro;
};
#define MCIF_VALID 0x00000001
#define MCIF_CACHED 0x00000004
#define MCIF_ESMTP 0x00000008
#define MCIF_EXPN 0x00000010
#define MCIF_SIZE 0x00000020
#define MCIF_8BITMIME 0x00000040
#define MCIF_7BIT 0x00000080
#define MCIF_INHEADER 0x00000200
#define MCIF_CVT8TO7 0x00000400
#define MCIF_DSN 0x00000800
#define MCIF_8BITOK 0x00001000
#define MCIF_CVT7TO8 0x00002000
#define MCIF_INMIME 0x00004000
#define MCIF_AUTH 0x00008000
#define MCIF_AUTHACT 0x00010000
#define MCIF_ENHSTAT 0x00020000
#define MCIF_PIPELINED 0x00040000
#define MCIF_VERB 0x00080000
#if STARTTLS
#define MCIF_TLS 0x00100000
#define MCIF_TLSACT 0x00200000
#define MCIF_EXTENS (MCIF_EXPN | MCIF_SIZE | MCIF_8BITMIME | MCIF_DSN | MCIF_8BITOK | MCIF_AUTH | MCIF_ENHSTAT | MCIF_TLS)
#else
#define MCIF_EXTENS (MCIF_EXPN | MCIF_SIZE | MCIF_8BITMIME | MCIF_DSN | MCIF_8BITOK | MCIF_AUTH | MCIF_ENHSTAT)
#endif
#define MCIF_DLVR_BY 0x00400000
#if _FFR_IGNORE_EXT_ON_HELO
# define MCIF_HELO 0x00800000
#endif
#define MCIF_INLONGLINE 0x01000000
#define MCIF_ONLY_EHLO 0x10000000
#define MCIS_CLOSED 0
#define MCIS_OPENING 1
#define MCIS_OPEN 2
#define MCIS_MAIL 3
#define MCIS_RCPT 4
#define MCIS_DATA 5
#define MCIS_QUITING 6
#define MCIS_SSD 7
#define MCIS_ERROR 8
extern void mci_cache __P((MCI *));
extern void mci_close __P((MCI *, char *where));
extern void mci_dump __P((SM_FILE_T *, MCI *, bool));
extern void mci_dump_all __P((SM_FILE_T *, bool));
extern void mci_flush __P((bool, MCI *));
extern MCI *mci_get __P((char *, MAILER *));
extern int mci_lock_host __P((MCI *));
extern bool mci_match __P((char *, MAILER *));
extern int mci_print_persistent __P((char *, char *));
extern int mci_purge_persistent __P((char *, char *));
extern MCI **mci_scan __P((MCI *));
extern void mci_setstat __P((MCI *, int, char *, char *));
extern void mci_store_persistent __P((MCI *));
extern int mci_traverse_persistent __P((int (*)(char *, char *), char *));
extern void mci_unlock_host __P((MCI *));
EXTERN int MaxMciCache;
EXTERN time_t MciCacheTimeout;
EXTERN time_t MciInfoTimeout;
struct header
{
char *h_field;
char *h_value;
struct header *h_link;
unsigned char h_macro;
unsigned long h_flags;
BITMAP256 h_mflags;
};
typedef struct header HDR;
struct hdrinfo
{
char *hi_field;
unsigned long hi_flags;
char *hi_ruleset;
};
extern struct hdrinfo HdrInfo[];
#define H_EOH 0x00000001
#define H_RCPT 0x00000002
#define H_DEFAULT 0x00000004
#define H_RESENT 0x00000008
#define H_CHECK 0x00000010
#define H_ACHECK 0x00000020
#define H_FORCE 0x00000040
#define H_TRACE 0x00000080
#define H_FROM 0x00000100
#define H_VALID 0x00000200
#define H_RECEIPTTO 0x00000400
#define H_ERRORSTO 0x00000800
#define H_CTE 0x00001000
#define H_CTYPE 0x00002000
#define H_BCC 0x00004000
#define H_ENCODABLE 0x00008000
#define H_STRIPCOMM 0x00010000
#define H_BINDLATE 0x00020000
#define H_USER 0x00040000
#define CHHDR_DEF 0x0001
#define CHHDR_CHECK 0x0002
#define CHHDR_USER 0x0004
#define CHHDR_QUEUE 0x0008
extern void addheader __P((char *, char *, int, ENVELOPE *, bool));
extern unsigned long chompheader __P((char *, int, HDR **, ENVELOPE *));
extern bool commaize __P((HDR *, char *, bool, MCI *, ENVELOPE *, int));
extern HDR *copyheader __P((HDR *, SM_RPOOL_T *));
extern void eatheader __P((ENVELOPE *, bool, bool));
extern char *hvalue __P((char *, HDR *));
extern void insheader __P((int, char *, char *, int, ENVELOPE *, bool));
extern bool isheader __P((char *));
extern bool putfromline __P((MCI *, ENVELOPE *));
extern void setupheaders __P((void));
#define TIMERS struct sm_timers
TIMERS
{
TIMER ti_overall;
};
#define PUSHTIMER(l, t) { if (tTd(98, l)) pushtimer(&t); }
#define POPTIMER(l, t) { if (tTd(98, l)) poptimer(&t); }
struct envelope
{
HDR *e_header;
long e_msgpriority;
time_t e_ctime;
char *e_to;
ADDRESS e_from;
char *e_sender;
char **e_fromdomain;
ADDRESS *e_sendqueue;
ADDRESS *e_errorqueue;
long e_msgsize;
char *e_msgid;
unsigned long e_flags;
int e_nrcpts;
short e_class;
short e_hopcount;
short e_nsent;
short e_sendmode;
short e_errormode;
short e_timeoutclass;
bool (*e_puthdr)__P((MCI *, HDR *, ENVELOPE *, int));
bool (*e_putbody)__P((MCI *, ENVELOPE *, char *));
ENVELOPE *e_parent;
ENVELOPE *e_sibling;
char *e_bodytype;
SM_FILE_T *e_dfp;
char *e_id;
#if _FFR_SESSID
char *e_sessid;
#endif
int e_qgrp;
int e_qdir;
int e_dfqgrp;
int e_dfqdir;
int e_xfqgrp;
int e_xfqdir;
SM_FILE_T *e_xfp;
SM_FILE_T *e_lockfp;
char *e_message;
char *e_statmsg;
char *e_quarmsg;
char e_qfletter;
char *e_msgboundary;
char *e_origrcpt;
char *e_envid;
char *e_status;
time_t e_dtime;
int e_ntries;
dev_t e_dfdev;
ino_t e_dfino;
MACROS_T e_macro;
MCI *e_mci;
char *e_auth_param;
TIMERS e_timers;
long e_deliver_by;
int e_dlvr_flag;
SM_RPOOL_T *e_rpool;
unsigned int e_features;
#if _FFR_MILTER_ENHSC
#define ENHSC_LEN 11
char e_enhsc[ENHSC_LEN];
#endif
};
#define EF_OLDSTYLE 0x00000001L
#define EF_INQUEUE 0x00000002L
#define EF_NO_BODY_RETN 0x00000004L
#define EF_CLRQUEUE 0x00000008L
#define EF_SENDRECEIPT 0x00000010L
#define EF_FATALERRS 0x00000020L
#define EF_DELETE_BCC 0x00000040L
#define EF_RESPONSE 0x00000080L
#define EF_RESENT 0x00000100L
#define EF_VRFYONLY 0x00000200L
#define EF_WARNING 0x00000400L
#define EF_QUEUERUN 0x00000800L
#define EF_GLOBALERRS 0x00001000L
#define EF_PM_NOTIFY 0x00002000L
#define EF_METOO 0x00004000L
#define EF_LOGSENDER 0x00008000L
#define EF_NORECEIPT 0x00010000L
#define EF_HAS8BIT 0x00020000L
#define EF_NL_NOT_EOL 0x00040000L
#define EF_CRLF_NOT_EOL 0x00080000L
#define EF_RET_PARAM 0x00100000L
#define EF_HAS_DF 0x00200000L
#define EF_IS_MIME 0x00400000L
#define EF_DONT_MIME 0x00800000L
#define EF_DISCARD 0x01000000L
#define EF_TOOBIG 0x02000000L
#define EF_SPLIT 0x04000000L
#define EF_UNSAFE 0x08000000L
#define EF_TOODEEP 0x10000000L
#define DLVR_NOTIFY 0x01
#define DLVR_RETURN 0x02
#define DLVR_TRACE 0x10
#define IS_DLVR_NOTIFY(e) (((e)->e_dlvr_flag & DLVR_NOTIFY) != 0)
#define IS_DLVR_RETURN(e) (((e)->e_dlvr_flag & DLVR_RETURN) != 0)
#define IS_DLVR_TRACE(e) (((e)->e_dlvr_flag & DLVR_TRACE) != 0)
#define IS_DLVR_BY(e) ((e)->e_dlvr_flag != 0)
#define BODYTYPE_NONE (0)
#define BODYTYPE_7BIT (1)
#define BODYTYPE_8BITMIME (2)
#define BODYTYPE_ILLEGAL (-1)
#define BODYTYPE_VALID(b) ((b) == BODYTYPE_7BIT || (b) == BODYTYPE_8BITMIME)
extern ENVELOPE BlankEnvelope;
extern void clearenvelope __P((ENVELOPE *, bool, SM_RPOOL_T *));
extern int dropenvelope __P((ENVELOPE *, bool, bool));
extern ENVELOPE *newenvelope __P((ENVELOPE *, ENVELOPE *, SM_RPOOL_T *));
extern void clrsessenvelope __P((ENVELOPE *));
extern void printenvflags __P((ENVELOPE *));
extern bool putbody __P((MCI *, ENVELOPE *, char *));
extern bool putheader __P((MCI *, HDR *, ENVELOPE *, int));
struct priority
{
char *pri_name;
int pri_val;
};
EXTERN int NumPriorities;
EXTERN struct priority Priorities[MAXPRIORITIES];
struct rewrite
{
char **r_lhs;
char **r_rhs;
struct rewrite *r_next;
int r_line;
};
#define MATCHZANY ((unsigned char)0220)
#define MATCHANY ((unsigned char)0221)
#define MATCHONE ((unsigned char)0222)
#define MATCHCLASS ((unsigned char)0223)
#define MATCHNCLASS ((unsigned char)0224)
#define MATCHREPL ((unsigned char)0225)
#define CANONNET ((unsigned char)0226)
#define CANONHOST ((unsigned char)0227)
#define CANONUSER ((unsigned char)0230)
#define CALLSUBR ((unsigned char)0231)
#define CONDIF ((unsigned char)0232)
#define CONDELSE ((unsigned char)0233)
#define CONDFI ((unsigned char)0234)
#define HOSTBEGIN ((unsigned char)0235)
#define HOSTEND ((unsigned char)0236)
#define LOOKUPBEGIN ((unsigned char)0205)
#define LOOKUPEND ((unsigned char)0206)
#define MACROEXPAND ((unsigned char)0201)
#define MACRODEXPAND ((unsigned char)0202)
#define MATCHZERO CANONHOST
#define MAXMATCH 9
#define MAX_MAP_ARGS 10
struct metamac
{
char metaname;
unsigned char metaval;
};
#define MID_OPMODE 0202
#if SM_HEAP_CHECK
extern void
macdefine_tagged __P((
MACROS_T *_mac,
ARGCLASS_T _vclass,
int _id,
char *_value,
char *_file,
int _line,
int _group));
# define macdefine(mac,c,id,v) \
macdefine_tagged(mac,c,id,v,__FILE__,__LINE__,sm_heap_group())
#else
extern void
macdefine __P((
MACROS_T *_mac,
ARGCLASS_T _vclass,
int _id,
char *_value));
# define macdefine_tagged(mac,c,id,v,file,line,grp) macdefine(mac,c,id,v)
#endif
extern void macset __P((MACROS_T *, int, char *));
#define macget(mac, i) (mac)->mac_table[i]
extern void expand __P((char *, char *, size_t, ENVELOPE *));
extern int macid_parse __P((char *, char **));
#define macid(name) macid_parse(name, NULL)
extern char *macname __P((int));
extern char *macvalue __P((int, ENVELOPE *));
extern int rscheck __P((char *, char *, char *, ENVELOPE *, int, int, char *, char *, ADDRESS *));
extern int rscap __P((char *, char *, char *, ENVELOPE *, char ***, char *, int));
extern void setclass __P((int, char *));
extern int strtorwset __P((char *, char **, int));
extern char *translate_dollars __P((char *, char *, int *));
extern bool wordinclass __P((char *, int));
#define NAMECANON struct _namecanon
NAMECANON
{
short nc_errno;
short nc_herrno;
short nc_stat;
short nc_flags;
char *nc_cname;
time_t nc_exp;
};
#define NCF_VALID 0x0001
struct hostsig_t
{
char *hs_sig;
time_t hs_exp;
};
typedef struct hostsig_t HOSTSIG_T;
extern bool getcanonname __P((char *, int, bool, int *));
extern int getmxrr __P((char *, char **, unsigned short *, bool, int *, bool, int *));
extern char *hostsignature __P((MAILER *, char *));
extern int getfallbackmxrr __P((char *));
#define MAPCLASS struct _mapclass
#define MAP struct _map
#define MAXMAPACTIONS 5
MAP
{
MAPCLASS *map_class;
MAPCLASS *map_orgclass;
char *map_mname;
long map_mflags;
char *map_file;
ARBPTR_T map_db1;
ARBPTR_T map_db2;
char *map_keycolnm;
char *map_valcolnm;
unsigned char map_keycolno;
unsigned char map_valcolno;
char map_coldelim;
char map_spacesub;
char *map_app;
char *map_tapp;
char *map_domain;
char *map_rebuild;
time_t map_mtime;
time_t map_timeout;
int map_retry;
pid_t map_pid;
int map_lockfd;
short map_specificity;
MAP *map_stack[MAXMAPSTACK];
short map_return[MAXMAPACTIONS];
};
#define MF_VALID 0x00000001
#define MF_INCLNULL 0x00000002
#define MF_OPTIONAL 0x00000004
#define MF_NOFOLDCASE 0x00000008
#define MF_MATCHONLY 0x00000010
#define MF_OPEN 0x00000020
#define MF_WRITABLE 0x00000040
#define MF_ALIAS 0x00000080
#define MF_TRY0NULL 0x00000100
#define MF_TRY1NULL 0x00000200
#define MF_LOCKED 0x00000400
#define MF_ALIASWAIT 0x00000800
#define MF_IMPL_HASH 0x00001000
#define MF_IMPL_NDBM 0x00002000
#define MF_APPEND 0x00008000
#define MF_KEEPQUOTES 0x00010000
#define MF_NODEFER 0x00020000
#define MF_REGEX_NOT 0x00040000
#define MF_DEFER 0x00080000
#define MF_SINGLEMATCH 0x00100000
#define MF_SINGLEDN 0x00200000
#define MF_FILECLASS 0x00400000
#define MF_OPENBOGUS 0x00800000
#define MF_CLOSING 0x01000000
#define DYNOPENMAP(map) if (!bitset(MF_OPEN, (map)->map_mflags)) \
{ \
if (!openmap(map)) \
return NULL; \
}
#define MA_NOTFOUND 0
#define MA_UNAVAIL 1
#define MA_TRYAGAIN 2
#define BIT_IS_MTP 0x01
#define BIT_ASK_MTP 0x02
#define RESET_MAPTEMPFAIL MapTempFail = 0
#define INIT_MAPTEMPFAIL MapTempFail = BIT_ASK_MTP
#define SET_MAPTEMPFAIL MapTempFail |= BIT_IS_MTP
#define IS_MAPTEMPFAIL bitset(BIT_IS_MTP, MapTempFail)
#define ASK_MAPTEMPFAIL bitset(BIT_ASK_MTP, MapTempFail)
MAPCLASS
{
char *map_cname;
char *map_ext;
short map_cflags;
bool (*map_parse)__P((MAP *, char *));
char *(*map_lookup)__P((MAP *, char *, char **, int *));
void (*map_store)__P((MAP *, char *, char *));
bool (*map_open)__P((MAP *, int));
void (*map_close)__P((MAP *));
};
#define MCF_ALIASOK 0x0001
#define MCF_ALIASONLY 0x0002
#define MCF_REBUILDABLE 0x0004
#define MCF_OPTFILE 0x0008
#define MCF_NOTPERSIST 0x0010
extern void closemaps __P((bool));
extern bool impl_map_open __P((MAP *, int));
extern void initmaps __P((void));
extern MAP *makemapentry __P((char *));
extern void maplocaluser __P((ADDRESS *, ADDRESS **, int, ENVELOPE *));
extern char *map_rewrite __P((MAP *, const char *, size_t, char **));
#if NETINFO
extern char *ni_propval __P((char *, char *, char *, char *, int));
#endif
extern bool openmap __P((MAP *));
extern int udbexpand __P((ADDRESS *, ADDRESS **, int, ENVELOPE *));
#if USERDB
extern void _udbx_close __P((void));
extern char *udbsender __P((char *, SM_RPOOL_T *));
#endif
#if LDAPMAP
struct lamvalues
{
char *lam_name;
int lam_code;
};
struct ladvalues
{
char *lad_name;
int lad_code;
};
struct lssvalues
{
char *lss_name;
int lss_code;
};
extern bool ldapmap_parseargs __P((MAP *, char *));
extern void ldapmap_set_defaults __P((char *));
#endif
#if PH_MAP
# include <phclient.h>
struct ph_map_struct
{
char *ph_servers;
char *ph_field_list;
PH *ph;
int ph_fastclose;
time_t ph_timeout;
};
typedef struct ph_map_struct PH_MAP_STRUCT;
#endif
#if NETINET || NETINET6 || NETUNIX || NETISO || NETNS || NETX25
union bigsockaddr
{
struct sockaddr sa;
# if NETUNIX
struct sockaddr_un sunix;
# endif
# if NETINET
struct sockaddr_in sin;
# endif
# if NETINET6
struct sockaddr_in6 sin6;
# endif
# if NETISO
struct sockaddr_iso siso;
# endif
# if NETNS
struct sockaddr_ns sns;
# endif
# if NETX25
struct sockaddr_x25 sx25;
# endif
};
# define SOCKADDR union bigsockaddr
extern char *anynet_ntoa __P((SOCKADDR *));
# if NETINET6
extern char *anynet_ntop __P((struct in6_addr *, char *, size_t));
extern int anynet_pton __P((int, const char *, void *));
# endif
extern char *hostnamebyanyaddr __P((SOCKADDR *));
extern char *validate_connection __P((SOCKADDR *, char *, ENVELOPE *));
# if SASL >= 20000
extern bool iptostring __P((SOCKADDR *, SOCKADDR_LEN_T, char *, unsigned));
# endif
#endif
#define NO_PID ((pid_t) 0)
#ifndef PROC_LIST_SEG
# define PROC_LIST_SEG 32
#endif
#define PROC_NONE 0
#define PROC_DAEMON 1
#define PROC_DAEMON_CHILD 2
#define PROC_QUEUE 3
#define PROC_QUEUE_CHILD 3
#define PROC_CONTROL 4
#define PROC_CONTROL_CHILD 5
extern void proc_list_add __P((pid_t, char *, int, int, int, SOCKADDR *));
extern void proc_list_clear __P((void));
extern void proc_list_display __P((SM_FILE_T *, char *));
extern void proc_list_drop __P((pid_t, int, int *));
extern void proc_list_probe __P((void));
extern void proc_list_set __P((pid_t, char *));
extern void proc_list_signal __P((int, int));
struct symtab
{
char *s_name;
short s_symtype;
struct symtab *s_next;
union
{
BITMAP256 sv_class;
ADDRESS *sv_addr;
MAILER *sv_mailer;
char *sv_alias;
MAPCLASS sv_mapclass;
MAP sv_map;
HOSTSIG_T sv_hostsig;
MCI sv_mci;
NAMECANON sv_namecanon;
int sv_macro;
int sv_ruleset;
struct hdrinfo sv_header;
char *sv_service[MAXMAPSTACK];
#if LDAPMAP
MAP *sv_lmap;
#endif
#if SOCKETMAP
MAP *sv_socketmap;
#endif
#if MILTER
struct milter *sv_milter;
#endif
QUEUEGRP *sv_queue;
} s_value;
};
typedef struct symtab STAB;
#define ST_UNDEF 0
#define ST_CLASS 1
#define ST_ADDRESS 2
#define ST_MAILER 3
#define ST_ALIAS 4
#define ST_MAPCLASS 5
#define ST_MAP 6
#define ST_HOSTSIG 7
#define ST_NAMECANON 8
#define ST_MACRO 9
#define ST_RULESET 10
#define ST_SERVICE 11
#define ST_HEADER 12
#if LDAPMAP
# define ST_LMAP 13
#endif
#if MILTER
# define ST_MILTER 14
#endif
#define ST_QUEUE 15
#if SOCKETMAP
# define ST_SOCKETMAP 16
#endif
#define ST_MCI 17
#define s_class s_value.sv_class
#define s_address s_value.sv_addr
#define s_mailer s_value.sv_mailer
#define s_alias s_value.sv_alias
#define s_mci s_value.sv_mci
#define s_mapclass s_value.sv_mapclass
#define s_hostsig s_value.sv_hostsig
#define s_map s_value.sv_map
#define s_namecanon s_value.sv_namecanon
#define s_macro s_value.sv_macro
#define s_ruleset s_value.sv_ruleset
#define s_service s_value.sv_service
#define s_header s_value.sv_header
#if LDAPMAP
# define s_lmap s_value.sv_lmap
#endif
#if SOCKETMAP
# define s_socketmap s_value.sv_socketmap
#endif
#if MILTER
# define s_milter s_value.sv_milter
#endif
#define s_quegrp s_value.sv_queue
#define ST_FIND 0
#define ST_ENTER 1
extern STAB *stab __P((char *, int, int));
extern void stabapply __P((void (*)(STAB *, int), int));
#define MD_DELIVER 'm'
#define MD_SMTP 's'
#define MD_ARPAFTP 'a'
#define MD_DAEMON 'd'
#define MD_FGDAEMON 'D'
#define MD_LOCAL 'l'
#define MD_VERIFY 'v'
#define MD_TEST 't'
#define MD_INITALIAS 'i'
#define MD_PRINT 'p'
#define MD_PRINTNQE 'P'
#define MD_FREEZE 'z'
#define MD_HOSTSTAT 'h'
#define MD_PURGESTAT 'H'
#define MD_QUEUERUN 'q'
#define MD_CHECKCONFIG 'C'
#if _FFR_LOCAL_DAEMON
EXTERN bool LocalDaemon;
#else
# define LocalDaemon false
#endif
#define SM_DELIVER 'i'
#define SM_FORK 'b'
#if _FFR_DM_ONE
#define SM_DM_ONE 'o'
#endif
#define SM_QUEUE 'q'
#define SM_DEFER 'd'
#define SM_VERIFY 'v'
#define DM_NOTSET (-1)
#define WILL_BE_QUEUED(m) ((m) == SM_QUEUE || (m) == SM_DEFER)
#define SM_DEFAULT '\0'
extern void set_delivery_mode __P((int, ENVELOPE *));
#define EM_PRINT 'p'
#define EM_MAIL 'm'
#define EM_WRITE 'w'
#define EM_BERKNET 'e'
#define EM_QUIET 'q'
#define MM_CVTMIME 0x0001
#define MM_PASS8BIT 0x0002
#define MM_MIME8BIT 0x0004
#define NRA_NO_ACTION 0
#define NRA_ADD_TO 1
#define NRA_ADD_APPARENTLY_TO 2
#define NRA_ADD_BCC 3
#define NRA_ADD_TO_UNDISCLOSED 4
#define PXLF_NOTHINGSPECIAL 0
#define PXLF_MAPFROM 0x0001
#define PXLF_STRIP8BIT 0x0002
#define PXLF_HEADER 0x0004
#define PXLF_NOADDEOL 0x0008
#define PXLF_STRIPMQUOTE 0x0010
#define PRIV_PUBLIC 0
#define PRIV_NEEDMAILHELO 0x00000001
#define PRIV_NEEDEXPNHELO 0x00000002
#define PRIV_NEEDVRFYHELO 0x00000004
#define PRIV_NOEXPN 0x00000008
#define PRIV_NOVRFY 0x00000010
#define PRIV_AUTHWARNINGS 0x00000020
#define PRIV_NOVERB 0x00000040
#define PRIV_RESTRICTMAILQ 0x00010000
#define PRIV_RESTRICTQRUN 0x00020000
#define PRIV_RESTRICTEXPAND 0x00040000
#define PRIV_NOETRN 0x00080000
#define PRIV_NOBODYRETN 0x00100000
#define PRIV_NORECEIPTS 0x00200000
#define PRIV_NOACTUALRECIPIENT 0x00400000
#define PRIV_GOAWAY 0x0000ffff
struct prival
{
char *pv_name;
unsigned long pv_flag;
};
EXTERN unsigned long PrivacyFlags;
#define RF_SENDERADDR 0x001
#define RF_HEADERADDR 0x002
#define RF_CANONICAL 0x004
#define RF_ADDDOMAIN 0x008
#define RF_COPYPARSE 0x010
#define RF_COPYPADDR 0x020
#define RF_COPYALL (RF_COPYPARSE|RF_COPYPADDR)
#define RF_COPYNONE 0
#define RF_RM_ADDR 0x040
#define RSF_RMCOMM 0x0001
#define RSF_UNSTRUCTURED 0x0002
#define RSF_COUNT 0x0004
#define M87F_OUTER 0
#define M87F_NO8BIT 0x0001
#define M87F_DIGEST 0x0002
#define M87F_NO8TO7 0x0004
extern bool mime7to8 __P((MCI *, HDR *, ENVELOPE *));
extern int mime8to7 __P((MCI *, HDR *, ENVELOPE *, char **, int, int));
#define RTSF_NO_BODY 0
#define RTSF_SEND_BODY 0x0001
#define RTSF_PM_BOUNCE 0x0002
extern int returntosender __P((char *, ADDRESS *, int, ENVELOPE *));
typedef SM_INT32 mi_int32;
#if MILTER
# define SMFTO_WRITE 0
# define SMFTO_READ 1
# define SMFTO_EOM 2
# define SMFTO_CONNECT 3
# define SMFTO_NUM_TO 4
struct milter
{
char *mf_name;
BITMAP256 mf_flags;
mi_int32 mf_fvers;
mi_int32 mf_fflags;
mi_int32 mf_pflags;
char *mf_conn;
int mf_sock;
char mf_state;
time_t mf_timeout[SMFTO_NUM_TO];
#if _FFR_MILTER_CHECK
mi_int32 mf_mta_prot_version;
mi_int32 mf_mta_prot_flags;
mi_int32 mf_mta_actions;
#endif
};
struct milters
{
mi_int32 mis_flags;
};
typedef struct milters milters_T;
#define MIS_FL_NONE 0x00000000
#define MIS_FL_DEL_RCPT 0x00000001
#define MIS_FL_REJ_RCPT 0x00000002
# define SMF_REJECT 'R'
# define SMF_TEMPFAIL 'T'
# define SMF_TEMPDROP '4'
EXTERN struct milter *InputFilters[MAXFILTERS];
EXTERN char *InputFilterList;
EXTERN int MilterLogLevel;
extern void setup_daemon_milters __P((void));
#endif
#define VENDOR_BERKELEY 1
#define VENDOR_SUN 2
#define VENDOR_HP 3
#define VENDOR_IBM 4
#define VENDOR_SENDMAIL 5
#define VENDOR_DEC 6
extern void vendor_daemon_setup __P((ENVELOPE *));
extern void vendor_set_uid __P((UID_T));
struct termescape
{
char *te_rv_on;
char *te_under_on;
char *te_normal;
};
#define D_AUTHREQ 'a'
#define D_BINDIF 'b'
#define D_CANONREQ 'c'
#define D_IFNHELO 'h'
#define D_FQMAIL 'f'
#define D_FQRCPT 'r'
#define D_SMTPS 's'
#define D_UNQUALOK 'u'
#define D_NOAUTH 'A'
#define D_NOCANON 'C'
#define D_NOETRN 'E'
#define D_NOTLS 'S'
#define D_ETRNONLY ((char)0x01)
#define D_OPTIONAL 'O'
#define D_DISABLE ((char)0x02)
#define D_ISSET ((char)0x03)
#if STARTTLS
#define TLS_I_NONE 0x00000000
#define TLS_I_CERT_EX 0x00000001
#define TLS_I_CERT_UNR 0x00000002
#define TLS_I_KEY_EX 0x00000004
#define TLS_I_KEY_UNR 0x00000008
#define TLS_I_CERTP_EX 0x00000010
#define TLS_I_CERTP_UNR 0x00000020
#define TLS_I_CERTF_EX 0x00000040
#define TLS_I_CERTF_UNR 0x00000080
#define TLS_I_RSA_TMP 0x00000100
#define TLS_I_USE_KEY 0x00000200
#define TLS_I_USE_CERT 0x00000400
#define TLS_I_VRFY_PATH 0x00000800
#define TLS_I_VRFY_LOC 0x00001000
#define TLS_I_CACHE 0x00002000
#define TLS_I_TRY_DH 0x00004000
#define TLS_I_REQ_DH 0x00008000
#define TLS_I_DHPAR_EX 0x00010000
#define TLS_I_DHPAR_UNR 0x00020000
#define TLS_I_DH512 0x00040000
#define TLS_I_DH1024 0x00080000
#define TLS_I_DH2048 0x00100000
#define TLS_I_NO_VRFY 0x00200000
#define TLS_I_KEY_OUNR 0x00400000
#define TLS_I_CRLF_EX 0x00800000
#define TLS_I_CRLF_UNR 0x01000000
#define TLS_I_SRV_CERT (TLS_I_CERT_EX | TLS_I_KEY_EX | \
TLS_I_KEY_UNR | TLS_I_KEY_OUNR | \
TLS_I_CERTP_EX | TLS_I_CERTF_EX | \
TLS_I_USE_KEY | TLS_I_USE_CERT | TLS_I_CACHE)
#define TLS_I_SRV (TLS_I_SRV_CERT | TLS_I_RSA_TMP | TLS_I_VRFY_PATH | \
TLS_I_VRFY_LOC | TLS_I_TRY_DH | TLS_I_DH512 | \
TLS_I_CACHE)
#define TLS_I_CLT (TLS_I_KEY_UNR | TLS_I_KEY_OUNR)
#define TLS_AUTH_OK 0
#define TLS_AUTH_NO 1
#define TLS_AUTH_FAIL (-1)
extern bool init_tls_library __P((void));
extern bool inittls __P((SSL_CTX **, unsigned long, long, bool, char *, char *, char *, char *, char *));
extern bool initclttls __P((bool));
extern void setclttls __P((bool));
extern bool initsrvtls __P((bool));
extern int tls_get_info __P((SSL *, bool, char *, MACROS_T *, bool));
extern int endtls __P((SSL *, char *));
extern void tlslogerr __P((const char *));
EXTERN char *CACertPath;
EXTERN char *CACertFile;
EXTERN char *CltCertFile;
EXTERN char *CltKeyFile;
# if _FFR_TLS_1
EXTERN char *CipherList;
EXTERN char *DHParams5;
# endif
EXTERN char *DHParams;
EXTERN char *RandFile;
EXTERN char *SrvCertFile;
EXTERN char *SrvKeyFile;
EXTERN char *CRLFile;
#if _FFR_CRLPATH
EXTERN char *CRLPath;
#endif
EXTERN unsigned long TLS_Srv_Opts;
EXTERN long Srv_SSL_Options, Clt_SSL_Options;
#endif
#define ANYQFL_LETTER '?'
#define QUARQF_LETTER 'h'
#define DATAFL_LETTER 'd'
#define XSCRPT_LETTER 'x'
#define NORMQF_LETTER 'q'
#define NEWQFL_LETTER 't'
# define TEMPQF_LETTER 'T'
# define LOSEQF_LETTER 'Q'
#define QSO_BYPRIORITY 0
#define QSO_BYHOST 1
#define QSO_BYTIME 2
#define QSO_BYFILENAME 3
#define QSO_RANDOM 4
#define QSO_BYMODTIME 5
#define QSO_NONE 6
#if _FFR_RHS
# define QSO_BYSHUFFLE 7
#endif
#define NOQGRP (-1)
#define ENVQGRP (-2)
#define NOAQGRP (-3)
#define ISVALIDQGRP(x) ((x) >= 0)
#define NOQDIR (-1)
#define ENVQDIR (-2)
#define NOAQDIR (-3)
#define ISVALIDQDIR(x) ((x) >= 0)
#define RS_QUEUEGROUP "queuegroup"
#define NOW ((time_t) (-1))
#define SAFE_NO 0
#define SAFE_INTERACTIVE 1
#define SAFE_REALLY 2
#define SAFE_REALLY_POSTMILTER 3
#define QM_NORMAL ' '
#define QM_QUARANTINE 'Q'
#define QM_LOST 'L'
struct queue_char
{
char *queue_match;
bool queue_negate;
struct queue_char *queue_next;
};
#define RWG_NONE 0x0000
#define RWG_FORK 0x0001
#define RWG_VERBOSE 0x0002
#define RWG_PERSISTENT 0x0004
#define RWG_FORCE 0x0008
#define RWG_RUNALL 0x0010
typedef struct queue_char QUEUE_CHAR;
EXTERN int volatile CurRunners;
EXTERN int MaxQueueRun;
EXTERN int MaxQueueChildren;
EXTERN int MaxRunnersPerQueue;
EXTERN int NiceQueueRun;
EXTERN int NumQueue;
EXTERN int QueueFileMode;
EXTERN int QueueMode;
EXTERN int QueueSortOrder;
EXTERN time_t MinQueueAge;
#if _FFR_EXPDELAY
EXTERN time_t MaxQueueAge;
#endif
EXTERN time_t QueueIntvl;
EXTERN char *QueueDir;
EXTERN QUEUE_CHAR *QueueLimitId;
EXTERN QUEUE_CHAR *QueueLimitQuarantine;
EXTERN QUEUE_CHAR *QueueLimitRecipient;
EXTERN QUEUE_CHAR *QueueLimitSender;
EXTERN QUEUEGRP *Queue[MAXQUEUEGROUPS + 1];
extern void assign_queueid __P((ENVELOPE *));
extern ADDRESS *copyqueue __P((ADDRESS *, SM_RPOOL_T *));
extern void cleanup_queues __P((void));
extern bool doqueuerun __P((void));
extern void initsys __P((ENVELOPE *));
extern void loseqfile __P((ENVELOPE *, char *));
extern int name2qid __P((char *));
extern char *qid_printname __P((ENVELOPE *));
extern char *qid_printqueue __P((int, int));
extern void quarantine_queue __P((char *, int));
extern char *queuename __P((ENVELOPE *, int));
extern void queueup __P((ENVELOPE *, bool, bool));
extern bool runqueue __P((bool, bool, bool, bool));
extern bool run_work_group __P((int, int));
extern void set_def_queueval __P((QUEUEGRP *, bool));
extern void setup_queues __P((bool));
extern bool setnewqueue __P((ENVELOPE *));
extern bool shouldqueue __P((long, time_t));
extern void sync_queue_time __P((void));
extern void init_qid_alg __P((void));
extern int print_single_queue __P((int, int));
#if REQUIRES_DIR_FSYNC
# define SYNC_DIR(path, panic) sync_dir(path, panic)
extern void sync_dir __P((char *, bool));
#else
# define SYNC_DIR(path, panic) ((void) 0)
#endif
EXTERN struct
{
time_t to_initial;
time_t to_mail;
time_t to_rcpt;
time_t to_datainit;
time_t to_datablock;
time_t to_datafinal;
time_t to_nextcommand;
time_t to_iconnect;
time_t to_connect;
time_t to_aconnect;
time_t to_rset;
time_t to_helo;
time_t to_quit;
time_t to_miscshort;
time_t to_ident;
time_t to_fileopen;
time_t to_control;
time_t to_lhlo;
#if SASL
time_t to_auth;
#endif
#if STARTTLS
time_t to_starttls;
#endif
time_t to_q_return[MAXTOCLASS];
time_t to_q_warning[MAXTOCLASS];
time_t res_retrans[MAXRESTOTYPES];
int res_retry[MAXRESTOTYPES];
} TimeOuts;
#define TOC_NORMAL 0
#define TOC_URGENT 1
#define TOC_NONURGENT 2
#define TOC_DSN 3
#define RES_TO_FIRST 0
#define RES_TO_NORMAL 1
#define RES_TO_DEFAULT 2
extern void inittimeouts __P((char *, bool));
#define DPI_PROBENONE 0
#define DPI_PROBEALL 1
#define DPI_SKIPLOOPBACK 2
#define tTd(flag, level) (tTdvect[flag] >= (unsigned char)level)
#define tTdlevel(flag) (tTdvect[flag])
extern unsigned char tTdvect[100];
#define NOQID ""
#define CURHOSTNAME (CurHostName == NULL ? "local" : CurHostName)
#define setstat(s) { \
if (ExitStat == EX_OK || ExitStat == EX_TEMPFAIL) \
ExitStat = s; \
}
#define STRUCTCOPY(s, d) d = s
#define SM_FREE_CLR(p) \
if ((p) != NULL) \
{ \
sm_free(p); \
(p) = NULL; \
} \
else
#define PSTRSET(var, val) \
do \
{ \
char *_newval = sm_pstrdup_x(val); \
if (var != NULL) \
sm_free(var); \
var = _newval; \
} while (0)
#define _CHECK_RESTART \
do \
{ \
if (ShutdownRequest != NULL) \
shutdown_daemon(); \
else if (RestartRequest != NULL) \
restart_daemon(); \
else if (RestartWorkGroup) \
restart_marked_work_groups(); \
} while (0)
# define CHECK_RESTART _CHECK_RESTART
#define XS_DEFAULT 0
#define XS_STARTTLS 1
#define XS_AUTH 2
#if _FFR_ADDR_TYPE_MODES
EXTERN bool AddrTypeModes;
#endif
EXTERN bool AllowBogusHELO;
EXTERN bool CheckAliases;
#if _FFR_QUEUE_RUN_PARANOIA
EXTERN int CheckQueueRunners;
#endif
EXTERN bool ColonOkInAddr;
#if !defined(_USE_SUN_NSSWITCH_) && !defined(_USE_DEC_SVC_CONF_)
EXTERN bool ConfigFileRead;
#endif
EXTERN bool DisConnected;
EXTERN bool DontExpandCnames;
EXTERN bool DontInitGroups;
EXTERN bool DontLockReadFiles;
EXTERN bool DontPruneRoutes;
EXTERN bool ForkQueueRuns;
EXTERN bool FromFlag;
EXTERN bool GrabTo;
EXTERN bool EightBitAddrOK;
EXTERN bool HasEightBits;
EXTERN bool HasWildcardMX;
EXTERN bool HoldErrs;
EXTERN bool IgnoreHostStatus;
EXTERN bool IgnrDot;
EXTERN bool LogUsrErrs;
EXTERN bool MatchGecos;
EXTERN bool MeToo;
EXTERN bool NoAlias;
EXTERN bool NoConnect;
EXTERN bool OnlyOneError;
EXTERN bool QuickAbort;
#if REQUIRES_DIR_FSYNC
EXTERN bool RequiresDirfsync;
#endif
EXTERN bool volatile RestartWorkGroup;
EXTERN bool RrtImpliesDsn;
EXTERN bool SaveFrom;
EXTERN bool SendMIMEErrors;
EXTERN bool SevenBitInput;
EXTERN bool SingleLineFromHeader;
EXTERN bool SingleThreadDelivery;
EXTERN bool SoftBounce;
EXTERN bool volatile StopRequest;
EXTERN bool SuprErrs;
EXTERN bool TryNullMXList;
EXTERN bool UseMSP;
EXTERN bool WorkAroundBrokenAAAA;
EXTERN bool UseErrorsTo;
EXTERN bool UseNameServer;
EXTERN char InetMode;
EXTERN char OpMode;
EXTERN char SpaceSub;
#if _FFR_BADRCPT_SHUTDOWN
EXTERN int BadRcptShutdown;
EXTERN int BadRcptShutdownGood;
#endif
EXTERN int BadRcptThrottle;
#if _FFR_RCPTTHROTDELAY
EXTERN unsigned int BadRcptThrottleDelay;
#else
# define BadRcptThrottleDelay 1
#endif
EXTERN int CheckpointInterval;
EXTERN int ConfigLevel;
EXTERN int ConnRateThrottle;
EXTERN int volatile CurChildren;
EXTERN int CurrentLA;
EXTERN int DefaultNotify;
EXTERN int DelayLA;
EXTERN int DontProbeInterfaces;
EXTERN int Errors;
EXTERN int ExitStat;
EXTERN int FastSplit;
EXTERN int FileMode;
EXTERN int LineNumber;
EXTERN int LogLevel;
EXTERN int MaxAliasRecursion;
EXTERN int MaxChildren;
EXTERN int MaxForwardEntries;
EXTERN int MaxHeadersLength;
EXTERN int MaxHopCount;
EXTERN int MaxMacroRecursion;
EXTERN int MaxMimeFieldLength;
EXTERN int MaxMimeHeaderLength;
EXTERN int MaxNOOPCommands;
EXTERN int MaxRcptPerMsg;
EXTERN int MaxRuleRecursion;
#if _FFR_MSG_ACCEPT
EXTERN char *MessageAccept;
#endif
EXTERN int MimeMode;
EXTERN int NoRecipientAction;
#if SM_CONF_SHM
EXTERN int Numfilesys;
EXTERN int *PNumFileSys;
# define NumFileSys (*PNumFileSys)
# else
EXTERN int NumFileSys;
# endif
EXTERN int QueueLA;
EXTERN int RefuseLA;
EXTERN time_t RejectLogInterval;
#if _FFR_MEMSTAT
EXTERN long QueueLowMem;
EXTERN long RefuseLowMem;
EXTERN char *MemoryResource;
#endif
EXTERN int SuperSafe;
EXTERN int VendorCode;
EXTERN int Verbose;
EXTERN gid_t DefGid;
EXTERN gid_t RealGid;
EXTERN gid_t RunAsGid;
EXTERN gid_t EffGid;
#if SM_CONF_SHM
EXTERN key_t ShmKey;
EXTERN char *ShmKeyFile;
#endif
EXTERN pid_t CurrentPid;
EXTERN pid_t DaemonPid;
EXTERN pid_t PidFilePid;
EXTERN uid_t DefUid;
EXTERN uid_t RealUid;
EXTERN uid_t RunAsUid;
EXTERN uid_t TrustedUid;
EXTERN size_t DataFileBufferSize;
EXTERN time_t DeliverByMin;
EXTERN time_t DialDelay;
EXTERN time_t SafeAlias;
EXTERN time_t ServiceCacheMaxAge;
EXTERN size_t XscriptFileBufferSize;
EXTERN MODE_T OldUmask;
EXTERN long MaxMessageSize;
EXTERN long MinBlocksFree;
EXTERN long QueueFactor;
EXTERN long WkClassFact;
EXTERN long WkRecipFact;
EXTERN long WkTimeFact;
EXTERN char *ControlSocketName;
EXTERN char *CurHostName;
EXTERN char *DeadLetterDrop;
EXTERN char *DefUser;
EXTERN char *DefaultCharSet;
EXTERN char *DoubleBounceAddr;
EXTERN char *ErrMsgFile;
EXTERN char *FallbackMX;
EXTERN char *FallbackSmartHost;
EXTERN char *FileName;
EXTERN char *ForwardPath;
EXTERN char *HeloName;
EXTERN char *HelpFile;
EXTERN char *HostStatDir;
EXTERN char *HostsFile;
extern char *Mbdb;
EXTERN char *MustQuoteChars;
EXTERN char *MyHostName;
EXTERN char *OperatorChars;
EXTERN char *PidFile;
EXTERN char *PostMasterCopy;
EXTERN char *ProcTitlePrefix;
EXTERN char *RealHostName;
EXTERN char *RealUserName;
EXTERN char *volatile RestartRequest;
EXTERN char *RunAsUserName;
EXTERN char *SafeFileEnv;
EXTERN char *ServiceSwitchFile;
EXTERN char *volatile ShutdownRequest;
EXTERN char *SmtpGreeting;
EXTERN char *SmtpPhase;
EXTERN char SmtpError[MAXLINE];
EXTERN char *StatFile;
EXTERN char *TimeZoneSpec;
EXTERN char *UdbSpec;
EXTERN char *UnixFromLine;
EXTERN char **ExternalEnviron;
EXTERN char **SaveArgv;
EXTERN BITMAP256 DontBlameSendmail;
EXTERN SM_FILE_T *InChannel;
EXTERN SM_FILE_T *OutChannel;
EXTERN SM_FILE_T *TrafficLogFile;
#if HESIOD
EXTERN void *HesiodContext;
#endif
EXTERN ENVELOPE *CurEnv;
EXTERN char *RuleSetNames[MAXRWSETS];
EXTERN char *UserEnviron[MAXUSERENVIRON + 1];
EXTERN struct rewrite *RewriteRules[MAXRWSETS];
EXTERN struct termescape TermEscape;
EXTERN SOCKADDR ConnectOnlyTo;
EXTERN SOCKADDR RealHostAddr;
extern const SM_EXC_TYPE_T EtypeQuickAbort;
EXTERN int ConnectionRateWindowSize;
extern void closexscript __P((ENVELOPE *));
extern void openxscript __P((ENVELOPE *));
extern void buffer_errors __P((void));
extern void flush_errors __P((bool));
extern void PRINTFLIKE(1, 2) message __P((const char *, ...));
extern void PRINTFLIKE(1, 2) nmessage __P((const char *, ...));
extern void PRINTFLIKE(1, 2) syserr __P((const char *, ...));
extern void PRINTFLIKE(2, 3) usrerrenh __P((char *, const char *, ...));
extern void PRINTFLIKE(1, 2) usrerr __P((const char *, ...));
extern int isenhsc __P((const char *, int));
extern int extenhsc __P((const char *, int, char *));
extern void alias __P((ADDRESS *, ADDRESS **, int, ENVELOPE *));
extern bool aliaswait __P((MAP *, char *, bool));
extern void forward __P((ADDRESS *, ADDRESS **, int, ENVELOPE *));
extern void readaliases __P((MAP *, SM_FILE_T *, bool, bool));
extern bool rebuildaliases __P((MAP *, bool));
extern void setalias __P((char *));
extern void logdelivery __P((MAILER *, MCI *, char *, const char *, ADDRESS *, time_t, ENVELOPE *));
extern void logsender __P((ENVELOPE *, char *));
extern void PRINTFLIKE(3, 4) sm_syslog __P((int, const char *, const char *, ...));
extern void giveresponse __P((int, char *, MAILER *, MCI *, ADDRESS *, time_t, ENVELOPE *, ADDRESS *));
extern int reply __P((MAILER *, MCI *, ENVELOPE *, time_t, void (*)__P((char *, bool, MAILER *, MCI *, ENVELOPE *)), char **, int));
extern void smtp __P((char *volatile, BITMAP256, ENVELOPE *volatile));
#if SASL
extern int smtpauth __P((MAILER *, MCI *, ENVELOPE *));
#endif
extern int smtpdata __P((MAILER *, MCI *, ENVELOPE *, ADDRESS *, time_t));
extern int smtpgetstat __P((MAILER *, MCI *, ENVELOPE *));
extern int smtpmailfrom __P((MAILER *, MCI *, ENVELOPE *));
extern void smtpmessage __P((char *, MAILER *, MCI *, ...));
extern void smtpinit __P((MAILER *, MCI *, ENVELOPE *, bool));
extern char *smtptodsn __P((int));
extern int smtpprobe __P((MCI *));
extern void smtpquit __P((MAILER *, MCI *, ENVELOPE *));
extern int smtprcpt __P((ADDRESS *, MAILER *, MCI *, ENVELOPE *, ADDRESS *, time_t));
extern void smtprset __P((MAILER *, MCI *, ENVELOPE *));
#define REPLYTYPE(r) ((r) / 100)
#define ISSMTPCODE(c) (isascii(c[0]) && isdigit(c[0]) && \
isascii(c[1]) && isdigit(c[1]) && \
isascii(c[2]) && isdigit(c[2]))
#define ISSMTPREPLY(c) (ISSMTPCODE(c) && \
(c[3] == ' ' || c[3] == '-' || c[3] == '\0'))
extern pid_t dowork __P((int, int, char *, bool, bool, ENVELOPE *));
extern pid_t doworklist __P((ENVELOPE *, bool, bool));
extern int endmailer __P((MCI *, ENVELOPE *, char **));
extern int mailfile __P((char *volatile, MAILER *volatile, ADDRESS *, volatile long, ENVELOPE *));
extern void sendall __P((ENVELOPE *, int));
#define STATS_NORMAL 'n'
#define STATS_QUARANTINE 'q'
#define STATS_REJECT 'r'
#define STATS_CONNECT 'c'
extern void markstats __P((ENVELOPE *, ADDRESS *, int));
extern void clearstats __P((void));
extern void poststats __P((char *));
extern void closecontrolsocket __P((bool));
extern void clrcontrol __P((void));
extern void control_command __P((int, ENVELOPE *));
extern int opencontrolsocket __P((void));
#if MILTER
extern void milter_config __P((char *, struct milter **, int));
extern void milter_setup __P((char *));
extern void milter_set_option __P((char *, char *, bool));
extern bool milter_init __P((ENVELOPE *, char *, milters_T *));
extern void milter_quit __P((ENVELOPE *));
extern void milter_abort __P((ENVELOPE *));
extern char *milter_connect __P((char *, SOCKADDR, ENVELOPE *, char *));
extern char *milter_helo __P((char *, ENVELOPE *, char *));
extern char *milter_envfrom __P((char **, ENVELOPE *, char *));
extern char *milter_data_cmd __P((ENVELOPE *, char *));
extern char *milter_envrcpt __P((char **, ENVELOPE *, char *, bool));
extern char *milter_data __P((ENVELOPE *, char *));
extern char *milter_unknown __P((char *, ENVELOPE *, char *));
#endif
extern char *addquotes __P((char *, SM_RPOOL_T *));
extern char *arpadate __P((char *));
extern bool atobool __P((char *));
extern int atooct __P((char *));
extern void auth_warning __P((ENVELOPE *, const char *, ...));
extern int blocksignal __P((int));
extern bool bitintersect __P((BITMAP256, BITMAP256));
extern bool bitzerop __P((BITMAP256));
extern int check_bodytype __P((char *));
extern void buildfname __P((char *, char *, char *, int));
extern bool chkclientmodifiers __P((int));
extern bool chkdaemonmodifiers __P((int));
extern int checkcompat __P((ADDRESS *, ENVELOPE *));
#ifdef XDEBUG
extern void checkfd012 __P((char *));
extern void checkfdopen __P((int, char *));
#endif
extern void checkfds __P((char *));
extern bool chownsafe __P((int, bool));
extern void cleanstrcpy __P((char *, char *, int));
#if SM_CONF_SHM
extern void cleanup_shm __P((bool));
#endif
extern void close_sendmail_pid __P((void));
extern void clrdaemon __P((void));
extern void collect __P((SM_FILE_T *, bool, HDR **, ENVELOPE *, bool));
extern bool connection_rate_check __P((SOCKADDR *, ENVELOPE *));
extern time_t convtime __P((char *, int));
extern char **copyplist __P((char **, bool, SM_RPOOL_T *));
extern void copy_class __P((int, int));
extern int count_open_connections __P((SOCKADDR *));
extern time_t curtime __P((void));
extern char *defcharset __P((ENVELOPE *));
extern char *denlstring __P((char *, bool, bool));
extern void dferror __P((SM_FILE_T *volatile, char *, ENVELOPE *));
extern void disconnect __P((int, ENVELOPE *));
extern void disk_status __P((SM_FILE_T *, char *));
extern bool dns_getcanonname __P((char *, int, bool, int *, int *));
extern pid_t dofork __P((void));
extern int drop_privileges __P((bool));
extern int dsntoexitstat __P((char *));
extern void dumpfd __P((int, bool, bool));
#if SM_HEAP_CHECK
extern void dumpstab __P((void));
#endif
extern void dumpstate __P((char *));
extern bool enoughdiskspace __P((long, ENVELOPE *));
extern char *exitstat __P((char *));
extern void fatal_error __P((SM_EXC_T *));
extern char *fgetfolded __P((char *, int *, SM_FILE_T *));
extern void fill_fd __P((int, char *));
extern char *find_character __P((char *, int));
extern int finduser __P((char *, bool *, SM_MBDB_T *));
extern void finis __P((bool, bool, volatile int));
extern void fixcrlf __P((char *, bool));
extern long freediskspace __P((const char *, long *));
#if NETINET6 && NEEDSGETIPNODE
extern void freehostent __P((struct hostent *));
#endif
extern char *get_column __P((char *, int, int, char *, int));
extern char *getauthinfo __P((int, bool *));
extern int getdtsize __P((void));
extern int getla __P((void));
extern char *getmodifiers __P((char *, BITMAP256));
extern BITMAP256 *getrequests __P((ENVELOPE *));
extern char *getvendor __P((int));
extern void help __P((char *, ENVELOPE *));
extern void init_md __P((int, char **));
extern void initdaemon __P((void));
extern void inithostmaps __P((void));
extern void initmacros __P((ENVELOPE *));
extern void initsetproctitle __P((int, char **, char **));
extern void init_vendor_macros __P((ENVELOPE *));
extern SIGFUNC_DECL intsig __P((int));
extern bool isloopback __P((SOCKADDR sa));
extern void load_if_names __P((void));
extern bool lockfile __P((int, char *, char *, int));
extern void log_sendmail_pid __P((ENVELOPE *));
extern void logundelrcpts __P((ENVELOPE *, char *, int, bool));
extern char lower __P((int));
extern void makelower __P((char *));
extern int makeconnection_ds __P((char *, MCI *));
extern int makeconnection __P((char *, volatile unsigned int, MCI *, ENVELOPE *, time_t));
extern void makeworkgroups __P((void));
extern void markfailure __P((ENVELOPE *, ADDRESS *, MCI *, int, bool));
extern void mark_work_group_restart __P((int, int));
extern MCI *mci_new __P((SM_RPOOL_T *));
extern char *munchstring __P((char *, char **, int));
extern struct hostent *myhostname __P((char *, int));
extern char *newstr __P((const char *));
#if NISPLUS
extern char *nisplus_default_domain __P((void));
#endif
extern bool path_is_dir __P((char *, bool));
extern int pickqdir __P((QUEUEGRP *qg, long fsize, ENVELOPE *e));
extern char *pintvl __P((time_t, bool));
extern void printav __P((SM_FILE_T *, char **));
extern void printmailer __P((SM_FILE_T *, MAILER *));
extern void printnqe __P((SM_FILE_T *, char *));
extern void printopenfds __P((bool));
extern void printqueue __P((void));
extern void printrules __P((void));
extern pid_t prog_open __P((char **, int *, ENVELOPE *));
extern bool putline __P((char *, MCI *));
extern bool putxline __P((char *, size_t, MCI *, int));
extern void queueup_macros __P((int, SM_FILE_T *, ENVELOPE *));
extern void readcf __P((char *, bool, ENVELOPE *));
extern SIGFUNC_DECL reapchild __P((int));
extern int releasesignal __P((int));
extern void resetlimits __P((void));
extern void restart_daemon __P((void));
extern void restart_marked_work_groups __P((void));
extern bool rfc822_string __P((char *));
extern void rmexpstab __P((void));
extern bool savemail __P((ENVELOPE *, bool));
extern void seed_random __P((void));
extern void sendtoargv __P((char **, ENVELOPE *));
extern void setclientoptions __P((char *));
extern bool setdaemonoptions __P((char *));
extern void setdefaults __P((ENVELOPE *));
extern void setdefuser __P((void));
extern bool setvendor __P((char *));
extern void set_op_mode __P((int));
extern void setoption __P((int, char *, bool, bool, ENVELOPE *));
extern sigfunc_t setsignal __P((int, sigfunc_t));
extern void sm_setuserenv __P((const char *, const char *));
extern void settime __P((ENVELOPE *));
#if STARTTLS
extern void set_tls_rd_tmo __P((int));
#else
#define set_tls_rd_tmo(rd_tmo)
#endif
extern char *sfgets __P((char *, int, SM_FILE_T *, time_t, char *));
extern char *shortenstring __P((const char *, size_t));
extern char *shorten_hostname __P((char []));
extern bool shorten_rfc822_string __P((char *, size_t));
extern void shutdown_daemon __P((void));
extern void sm_closefrom __P((int lowest, int highest));
extern void sm_close_on_exec __P((int lowest, int highest));
extern struct hostent *sm_gethostbyname __P((char *, int));
extern struct hostent *sm_gethostbyaddr __P((char *, int, int));
extern void sm_getla __P((void));
extern struct passwd *sm_getpwnam __P((char *));
extern struct passwd *sm_getpwuid __P((UID_T));
extern void sm_setproctitle __P((bool, ENVELOPE *, const char *, ...));
extern pid_t sm_wait __P((int *));
extern bool split_by_recipient __P((ENVELOPE *e));
extern void stop_sendmail __P((void));
extern void stripbackslash __P((char *));
extern bool strreplnonprt __P((char *, int));
extern bool strcontainedin __P((bool, char *, char *));
extern int switch_map_find __P((char *, char *[], short []));
#if STARTTLS
extern void tls_set_verify __P((SSL_CTX *, SSL *, bool));
#endif
extern bool transienterror __P((int));
extern void truncate_at_delim __P((char *, size_t, int));
extern void tTflag __P((char *));
extern void tTsetup __P((unsigned char *, unsigned int, char *));
extern SIGFUNC_DECL tick __P((int));
extern char *ttypath __P((void));
extern void unlockqueue __P((ENVELOPE *));
#if !HASUNSETENV
extern void unsetenv __P((char *));
#endif
#if SM_CONF_SHM
extern void upd_qs __P((ENVELOPE *, int, int, char *));
# define updfs(e, count, space, where) upd_qs(e, count, space, where)
#else
# define updfs(e, count, space, where)
# define upd_qs(e, count, space, where)
#endif
extern char *username __P((void));
extern bool usershellok __P((char *, char *));
extern void vendor_post_defaults __P((ENVELOPE *));
extern void vendor_pre_defaults __P((ENVELOPE *));
extern int waitfor __P((pid_t));
extern bool writable __P((char *, ADDRESS *, long));
#if SM_HEAP_CHECK
# define xalloc(size) xalloc_tagged(size, __FILE__, __LINE__)
extern char *xalloc_tagged __P((int, char*, int));
#else
extern char *xalloc __P((int));
#endif
extern void xputs __P((SM_FILE_T *, const char *));
extern char *xtextify __P((char *, char *));
extern bool xtextok __P((char *));
extern int xunlink __P((char *));
extern char *xuntextify __P((char *));
#undef EXTERN
#endif