SCCS-vsn: usr.sbin/sendmail/src/alias.c 3.19
SCCS-vsn: usr.sbin/sendmail/src/arpadate.c 3.6
SCCS-vsn: usr.sbin/sendmail/src/conf.c 3.28
SCCS-vsn: usr.sbin/sendmail/src/deliver.c 3.35
SCCS-vsn: usr.sbin/sendmail/src/collect.c 3.19
SCCS-vsn: usr.sbin/sendmail/src/err.c 3.10
SCCS-vsn: usr.sbin/sendmail/src/sendmail.h 3.37
SCCS-vsn: usr.sbin/sendmail/src/parseaddr.c 3.23
SCCS-vsn: usr.sbin/sendmail/src/savemail.c 3.17
SCCS-vsn: usr.sbin/sendmail/src/main.c 3.32
SCCS-vsn: usr.sbin/sendmail/src/readcf.c 3.13
SCCS-vsn: usr.sbin/sendmail/src/macro.c 3.4
SCCS-vsn: usr.sbin/sendmail/src/headers.c 3.6
SCCS-vsn: usr.sbin/sendmail/src/stab.c 3.8
SCCS-vsn: bin/rmail/rmail.c 3.3
SCCS-vsn: usr.sbin/sendmail/src/recipient.c 3.10
SCCS-vsn: usr.sbin/sendmail/src/stats.c 3.2
SCCS-vsn: usr.sbin/sendmail/src/version.c 3.21
18 files changed:
* If you don't run uucp you don't even need any rmail.
*/
* If you don't run uucp you don't even need any rmail.
*/
-static char SccsId[] = "@(#)rmail.c 3.2 %G%";
+static char SccsId[] = "@(#)rmail.c 3.3 %G%";
# include <stdio.h>
# include <sysexits.h>
# include <stdio.h>
# include <sysexits.h>
- fgets(lbuf, sizeof lbuf, stdin);
+ (void) fgets(lbuf, sizeof lbuf, stdin);
if (strncmp(lbuf, "From ", 5) != 0 && strncmp(lbuf, ">From ", 6) != 0)
break;
sscanf(lbuf, "%s %s", junk, ufrom);
if (strncmp(lbuf, "From ", 5) != 0 && strncmp(lbuf, ">From ", 6) != 0)
break;
sscanf(lbuf, "%s %s", junk, ufrom);
# include "sendmail.h"
# ifdef DBM
# include "sendmail.h"
# ifdef DBM
-static char SccsId[] = "@(#)alias.c 3.18 %G% (with DBM)";
+static char SccsId[] = "@(#)alias.c 3.19 %G% (with DBM)";
-static char SccsId[] = "@(#)alias.c 3.18 %G% (without DBM)";
+static char SccsId[] = "@(#)alias.c 3.19 %G% (without DBM)";
+ /*
+ ** Look up this name
+ */
+
# ifdef DBM
/* create a key for fetch */
lhs.dptr = a->q_user;
# ifdef DBM
/* create a key for fetch */
lhs.dptr = a->q_user;
- /* read and interpret lines */
+
+ /*
+ ** Read and interpret lines
+ */
+
lineno = 0;
skipping = FALSE;
while (fgets(line, sizeof (line), af) != NULL)
lineno = 0;
skipping = FALSE;
while (fgets(line, sizeof (line), af) != NULL)
+ /*
+ ** Process the LHS
+ ** Find the final colon, and parse the address.
+ ** It should resolve to a local name -- this will
+ ** be checked later (we want to optionally do
+ ** parsing of the RHS first to maximize error
+ ** detection).
+ */
+
for (p = line; *p != '\0' && *p != ':' && *p != '\n'; p++)
continue;
if (*p == '\0' || *p == '\n')
for (p = line; *p != '\0' && *p != ':' && *p != '\n'; p++)
continue;
if (*p == '\0' || *p == '\n')
*--p = ':';
goto syntaxerr;
}
*--p = ':';
goto syntaxerr;
}
+
+ /*
+ ** Process the RHS.
+ ** 'al' is the internal form of the LHS address.
+ ** 'p' points to the text of the RHS.
+ */
+
+ (void) parse(p2, &bl, -1);
p[-1] = c;
while (isspace(*p))
p++;
p[-1] = c;
while (isspace(*p))
p++;
/* see if there should be a continuation line */
c = fgetc(af);
if (!feof(af))
/* see if there should be a continuation line */
c = fgetc(af);
if (!feof(af))
if (c != ' ' && c != '\t')
break;
if (c != ' ' && c != '\t')
break;
syserr("aliases: %d: cannot alias non-local names", lineno);
continue;
}
syserr("aliases: %d: cannot alias non-local names", lineno);
continue;
}
+
+ /*
+ ** Insert alias into symbol table or DBM file
+ */
+
** This is similar but not identical to aliasing.
**
** Parameters:
** This is similar but not identical to aliasing.
**
** Parameters:
-** user -- the name of the user who's mail we
-** would like to forward to.
+** user -- the name of the user who's mail we would like
+** to forward to. It must have been verified --
+** i.e., the q_home field must have been filled
+** in.
ADDRESS *user;
{
char buf[60];
ADDRESS *user;
{
char buf[60];
- register FILE *fp;
- register char *p;
struct stat stbuf;
# ifdef DEBUG
struct stat stbuf;
# ifdef DEBUG
if (user->q_mailer != MN_LOCAL || bitset(QBADADDR, user->q_flags))
return;
if (user->q_mailer != MN_LOCAL || bitset(QBADADDR, user->q_flags))
return;
+# ifdef DEBUG
+ if (user->q_home == NULL)
+ syserr("forward: no home");
+# endif DEBUG
/* good address -- look for .forward file in home */
define('z', user->q_home);
/* good address -- look for .forward file in home */
define('z', user->q_home);
# include <sys/timeb.h>
# endif
# include <sys/timeb.h>
# endif
-static char SccsId[] = "@(#)arpadate.c 3.5 %G%";
+static char SccsId[] = "@(#)arpadate.c 3.6 %G%";
/*
** ARPADATE -- Create date in ARPANET format
/*
** ARPADATE -- Create date in ARPANET format
** Timezone is computed from local time, rather than
** from whereever (and whenever) the message was sent.
** To do better is very hard.
** Timezone is computed from local time, rather than
** from whereever (and whenever) the message was sent.
** To do better is very hard.
+**
+** Some sites are now inserting the timezone into the
+** local date. This routine should figure out what
+** the format is and work appropriately.
-# ifdef V6
-# define DST_NAME "PDT"
-# define STD_NAME "PST"
-# endif
-
# define NULL 0
struct cvttab
# define NULL 0
struct cvttab
extern struct tm *localtime();
# ifdef V6
long t;
extern struct tm *localtime();
# ifdef V6
long t;
+ extern char *StdTimezone, *DstTimezone;
+ extern long time();
# else
struct timeb t;
extern struct timeb *ftime();
extern char *timezone();
# endif
# else
struct timeb t;
extern struct timeb *ftime();
extern char *timezone();
# endif
+ /*
+ ** Get current time.
+ ** This will be used if a null argument is passed and
+ ** to resolve the timezone.
+ */
+
if (ud == NULL)
ud = ctime(&t);
# else
if (ud == NULL)
ud = ctime(&t);
# else
ud = ctime(&t.time);
# endif
ud = ctime(&t.time);
# endif
+ /*
+ ** Crack the UNIX date line in a singularly unoriginal way.
+ */
+
q = b;
p = &ud[8]; /* 16 */
q = b;
p = &ud[8]; /* 16 */
/* -PST or -PDT */
# ifdef V6
if (localtime(&t)->tm_isdst)
/* -PST or -PDT */
# ifdef V6
if (localtime(&t)->tm_isdst)
# else
p = timezone(t.timezone, localtime(&t.time)->tm_isdst);
# endif V6
# else
p = timezone(t.timezone, localtime(&t.time)->tm_isdst);
# endif V6
# include <errno.h>
# include "sendmail.h"
# include <errno.h>
# include "sendmail.h"
-static char SccsId[] = "@(#)collect.c 3.18 %G%";
+static char SccsId[] = "@(#)collect.c 3.19 %G%";
/*
** COLLECT -- read & parse message header & make temp file.
/*
** COLLECT -- read & parse message header & make temp file.
register FILE *tf;
char buf[MAXFIELD+1];
register char *p;
register FILE *tf;
char buf[MAXFIELD+1];
register char *p;
- char c;
- extern bool isheader();
char *xfrom;
extern char *hvalue();
extern char *mktemp();
char *xfrom;
extern char *hvalue();
extern char *mktemp();
- extern char *capitalize();
-# ifdef DEBUG
- HDR *h;
-# endif
- /* try to read a UNIX-style From line */
+ /*
+ ** Try to read a UNIX-style From line
+ */
+
if (fgets(buf, sizeof buf, stdin) == NULL)
return;
if (strncmp(buf, "From ", 5) == 0)
if (fgets(buf, sizeof buf, stdin) == NULL)
return;
if (strncmp(buf, "From ", 5) == 0)
for (; !feof(stdin); !feof(stdin) && fgets(buf, sizeof buf, stdin))
{
for (; !feof(stdin); !feof(stdin) && fgets(buf, sizeof buf, stdin))
{
+ register char c;
+ extern bool isheader();
+
/* see if the header is over */
if (!isheader(buf))
break;
/* see if the header is over */
if (!isheader(buf))
break;
if (xfrom == NULL)
xfrom = hvalue("original-from");
if (ArpaMode != ARPA_NONE)
if (xfrom == NULL)
xfrom = hvalue("original-from");
if (ArpaMode != ARPA_NONE)
+ setfrom(xfrom, (char *) NULL);
/* full name of from person */
p = hvalue("full-name");
/* full name of from person */
p = hvalue("full-name");
# ifdef DEBUG
if (Debug)
{
# ifdef DEBUG
if (Debug)
{
+ HDR *h;
+ extern char *capitalize();
+
printf("----- collected header -----\n");
for (h = Header; h != NULL; h = h->h_link)
printf("%s: %s\n", capitalize(h->h_field), h->h_value);
printf("----- collected header -----\n");
for (h = Header; h != NULL; h = h->h_link)
printf("%s: %s\n", capitalize(h->h_field), h->h_value);
** HdrInfo -- a table describing well-known header fields.
** Each entry has the field name and some flags,
** which are described in sendmail.h.
** HdrInfo -- a table describing well-known header fields.
** Each entry has the field name and some flags,
** which are described in sendmail.h.
+** StdTimezone -- name of local timezone in standard time
+** (V6 only).
+** DstTimezone -- name of local timezone in daylight savings
+** time (V6 only).
**
** Notes:
** I have tried to put almost all the reasonable
**
** Notes:
** I have tried to put almost all the reasonable
-static char SccsId[] = "@(#)conf.c 3.27 %G%";
+static char SccsId[] = "@(#)conf.c 3.28 %G%";
# include <whoami.h> /* definitions of machine id's at berkeley */
# include <whoami.h> /* definitions of machine id's at berkeley */
char *AliasFile = "/usr/lib/aliases"; /* alias file */
char *ConfFile = "/usr/lib/sendmail.cf"; /* runtime configuration */
char *StatFile = "/usr/eric/mailstats"; /* statistics summary */
char *AliasFile = "/usr/lib/aliases"; /* alias file */
char *ConfFile = "/usr/lib/sendmail.cf"; /* runtime configuration */
char *StatFile = "/usr/eric/mailstats"; /* statistics summary */
+
+
+
+/*
+** V6 system configuration.
+*/
+
+# ifdef V6
+char *StdTimezone = "PST"; /* std time timezone */
+char *DstTimezone = "PDT"; /* daylight time timezone */
+# endif V6
# include <syslog.h>
# endif LOG
# include <syslog.h>
# endif LOG
-static char SccsId[] = "@(#)deliver.c 3.34 %G%";
+static char SccsId[] = "@(#)deliver.c 3.35 %G%";
-** DELIVER -- Deliver a message to a particular address.
+** DELIVER -- Deliver a message to a list of addresses.
+**
+** This routine delivers to everyone on the same host as the
+** user on the head of the list. It is clever about mailers
+** that don't handle multiple users. It is NOT guaranteed
+** that it will deliver to all these addresses however -- so
+** deliver should be called once for each address on the
+** list.
-** to -- the address to deliver the message to.
+** to -- head of the address list to deliver to.
** editfcn -- if non-NULL, we want to call this function
** to output the letter (instead of just out-
** putting it raw).
** editfcn -- if non-NULL, we want to call this function
** to output the letter (instead of just out-
** putting it raw).
user = to->q_user;
To = to->q_paddr;
to->q_flags |= QDONTSEND;
user = to->q_user;
To = to->q_paddr;
to->q_flags |= QDONTSEND;
# ifdef DEBUG
if (Debug)
printf(" send to `%s'\n", user);
# ifdef DEBUG
if (Debug)
printf(" send to `%s'\n", user);
+ /*
+ ** Address is verified -- add this user to mailer
+ ** argv, and add it to the print list of recipients.
+ */
+
/* create list of users for error messages */
if (tobuf[0] != '\0')
(void) strcat(tobuf, ",");
/* create list of users for error messages */
if (tobuf[0] != '\0')
(void) strcat(tobuf, ",");
** The argument vector gets built, pipes
** are created as necessary, and we fork & exec as
** appropriate.
** The argument vector gets built, pipes
** are created as necessary, and we fork & exec as
** appropriate.
- **
- ** Notice the tacky hack to handle private mailers.
** Side Effects:
** Errors may be incremented.
** ExitStat may be set.
** Side Effects:
** Errors may be incremented.
** ExitStat may be set.
-**
-** Called By:
-** deliver
*/
giveresponse(stat, force, m)
*/
giveresponse(stat, force, m)
extern int N_SysEx;
char buf[30];
extern int N_SysEx;
char buf[30];
+ /*
+ ** Compute status message from code.
+ */
+
i = stat - EX__BASE;
if (i < 0 || i > N_SysEx)
statmsg = NULL;
i = stat - EX__BASE;
if (i < 0 || i > N_SysEx)
statmsg = NULL;
{
char buf[BUFSIZ];
register int i;
{
char buf[BUFSIZ];
register int i;
- HDR *h;
- register char *p;
extern char *arpadate();
bool anyheader = FALSE;
extern char *capitalize();
extern char SentDate[];
extern char *arpadate();
bool anyheader = FALSE;
extern char *capitalize();
extern char SentDate[];
- /* output "From" line unless supressed */
+ /*
+ ** Output "From" line unless supressed
+ */
+
if (!bitset(M_NHDR, m->m_flags))
{
(void) expand("$l", buf, &buf[sizeof buf - 1]);
fprintf(fp, "%s\n", buf);
}
if (!bitset(M_NHDR, m->m_flags))
{
(void) expand("$l", buf, &buf[sizeof buf - 1]);
fprintf(fp, "%s\n", buf);
}
- /* output all header lines */
+ /*
+ ** Output all header lines
+ */
+
for (h = Header; h != NULL; h = h->h_link)
{
for (h = Header; h != NULL; h = h->h_link)
{
if (bitset(H_CHECK|H_ACHECK, h->h_flags) && !bitset(h->h_mflags, m->m_flags))
{
p = ")><("; /* can't happen (I hope) */
if (bitset(H_CHECK|H_ACHECK, h->h_flags) && !bitset(h->h_mflags, m->m_flags))
{
p = ")><("; /* can't happen (I hope) */
fprintf(fp, "Original-From: %s\n", ofrom);
}
}
fprintf(fp, "Original-From: %s\n", ofrom);
}
}
if (anyheader)
fprintf(fp, "\n");
if (anyheader)
fprintf(fp, "\n");
- /* output the body of the message */
+ /*
+ ** Output the body of the message
+ */
+
rewind(TempFile);
while (!ferror(fp) && (i = fread(buf, 1, BUFSIZ, TempFile)) > 0)
(void) fwrite(buf, 1, i, fp);
rewind(TempFile);
while (!ferror(fp) && (i = fread(buf, 1, BUFSIZ, TempFile)) > 0)
(void) fwrite(buf, 1, i, fp);
{
register FILE *f;
register int pid;
{
register FILE *f;
register int pid;
/*
** Fork so we can change permissions here.
/*
** Fork so we can change permissions here.
(void) fclose(f);
(void) fflush(stdout);
exit(EX_OK);
(void) fclose(f);
(void) fflush(stdout);
exit(EX_OK);
# include <syslog.h>
# endif LOG
# include <syslog.h>
# endif LOG
-static char SccsId[] = "@(#)err.c 3.9 %G%";
+static char SccsId[] = "@(#)err.c 3.10 %G%";
- syslog(LOG_ERR, "%s->%s: %s", From.q_paddr, To, errbuf);
+ syslog(LOG_ERR, "%s->%s: %s", From.q_paddr, To, &errbuf[4]);
# include <errno.h>
# include "sendmail.h"
# include <errno.h>
# include "sendmail.h"
-static char SccsId[] = "@(#)headers.c 3.5 %G%";
+static char SccsId[] = "@(#)headers.c 3.6 %G%";
/*
** CHOMPHEADER -- process and save a header line.
/*
** CHOMPHEADER -- process and save a header line.
**
** Side Effects:
** The header is saved on the header list.
**
** Side Effects:
** The header is saved on the header list.
+** Contents of 'line' are destroyed.
*/
chompheader(line, def)
*/
chompheader(line, def)
\f/*
** ISHEADER -- predicate telling if argument is a header.
**
\f/*
** ISHEADER -- predicate telling if argument is a header.
**
+** A line is a header if it has a single word followed by
+** optional white space followed by a colon.
+**
** Parameters:
** s -- string to check for possible headerness.
**
** Parameters:
** s -- string to check for possible headerness.
**
**
** Side Effects:
** none.
**
** Side Effects:
** none.
+**
+** Bugs:
+** According to RFC733, there should be a newline
+** permitted after the word but before the colon.
+** We don't seem to support that.....
-static char SccsId[] = "@(#)macro.c 3.3 %G%";
+static char SccsId[] = "@(#)macro.c 3.4 %G%";
char *Macro[128];
extern int Debug;
char *Macro[128];
extern int Debug;
** of the last usable position in buf.
**
** Returns:
** of the last usable position in buf.
**
** Returns:
+** End of interpolated output.
**
** Side Effects:
** none.
**
** Side Effects:
** none.
register char *buf;
char *buflim;
{
register char *buf;
char *buflim;
{
+ bool skipping; /* set if conditionally skipping output */
# ifdef DEBUG
if (Debug > 3)
# ifdef DEBUG
if (Debug > 3)
skipping = FALSE;
for (bp = buf; *s != '\0'; s++)
{
skipping = FALSE;
for (bp = buf; *s != '\0'; s++)
{
- /* q will be the interpolated quantity */
+ register char *q;
+
+ /*
+ ** Check for non-ordinary (special?) character --
+ ** always escaped with dollar sign.
+ ** 'q' will be the interpolated quantity.
+ */
+
q = NULL;
if (*s == '$')
{
q = NULL;
if (*s == '$')
{
# include <syslog.h>
# endif LOG
# include <syslog.h>
# endif LOG
-static char SccsId[] = "@(#)main.c 3.31 %G%";
+static char SccsId[] = "@(#)main.c 3.32 %G%";
/*
** SENDMAIL -- Post mail to a set of destinations.
/*
** SENDMAIL -- Post mail to a set of destinations.
** -Ffullname Select what the full-name should be
** listed as.
** -a This mail should be in ARPANET std
** -Ffullname Select what the full-name should be
** listed as.
** -a This mail should be in ARPANET std
+** format (obsolete version).
+** -am Called from an FTP "MAIL" command.
+** -af Called from an FTP "MLFL" command.
** -n Don't do aliasing. This might be used
** when delivering responses, for
** instance.
** -n Don't do aliasing. This might be used
** when delivering responses, for
** instance.
** everything that happens.
** -t Read "to" addresses from message.
** Looks at To:, Cc:, and Bcc: lines.
** everything that happens.
** -t Read "to" addresses from message.
** Looks at To:, Cc:, and Bcc: lines.
+** -I Initialize the DBM alias files from
+** the text format files.
** -Cfilename Use alternate configuration file.
** -Afilename Use alternate alias file.
** -DXvalue Define macro X to have value.
** -Cfilename Use alternate configuration file.
** -Afilename Use alternate alias file.
** -DXvalue Define macro X to have value.
** Compilation Flags:
** LOG -- if set, everything is logged.
**
** Compilation Flags:
** LOG -- if set, everything is logged.
**
-** Compilation Instructions:
-** cc -c -O main.c conf.c deliver.c parse.c
-** cc -n -s *.o -lS
-** chown root a.out
-** chmod 755 a.out
-** mv a.out sendmail
-**
-** Deficiencies:
-** It ought to collect together messages that are
-** destined for a single host and send these
-** to the auxiliary mail server together.
-** It should take "user at host" as three separate
-** parameters and combine them into one address.
-**
** Author:
** Eric Allman, UCB/INGRES
*/
** Author:
** Eric Allman, UCB/INGRES
*/
break;
case 'F': /* set full name */
break;
case 'F': /* set full name */
+ p += 2;
+ if (*p == '\0')
+ {
+ p = *++argv;
+ if (--argc <= 0 || *p == '-')
+ {
+ syserr("Bad -F flag");
+ argc++;
+ argv--;
+ break;
+ }
+ }
+ fullname = p;
break;
case 'h': /* hop count */
break;
case 'h': /* hop count */
**
** Side Effects:
** exits sendmail
**
** Side Effects:
** exits sendmail
-**
-** Called By:
-** main
-** via signal on interrupt.
-**
-** Deficiencies:
-** It may be that it should only remove the input
-** file if there have been no errors.
** Side Effects:
** Turns the standard output into a special file
** somewhere.
** Side Effects:
** Turns the standard output into a special file
** somewhere.
-**
-** Called By:
-** main
-static char SccsId[] = "@(#)parseaddr.c 3.22 %G%";
+static char SccsId[] = "@(#)parseaddr.c 3.23 %G%";
/*
** PARSE -- Parse an address
/*
** PARSE -- Parse an address
static char buf[MAXNAME+MAXATOM];
static char *av[MAXATOM+1];
char **avp;
static char buf[MAXNAME+MAXATOM];
static char *av[MAXATOM+1];
char **avp;
bool bslashmode;
int cmntcnt;
int brccnt;
bool bslashmode;
int cmntcnt;
int brccnt;
int nstate;
extern char lower();
int nstate;
extern char lower();
q = buf;
bslashmode = FALSE;
cmntcnt = brccnt = 0;
q = buf;
bslashmode = FALSE;
cmntcnt = brccnt = 0;
case SPACE: /* linear white space */
state = nstate;
case SPACE: /* linear white space */
state = nstate;
break;
case OPER: /* operator */
break;
case OPER: /* operator */
return (NULL);
}
brccnt++;
return (NULL);
}
brccnt++;
if (brccnt == 1)
{
/* we prefer using machine readable name */
if (brccnt == 1)
{
/* we prefer using machine readable name */
printaddr(a, follow)
register ADDRESS *a;
bool follow;
printaddr(a, follow)
register ADDRESS *a;
bool follow;
-static char SccsId[] = "@(#)readcf.c 3.12 %G%";
+static char SccsId[] = "@(#)readcf.c 3.13 %G%";
/*
** READCF -- read control file.
/*
** READCF -- read control file.
margv[i++] = NULL;
/* save the argv */
margv[i++] = NULL;
/* save the argv */
- m->m_argv = (char **) xalloc(sizeof margv[0] * i);
+ m->m_argv = (char **) xalloc((unsigned) (sizeof margv[0] * i));
bmove((char *) margv, (char *) m->m_argv, sizeof margv[0] * i);
}
\f/*
bmove((char *) margv, (char *) m->m_argv, sizeof margv[0] * i);
}
\f/*
** prints rewrite rules.
*/
** prints rewrite rules.
*/
printrules()
{
register struct rewrite *rwp;
printrules()
{
register struct rewrite *rwp;
\f/*
** CRACKOPTS -- crack mailer options
**
\f/*
** CRACKOPTS -- crack mailer options
**
'h', M_HST_UPPER,
'x', M_FULLNAME,
'A', M_ARPAFMT,
'h', M_HST_UPPER,
'x', M_FULLNAME,
'A', M_ARPAFMT,
# include <pwd.h>
# include "sendmail.h"
# include <pwd.h>
# include "sendmail.h"
-static char SccsId[] = "@(#)recipient.c 3.9 %G%";
+static char SccsId[] = "@(#)recipient.c 3.10 %G%";
/*
** SENDTO -- Designate a send list.
/*
** SENDTO -- Designate a send list.
int copyf;
{
register char *p;
int copyf;
{
register char *p;
- register char *q;
- register char c;
- ADDRESS *a;
- bool more;
+ bool more; /* set if more addresses to send to */
- /* more keeps track of what the previous delimiter was */
more = TRUE;
for (p = list; more; )
{
more = TRUE;
for (p = list; more; )
{
+ register char *q;
+ register char c;
+ ADDRESS *a;
+
/* find the end of this address */
while (*p == ' ' || *p == '\t')
p++;
/* find the end of this address */
while (*p == ' ' || *p == '\t')
p++;
register ADDRESS *a;
{
register ADDRESS *q;
register ADDRESS *a;
{
register ADDRESS *q;
register struct mailer *m;
register struct mailer *m;
To = a->q_paddr;
m = Mailer[a->q_mailer];
To = a->q_paddr;
m = Mailer[a->q_mailer];
** If the list is empty, just add it.
*/
** If the list is empty, just add it.
*/
- if (m->m_sendq == NULL)
- {
- m->m_sendq = a;
- }
- else
+ for (pq = &m->m_sendq; (q = *pq) != NULL; pq = &q->q_next)
- ADDRESS *pq;
-
- for (q = m->m_sendq; q != NULL; pq = q, q = q->q_next)
+ if (!ForceMail && sameaddr(q, a, FALSE))
- if (!ForceMail && sameaddr(q, a, FALSE))
- {
- if (Debug)
- printf("(%s in sendq)\n", a->q_paddr);
+ if (Debug)
+ printf("(%s in sendq)\n", a->q_paddr);
- if (Verbose && !bitset(QDONTSEND, a->q_flags))
- message(Arpa_Info, "duplicate supressed");
- return;
- }
+ if (Verbose && !bitset(QDONTSEND, a->q_flags))
+ message(Arpa_Info, "duplicate supressed");
+ return;
-
- /* add address on list */
- q = pq;
- q->q_next = a;
+
+ /* add address on list */
+ *pq = a;
a->q_next = NULL;
if (DontSend)
a->q_flags |= QDONTSEND;
a->q_next = NULL;
if (DontSend)
a->q_flags |= QDONTSEND;
# include <pwd.h>
# include "sendmail.h"
# include <pwd.h>
# include "sendmail.h"
-static char SccsId[] = "@(#)savemail.c 3.16 %G%";
+static char SccsId[] = "@(#)savemail.c 3.17 %G%";
/*
** SAVEMAIL -- Save mail on error
/*
** SAVEMAIL -- Save mail on error
** Saves the letter, by writing or mailing it back to the
** sender, or by putting it in dead.letter in her home
** directory.
** Saves the letter, by writing or mailing it back to the
** sender, or by putting it in dead.letter in her home
** directory.
-**
-** WARNING: the user id is reset to the original user.
syserr("Cannot open %s", Transcript);
(void) expand("$n", buf, &buf[sizeof buf - 1]);
printf("\r\nMessage from %s...\r\n", buf);
syserr("Cannot open %s", Transcript);
(void) expand("$n", buf, &buf[sizeof buf - 1]);
printf("\r\nMessage from %s...\r\n", buf);
- printf("Errors occurred while sending mail, transcript follows:\r\n");
+ printf("Errors occurred while sending mail; transcript follows:\r\n");
while (fgets(buf, sizeof buf, xfile) != NULL && !ferror(stdout))
fputs(buf, stdout);
if (ferror(stdout))
while (fgets(buf, sizeof buf, xfile) != NULL && !ferror(stdout))
fputs(buf, stdout);
if (ferror(stdout))
ExitStat = EX_SOFTWARE;
finis();
}
ExitStat = EX_SOFTWARE;
finis();
}
i = deliver(&to_addr, errhdr);
bmove((char *) &to_addr, (char *) &From, sizeof From);
if (i != 0)
i = deliver(&to_addr, errhdr);
bmove((char *) &to_addr, (char *) &From, sizeof From);
if (i != 0)
+ register struct mailer *m;
{
char buf[MAXLINE];
register FILE *xfile;
{
char buf[MAXLINE];
register FILE *xfile;
if ((xfile = fopen(Transcript, "r")) == NULL)
syserr("Cannot open %s", Transcript);
errno = 0;
if ((xfile = fopen(Transcript, "r")) == NULL)
syserr("Cannot open %s", Transcript);
errno = 0;
+
+ /*
+ ** Output header of error message.
+ */
+
+ if (bitset(M_NEEDDATE, m->m_flags))
+ {
+ (void) expand("$b", buf, &buf[sizeof buf - 1]);
+ fprintf(fp, "Date: %s\n", buf);
+ }
+ if (bitset(M_NEEDFROM, m->m_flags))
+ {
+ (void) expand("$g", buf, &buf[sizeof buf - 1]);
+ fprintf(fp, "From: %s (Mail Delivery Subsystem)\n", buf);
+ }
fprintf(fp, "To: %s\n", To);
fprintf(fp, "Subject: Unable to deliver mail\n");
fprintf(fp, "To: %s\n", To);
fprintf(fp, "Subject: Unable to deliver mail\n");
+
+ /*
+ ** Output transcript of errors
+ */
+
fprintf(fp, "\n ----- Transcript of session follows -----\n");
while (fgets(buf, sizeof buf, xfile) != NULL)
fputs(buf, fp);
fprintf(fp, "\n ----- Transcript of session follows -----\n");
while (fgets(buf, sizeof buf, xfile) != NULL)
fputs(buf, fp);
+
+ /*
+ ** Output text of original message
+ */
+
if (NoReturn)
fprintf(fp, "\n ----- Return message suppressed -----\n\n");
else if (TempFile != NULL)
if (NoReturn)
fprintf(fp, "\n ----- Return message suppressed -----\n\n");
else if (TempFile != NULL)
}
else
fprintf(fp, "\n ----- No message was collected -----\n\n");
}
else
fprintf(fp, "\n ----- No message was collected -----\n\n");
+
+ /*
+ ** Cleanup and exit
+ */
+
(void) fclose(xfile);
if (errno != 0)
syserr("errhdr: I/O error");
(void) fclose(xfile);
if (errno != 0)
syserr("errhdr: I/O error");
/*
** SENDMAIL.H -- Global definitions for sendmail.
**
/*
** SENDMAIL.H -- Global definitions for sendmail.
**
-** @(#)sendmail.h 3.36 %G%
+** @(#)sendmail.h 3.37 %G%
# define M_HST_UPPER 020000 /* preserve host case distinction */
# define M_FULLNAME 040000 /* want Full-Name field */
# define M_HST_UPPER 020000 /* preserve host case distinction */
# define M_FULLNAME 040000 /* want Full-Name field */
-# define M_ARPAFMT (M_NEEDDATE|M_NEEDFROM|M_NEEDDATE)
+# define M_ARPAFMT (M_NEEDDATE|M_NEEDFROM|M_MSGID)
-static char SccsId[] = "@(#)stab.c 3.7 %G%";
+static char SccsId[] = "@(#)stab.c 3.8 %G%";
/*
** STAB -- manage the symbol table
/*
** STAB -- manage the symbol table
extern bool sameword();
register int hfunc;
register char *p;
extern bool sameword();
register int hfunc;
register char *p;
# ifdef DEBUG
if (Debug > 4)
# ifdef DEBUG
if (Debug > 4)
-static char SccsId[] = "@(#)stats.c 3.1 %G%";
+static char SccsId[] = "@(#)stats.c 3.2 %G%";
/*
** POSTSTATS -- post statistics in the statistics file
/*
** POSTSTATS -- post statistics in the statistics file
{
register int fd;
struct statistics stat;
{
register int fd;
struct statistics stat;
+ extern long lseek();
+ extern long time();
- time(&Stat.stat_itime);
+ (void) time(&Stat.stat_itime);
Stat.stat_size = sizeof Stat;
fd = open(sfile, 2);
if (fd < 0)
return;
Stat.stat_size = sizeof Stat;
fd = open(sfile, 2);
if (fd < 0)
return;
- if (read(fd, &stat, sizeof stat) == sizeof stat &&
+ if (read(fd, (char *) &stat, sizeof stat) == sizeof stat &&
stat.stat_size == sizeof stat)
{
/* merge current statistics into statfile */
stat.stat_size == sizeof stat)
{
/* merge current statistics into statfile */
- bmove(&Stat, &stat, sizeof stat);
+ bmove((char *) &Stat, (char *) &stat, sizeof stat);
- lseek(fd, 0L, 0);
- write(fd, &stat, sizeof stat);
- close(fd);
+ (void) lseek(fd, 0L, 0);
+ (void) write(fd, (char *) &stat, sizeof stat);
+ (void) close(fd);
}
\f/*
** KBYTES -- given a number, returns the number of Kbytes.
}
\f/*
** KBYTES -- given a number, returns the number of Kbytes.
-static char SccsId[] = "@(#)SendMail version 3.20 of %G%";
+static char SccsId[] = "@(#)SendMail version 3.21 of %G%";
-char Version[] = "3.20 [%G%]";
+char Version[] = "3.21 [%G%]";