diff options
author | mikeh <mikeh@FreeBSD.org> | 2001-12-18 20:52:09 +0000 |
---|---|---|
committer | mikeh <mikeh@FreeBSD.org> | 2001-12-18 20:52:09 +0000 |
commit | e4034fe298af9398dae0cac602d8a28ec6e51489 (patch) | |
tree | 89731abafbceb13b0e7b78a6e281339c99fbfef9 | |
parent | 1750942f6f64d20cc8853d2d1a60a3daaeeb1110 (diff) | |
download | FreeBSD-src-e4034fe298af9398dae0cac602d8a28ec6e51489.zip FreeBSD-src-e4034fe298af9398dae0cac602d8a28ec6e51489.tar.gz |
Sync with most of NetBSD's changes, including:
*) Sync with 4.4BSD-Lite2
*) Set usecs for utimes()
*) Add 'inc' command and 'autoinc' option that check for new mail
manually and automatically, respectively
*) Use POSIX signal handling and tty semantics
*) Handle long lines correctly when paging messages
*) Add ability to explicitly search 'To:' line
*) Various manpage cleanups
*) Support overriding '~/.mailrc' with $MAILRC
*) Support 'askbcc' and 'asksub' options
*) Fix various bugs
Reviewed by: ru (mail.1)
Obtained from: NetBSD
-rw-r--r-- | usr.bin/mail/aux.c | 6 | ||||
-rw-r--r-- | usr.bin/mail/cmd1.c | 27 | ||||
-rw-r--r-- | usr.bin/mail/cmd3.c | 10 | ||||
-rw-r--r-- | usr.bin/mail/cmdtab.c | 1 | ||||
-rw-r--r-- | usr.bin/mail/collect.c | 43 | ||||
-rw-r--r-- | usr.bin/mail/def.h | 2 | ||||
-rw-r--r-- | usr.bin/mail/extern.h | 23 | ||||
-rw-r--r-- | usr.bin/mail/fio.c | 78 | ||||
-rw-r--r-- | usr.bin/mail/head.c | 2 | ||||
-rw-r--r-- | usr.bin/mail/lex.c | 66 | ||||
-rw-r--r-- | usr.bin/mail/list.c | 50 | ||||
-rw-r--r-- | usr.bin/mail/mail.1 | 106 | ||||
-rw-r--r-- | usr.bin/mail/main.c | 18 | ||||
-rw-r--r-- | usr.bin/mail/names.c | 10 | ||||
-rw-r--r-- | usr.bin/mail/popen.c | 52 | ||||
-rw-r--r-- | usr.bin/mail/quit.c | 4 | ||||
-rw-r--r-- | usr.bin/mail/send.c | 24 | ||||
-rw-r--r-- | usr.bin/mail/tty.c | 74 |
18 files changed, 439 insertions, 157 deletions
diff --git a/usr.bin/mail/aux.c b/usr.bin/mail/aux.c index d8c32b3..4db5b85 100644 --- a/usr.bin/mail/aux.c +++ b/usr.bin/mail/aux.c @@ -345,9 +345,9 @@ alter(name) if (stat(name, &sb)) return; - tv[0].tv_sec = time((time_t *)0) + 1; - tv[1].tv_sec = sb.st_mtime; - tv[0].tv_usec = tv[1].tv_usec = 0; + (void)gettimeofday(&tv[0], (struct timezone *)NULL); + tv[0].tv_sec++; + TIMESPEC_TO_TIMEVAL(&tv[1], &sb.st_mtimespec); (void)utimes(name, tv); } diff --git a/usr.bin/mail/cmd1.c b/usr.bin/mail/cmd1.c index aa5ad53..8c51077 100644 --- a/usr.bin/mail/cmd1.c +++ b/usr.bin/mail/cmd1.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)cmd1.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)cmd1.c 8.2 (Berkeley) 4/20/95"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -111,7 +111,7 @@ scroll(arg) case 0: case '+': s++; - if (s * size > msgCount) { + if (s * size >= msgCount) { printf("On last screenful of messages\n"); return (0); } @@ -460,3 +460,26 @@ folders() (void)run_command(cmd, 0, -1, -1, dirname, NULL, NULL); return (0); } + +/* + * Update the mail file with any new messages that have + * come in since we started reading mail. + */ +int +inc(v) + void *v; +{ + int nmsg, mdot; + + nmsg = incfile(); + + if (nmsg == 0) + printf("No new mail.\n"); + else if (nmsg > 0) { + mdot = newfileinfo(msgCount - nmsg); + dot = &message[mdot - 1]; + } else + printf("\"inc\" command failed...\n"); + + return (0); +} diff --git a/usr.bin/mail/cmd3.c b/usr.bin/mail/cmd3.c index 4ead961..8d21dd4 100644 --- a/usr.bin/mail/cmd3.c +++ b/usr.bin/mail/cmd3.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)cmd3.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)cmd3.c 8.2 (Berkeley) 4/20/95"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -357,7 +357,7 @@ rexit(e) { if (sourcing) return (1); - exit(e); + exit(0); /*NOTREACHED*/ } @@ -423,7 +423,9 @@ unset(arglist) errs = 0; for (ap = arglist; *ap != NULL; ap++) { if ((vp2 = lookup(*ap)) == NULL) { - if (!sourcing) { + if (getenv(*ap)) + unsetenv(*ap); + else if (!sourcing) { printf("\"%s\": undefined variable\n", *ap); errs++; } @@ -552,7 +554,7 @@ file(argv) { if (argv[0] == NULL) { - newfileinfo(); + newfileinfo(0); return (0); } if (setfile(*argv) < 0) diff --git a/usr.bin/mail/cmdtab.c b/usr.bin/mail/cmdtab.c index d375b88..7c49205 100644 --- a/usr.bin/mail/cmdtab.c +++ b/usr.bin/mail/cmdtab.c @@ -120,5 +120,6 @@ const struct cmd cmdtab[] = { { "core", core, M|NOLIST, 0, 0 }, { "#", null, M|NOLIST, 0, 0 }, { "clobber", clobber, M|RAWLIST, 0, 1 }, + { "inc", inc, T|NOLIST, 0, 0 }, { 0, 0, 0, 0, 0 } }; diff --git a/usr.bin/mail/collect.c b/usr.bin/mail/collect.c index 12fac37..4c42c90 100644 --- a/usr.bin/mail/collect.c +++ b/usr.bin/mail/collect.c @@ -80,14 +80,19 @@ collect(hp, printheaders) FILE *fbuf; int lc, cc, escape, eofcount, fd, c, t; char linebuf[LINESIZE], tempname[PATHSIZE], *cp, getsub; - int omask; + sigset_t nset; + int longline, lastlong, rc; /* So we don't make 2 or more lines + out of a long input line. */ collf = NULL; /* * Start catching signals from here, but we're still die on interrupts * until we're in the main loop. */ - omask = sigblock(sigmask(SIGINT) | sigmask(SIGHUP)); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, SIGINT); + (void)sigaddset(&nset, SIGHUP); + (void)sigprocmask(SIG_BLOCK, &nset, NULL); if ((saveint = signal(SIGINT, SIG_IGN)) != SIG_IGN) (void)signal(SIGINT, collint); if ((savehup = signal(SIGHUP, SIG_IGN)) != SIG_IGN) @@ -99,7 +104,7 @@ collect(hp, printheaders) (void)rm(tempname); goto err; } - sigsetmask(omask & ~(sigmask(SIGINT) | sigmask(SIGHUP))); + (void)sigprocmask(SIG_UNBLOCK, &nset, NULL); noreset++; (void)snprintf(tempname, sizeof(tempname), @@ -131,6 +136,8 @@ collect(hp, printheaders) escape = ESCAPE; eofcount = 0; hadintr = 0; + lastlong = 0; + longline = 0; if (!setjmp(colljmp)) { if (getsub) @@ -163,14 +170,17 @@ cont: } break; } + lastlong = longline; + longline = c == LINESIZE - 1; eofcount = 0; hadintr = 0; if (linebuf[0] == '.' && linebuf[1] == '\0' && - value("interactive") != NULL && + value("interactive") != NULL && !lastlong && (value("dot") != NULL || value("ignoreeof") != NULL)) break; - if (linebuf[0] != escape || value("interactive") == NULL) { - if (putline(collf, linebuf) < 0) + if (linebuf[0] != escape || value("interactive") == NULL || + lastlong) { + if (putline(collf, linebuf, !longline) < 0) goto err; continue; } @@ -182,7 +192,7 @@ cont: * Otherwise, it's an error. */ if (c == escape) { - if (putline(collf, &linebuf[1]) < 0) + if (putline(collf, &linebuf[1], !longline) < 0) goto err; else break; @@ -298,9 +308,11 @@ cont: (void)fflush(stdout); lc = 0; cc = 0; - while (readline(fbuf, linebuf, LINESIZE) >= 0) { - lc++; - if ((t = putline(collf, linebuf)) < 0) { + while ((rc = readline(fbuf, linebuf, LINESIZE)) >= 0) { + if (rc != LINESIZE - 1) + lc++; + if ((t = putline(collf, linebuf, + rc != LINESIZE - 1)) < 0) { (void)Fclose(fbuf); goto err; } @@ -388,13 +400,13 @@ out: if (collf != NULL) rewind(collf); noreset--; - (void)sigblock(sigmask(SIGINT) | sigmask(SIGHUP)); + (void)sigprocmask(SIG_BLOCK, &nset, NULL); (void)signal(SIGINT, saveint); (void)signal(SIGHUP, savehup); (void)signal(SIGTSTP, savetstp); (void)signal(SIGTTOU, savettou); (void)signal(SIGTTIN, savettin); - (void)sigsetmask(omask); + (void)sigprocmask(SIG_UNBLOCK, &nset, NULL); return (collf); } @@ -576,10 +588,13 @@ collstop(s) int s; { sig_t old_action = signal(s, SIG_DFL); + sigset_t nset; - (void)sigsetmask(sigblock(0) & ~sigmask(s)); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, s); + (void)sigprocmask(SIG_UNBLOCK, &nset, NULL); (void)kill(0, s); - (void)sigblock(sigmask(s)); + (void)sigprocmask(SIG_BLOCK, &nset, NULL); (void)signal(s, old_action); if (colljmp_p) { colljmp_p = 0; diff --git a/usr.bin/mail/def.h b/usr.bin/mail/def.h index 8b5e4ee..3ef4ed0 100644 --- a/usr.bin/mail/def.h +++ b/usr.bin/mail/def.h @@ -30,7 +30,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * @(#)def.h 8.2 (Berkeley) 3/21/94 + * @(#)def.h 8.4 (Berkeley) 4/20/95 * * $FreeBSD$ */ diff --git a/usr.bin/mail/extern.h b/usr.bin/mail/extern.h index cbd622c..f012962 100644 --- a/usr.bin/mail/extern.h +++ b/usr.bin/mail/extern.h @@ -30,7 +30,7 @@ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF * SUCH DAMAGE. * - * @(#)extern.h 8.1 (Berkeley) 6/6/93 + * @(#)extern.h 8.2 (Berkeley) 4/20/95 * * $FreeBSD$ */ @@ -147,6 +147,8 @@ int igcomp __P((const void *, const void *)); int igfield __P((char *[])); int ignore1 __P((char *[], struct ignoretab *, const char *)); int igshow __P((struct ignoretab *, const char *)); +int inc __P((void *)); +int incfile __P((void)); void intr __P((int)); int isdate __P((char [])); int isdir __P((char [])); @@ -163,7 +165,7 @@ struct var * int mail __P((struct name *, struct name *, struct name *, struct name *, char *, char *)); void mail1 __P((struct header *, int)); -void makemessage __P((FILE *)); +void makemessage __P((FILE *, int)); void mark __P((int)); int markall __P((char [], int)); int matchsender __P((char *, int)); @@ -175,19 +177,19 @@ void mespipe __P((FILE *, char [])); int messize __P((int *)); int metamess __P((int, int)); int more __P((int *)); -int newfileinfo __P((void)); +int newfileinfo __P((int)); int next __P((int *)); int null __P((int)); void parse __P((char [], struct headline *, char [])); int pcmdlist __P((void)); int pdot __P((void)); -void prepare_child __P((int, int, int)); +void prepare_child __P((sigset_t *, int, int)); int preserve __P((int *)); void prettyprint __P((struct name *)); void printgroup __P((char [])); void printhead __P((int)); int puthead __P((struct header *, FILE *, int)); -int putline __P((FILE *, char *)); +int putline __P((FILE *, char *, int)); int pversion __P((int)); void quit __P((void)); int quitcmd __P((void)); @@ -199,7 +201,8 @@ int respond __P((int *)); int retfield __P((char *[])); int rexit __P((int)); int rm __P((char *)); -int run_command __P((char *, int, int, int, char *, char *, char *)); +int run_command __P((char *, sigset_t *, int, int, char *, char *, + char *)); int save __P((char [])); int save1 __P((char [], int, const char *, struct ignoretab *)); void savedeadletter __P((FILE *)); @@ -211,12 +214,13 @@ void scaninit __P((void)); int schdir __P((char **)); int screensize __P((void)); int scroll __P((char [])); -int sendmessage __P((struct message *, FILE *, struct ignoretab *, char *)); +int sendmessage __P((struct message *, FILE *, struct ignoretab *, + char *)); int sendmail __P((char *)); int set __P((char **)); int setfile __P((char *)); void setmsize __P((int)); -void setptr __P((FILE *)); +void setptr __P((FILE *, off_t)); void setscreensize __P((void)); int shell __P((char *)); void sigchild __P((int)); @@ -224,7 +228,8 @@ void sort __P((char **)); int source __P((char **)); void spreserve __P((void)); void sreset __P((void)); -int start_command __P((char *, int, int, int, char *, char *, char *)); +int start_command __P((char *, sigset_t *, int, int, char *, char *, + char *)); void statusput __P((struct message *, FILE *, char *)); void stop __P((int)); int stouch __P((int [])); diff --git a/usr.bin/mail/fio.c b/usr.bin/mail/fio.c index c9dcb94..0c78e3e 100644 --- a/usr.bin/mail/fio.c +++ b/usr.bin/mail/fio.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)fio.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)fio.c 8.2 (Berkeley) 4/20/95"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -60,16 +60,17 @@ extern int wait_status; * Set up the input pointers while copying the mail file into /tmp. */ void -setptr(ibuf) +setptr(ibuf, offset) FILE *ibuf; + off_t offset; { int c, count; char *cp, *cp2; struct message this; FILE *mestmp; - off_t offset; int maybe, inhead; char linebuf[LINESIZE], pathbuf[PATHSIZE]; + int omsgCount; /* Get temporary file. */ (void)snprintf(pathbuf, sizeof(pathbuf), "%s/mail.XXXXXXXXXX", tmpdir); @@ -77,10 +78,23 @@ setptr(ibuf) err(1, "can't open %s", pathbuf); (void)rm(pathbuf); - msgCount = 0; + if (offset == 0) { + msgCount = 0; + } else { + /* Seek into the file to get to the new messages */ + (void)fseek(ibuf, offset, SEEK_SET); + /* + * We need to make "offset" a pointer to the end of + * the temp file that has the copy of the mail file. + * If any messages have been edited, this will be + * different from the offset into the mail file. + */ + (void)fseek(otf, 0L, SEEK_END); + offset = ftell(otf); + } + omsgCount = msgCount; maybe = 1; inhead = 0; - offset = 0; this.m_flag = MUSED|MNEW; this.m_size = 0; this.m_lines = 0; @@ -90,7 +104,7 @@ setptr(ibuf) if (fgets(linebuf, sizeof(linebuf), ibuf) == NULL) { if (append(&this, mestmp)) errx(1, "temporary file"); - makemessage(mestmp); + makemessage(mestmp, omsgCount); return; } count = strlen(linebuf); @@ -150,21 +164,25 @@ setptr(ibuf) /* * Drop the passed line onto the passed output buffer. * If a write error occurs, return -1, else the count of - * characters written, including the newline. + * characters written, including the newline if requested. */ int -putline(obuf, linebuf) +putline(obuf, linebuf, outlf) FILE *obuf; char *linebuf; + int outlf; { int c; c = strlen(linebuf); (void)fwrite(linebuf, sizeof(*linebuf), c, obuf); - fprintf(obuf, "\n"); + if (outlf) { + fprintf(obuf, "\n"); + c++; + } if (ferror(obuf)) return (-1); - return (c + 1); + return (c); } /* @@ -212,20 +230,27 @@ setinput(mp) * a dynamically allocated message structure. */ void -makemessage(f) +makemessage(f, omsgCount) FILE *f; + int omsgCount; { - int size = (msgCount + 1) * sizeof(struct message); - - if (message != 0) - (void)free(message); - if ((message = malloc((unsigned)size)) == NULL) - err(1, "Out of memory"); - dot = message; - size -= sizeof(struct message); + size_t size; + struct message *nmessage; + + size = (msgCount + 1) * sizeof(struct message); + nmessage = (struct message *)realloc(message, size); + if (nmessage == NULL) + errx(1, "Insufficient memory for %d messages\n", + msgCount); + if (omsgCount == 0 || message == NULL) + dot = nmessage; + else + dot = nmessage + (dot - message); + message = nmessage; + size -= (omsgCount + 1) * sizeof(struct message); (void)fflush(f); (void)lseek(fileno(f), (off_t)sizeof(*message), 0); - if (read(fileno(f), (char *)message, size) != size) + if (read(fileno(f), (char *)&message[omsgCount], size) != size) errx(1, "Message temporary file corrupted"); message[msgCount].m_size = 0; message[msgCount].m_lines = 0; @@ -263,7 +288,7 @@ rm(name) } static int sigdepth; /* depth of holdsigs() */ -static int omask; +static sigset_t nset, oset; /* * Hold signals SIGHUP, SIGINT, and SIGQUIT. */ @@ -271,8 +296,13 @@ void holdsigs() { - if (sigdepth++ == 0) - omask = sigblock(sigmask(SIGHUP)|sigmask(SIGINT)|sigmask(SIGQUIT)); + if (sigdepth++ == 0) { + (void)sigemptyset(&nset); + (void)sigaddset(&nset, SIGHUP); + (void)sigaddset(&nset, SIGINT); + (void)sigaddset(&nset, SIGQUIT); + (void)sigprocmask(SIG_BLOCK, &nset, &oset); + } } /* @@ -283,7 +313,7 @@ relsesigs() { if (--sigdepth == 0) - (void)sigsetmask(omask); + (void)sigprocmask(SIG_SETMASK, &oset, NULL); } /* diff --git a/usr.bin/mail/head.c b/usr.bin/mail/head.c index 0f214d7..806ab6d 100644 --- a/usr.bin/mail/head.c +++ b/usr.bin/mail/head.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)head.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)head.c 8.2 (Berkeley) 4/20/95"; #endif static const char rcsid[] = "$FreeBSD$"; diff --git a/usr.bin/mail/lex.c b/usr.bin/mail/lex.c index c0f2604..c7f674c 100644 --- a/usr.bin/mail/lex.c +++ b/usr.bin/mail/lex.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)lex.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)lex.c 8.2 (Berkeley) 4/20/95"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -68,7 +68,7 @@ setfile(name) FILE *ibuf; int i, fd; struct stat stb; - char isedit = *name != '%'; + char isedit = *name != '%' || getuserid(myname) != getuid(); char *who = name[1] ? name + 1 : myname; char tempname[PATHSIZE]; static int shudclob; @@ -136,8 +136,14 @@ setfile(name) err(1, "%s", tempname); (void)fcntl(fileno(itf), F_SETFD, 1); (void)rm(tempname); - setptr(ibuf); + setptr(ibuf, 0); setmsize(msgCount); + /* + * New mail may have arrived while we were reading + * the mail file, so reset mailsize to be where + * we really are in the file... + */ + mailsize = ftell(ibuf); (void)Fclose(ibuf); relsesigs(); sawcom = 0; @@ -149,6 +155,36 @@ nomail: return (0); } +/* + * Incorporate any new mail that has arrived since we first + * started reading mail. + */ +int +incfile() +{ + int newsize; + int omsgCount = msgCount; + FILE *ibuf; + + ibuf = Fopen(mailname, "r"); + if (ibuf == NULL) + return (-1); + holdsigs(); + newsize = fsize(ibuf); + if (newsize == 0) + return (-1); /* mail box is now empty??? */ + if (newsize < mailsize) + return (-1); /* mail box has shrunk??? */ + if (newsize == mailsize) + return (0); /* no new mail */ + setptr(ibuf, mailsize); + setmsize(msgCount); + mailsize = ftell(ibuf); + (void)Fclose(ibuf); + relsesigs(); + return (msgCount - omsgCount); +} + int *msgvec; int reset_on_stop; /* do a reset() if stopped */ @@ -178,6 +214,8 @@ commands() * string space, and flush the output. */ if (!sourcing && value("interactive") != NULL) { + if ((value("autoinc") != NULL) && (incfile() > 0)) + printf("New mail has arrived.\n"); reset_on_stop = 1; printf("%s", prompt); } @@ -411,6 +449,8 @@ out: unstack(); return (0); } + if (com == NULL) + return (0); if (value("autoprint") != NULL && com->c_argtype & P) if ((dot->m_flag & MDELETED) == 0) { muvec[0] = dot - &message[0] + 1; @@ -431,7 +471,7 @@ setmsize(sz) int sz; { - if (msgvec != 0) + if (msgvec != NULL) (void)free(msgvec); msgvec = calloc((unsigned)(sz + 1), sizeof(*msgvec)); } @@ -523,10 +563,13 @@ stop(s) int s; { sig_t old_action = signal(s, SIG_DFL); + sigset_t nset; - (void)sigsetmask(sigblock(0) & ~sigmask(s)); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, s); + (void)sigprocmask(SIG_UNBLOCK, &nset, NULL); (void)kill(0, s); - (void)sigblock(sigmask(s)); + (void)sigprocmask(SIG_BLOCK, &nset, NULL); (void)signal(s, old_action); if (reset_on_stop) { reset_on_stop = 0; @@ -556,7 +599,7 @@ announce() { int vec[2], mdot; - mdot = newfileinfo(); + mdot = newfileinfo(0); vec[0] = mdot; vec[1] = 0; dot = &message[mdot - 1]; @@ -572,23 +615,24 @@ announce() * Return a likely place to set dot. */ int -newfileinfo() +newfileinfo(omsgCount) + int omsgCount; { struct message *mp; int u, n, mdot, d, s; char fname[PATHSIZE+1], zname[PATHSIZE+1], *ename; - for (mp = &message[0]; mp < &message[msgCount]; mp++) + for (mp = &message[omsgCount]; mp < &message[msgCount]; mp++) if (mp->m_flag & MNEW) break; if (mp >= &message[msgCount]) - for (mp = &message[0]; mp < &message[msgCount]; mp++) + for (mp = &message[omsgCount]; mp < &message[msgCount]; mp++) if ((mp->m_flag & MREAD) == 0) break; if (mp < &message[msgCount]) mdot = mp - &message[0] + 1; else - mdot = 1; + mdot = omsgCount + 1; s = d = 0; for (mp = &message[0], n = 0, u = 0; mp < &message[msgCount]; mp++) { if (mp->m_flag & MNEW) diff --git a/usr.bin/mail/list.c b/usr.bin/mail/list.c index 04b1586..1dbc587 100644 --- a/usr.bin/mail/list.c +++ b/usr.bin/mail/list.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)list.c 8.2 (Berkeley) 4/19/94"; +static char sccsid[] = "@(#)list.c 8.4 (Berkeley) 5/1/95"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -687,6 +687,49 @@ matchsender(str, mesg) } /* + * See if the passed name received the passed message number. Return true + * if so. + */ + +static char *to_fields[] = { "to", "cc", "bcc", NULL }; + +int +matchto(str, mesg) + char *str; + int mesg; +{ + struct message *mp; + char *cp, *cp2, *backup, **to; + + str++; + + /* null string matches nothing instead of everything */ + if (*str == '\0') + return (0); + + mp = &message[mesg - 1]; + + for (to = to_fields; *to != NULL; to++) { + cp = str; + cp2 = hfield(*to, mp); + if (cp2 != NULL) { + backup = cp2; + while (*cp2 != '\0') { + if (*cp == '\0') + return (1); + if (toupper(*cp++) != toupper(*cp2++)) { + cp2 = ++backup; + cp = str; + } + } + if (*cp == '\0') + return (1); + } + } + return (0); +} + +/* * See if the given string matches inside the subject field of the * given message. For the purpose of the scan, we ignore case differences. * If it does, return true. The string search argument is assumed to @@ -715,8 +758,11 @@ matchsubj(str, mesg) */ if (value("searchheaders") && (cp = strchr(str, ':')) != NULL) { + /* Check for special case "/To:" */ + if (strncasecmp(str, "To:", 3) == 0) + return (matchto(cp, mesg)); *cp++ = '\0'; - cp2 = hfield(str, mp); + cp2 = hfield(*str != '\0' ? str : "subject", mp); cp[-1] = ':'; str = cp; } else { diff --git a/usr.bin/mail/mail.1 b/usr.bin/mail/mail.1 index e38be25..0b68435 100644 --- a/usr.bin/mail/mail.1 +++ b/usr.bin/mail/mail.1 @@ -29,14 +29,15 @@ .\" OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF .\" SUCH DAMAGE. .\" -.\" @(#)mail.1 8.2 (Berkeley) 12/30/93 +.\" @(#)mail.1 8.8 (Berkeley) 4/28/95 .\" $FreeBSD$ .\" -.Dd December 30, 1993 +.Dd April 28, 1995 .Dt MAIL 1 .Os .Sh NAME -.Nm mail +.Nm mail , +.Nm Mail .Nd send and receive mail .Sh SYNOPSIS .Nm @@ -174,7 +175,7 @@ and moving backwards and forwards, and simple numbers. .Pp -.Ss Disposing of mail. +.Ss Disposing of mail After examining a message you can .Ic delete .Pq Ic d @@ -219,7 +220,7 @@ which prints the first few lines of a message could be used in .Dq Li top \&* to print the first few lines of all messages. .Pp -.Ss Replying to or originating mail. +.Ss Replying to or originating mail You can use the .Ic reply command to @@ -245,7 +246,7 @@ message or to a shell to run some commands. (These options are given in the summary below.) .Pp -.Ss Ending a mail processing session. +.Ss Ending a mail processing session You can end a .Nm session with the @@ -260,7 +261,7 @@ Unexamined messages go back to the post office. .Fl f option above). .Pp -.Ss Personal and system wide distribution lists. +.Ss Personal and system wide distribution lists It is also possible to create a personal distribution lists so that, for instance, you can send mail to .Dq Li cohorts @@ -293,7 +294,7 @@ System wide are not expanded when the mail is sent, but any reply returned to the machine will have the system wide alias expanded as all mail goes through -.Xr sendmail . +.Xr sendmail 8 . .Pp .Ss Network mail (ARPA, UUCP, Berknet) See @@ -392,7 +393,7 @@ listed on the list. If the .Ic alternates -command is given with no argument, the current set of alternate +command is given with no argument, the current set of alternative names is displayed. .It Ic chdir .Pq Ic c @@ -505,13 +506,17 @@ If .Ic ignore is executed with no arguments, it lists the current set of ignored fields. +.It Ic inc +Incorporate any new messages that have arrived while mail +is being read. +The new messages are added to the end of the message list, +and the current message is reset to be the first new mail message. +This does not renumber the existing message list, nor does +does it cause any changes made so far to be saved. .It Ic mail .Pq Ic m Takes as argument login names and distribution group names and sends mail to those people. -.It Ic more -.Pq Ic \&mo -Takes a list of messages and invokes the pager on that list. .It Ic mbox Indicate that a list of messages be sent to .Ic mbox @@ -522,10 +527,12 @@ action for messages if you do have the .Ic hold option set. +.It Ic more +.Pq Ic \&mo +Takes a list of messages and invokes the pager on that list. .It Ic next -.Pq Ic n +.Ic ( n , like -( .Ic \&+ or .Tn CR ) @@ -572,14 +579,14 @@ A synonym for .Ic reply . .It Ic retain Add the list of header fields named to the -.Ar retained list -Only the header fields in the retain list +.Em "retained list" . +Only the header fields in the retained list are shown on your terminal when you print a message. All other header fields are suppressed. The -.Ic Type +.Ic type and -.Ic Print +.Ic print commands can be used to print a message in its entirety. If .Ic retain @@ -788,11 +795,11 @@ Cause the named string to become the current subject field. .It Ic \&~\&t Ns Ar name ... Add the given names to the direct recipient list. .It Ic \&~\&v -Invoke an alternate editor (defined by the +Invoke an alternative editor (defined by the .Ev VISUAL option) on the message collected so far. -Usually, the alternate editor will be a +Usually, the alternative editor will be a screen editor. After you quit the editor, you may resume appending text to the end of your message. @@ -838,17 +845,28 @@ to be appended to the end rather than prepended. This should always be set (preferably in one of the system-wide .Pa mail.rc files). -.It Ar ask +.It Ar ask , asksub Causes .Nm to prompt you for the subject of each message you send. If you respond with simply a newline, no subject field will be sent. +.It Ar askbcc +Causes you to be prompted for additional blind carbon copy recipients at the +end of each message. +Responding with a newline indicates your +satisfaction with the current list. .It Ar askcc Causes you to be prompted for additional carbon copy recipients at the end of each message. Responding with a newline indicates your satisfaction with the current list. +.It Ar autoinc +Causes new mail to be automatically incorporated when it arrives. +Setting this is similar to issuing the +.Ic inc +command at each prompt, except that the current message is not +reset when new mail arrives. .It Ar autoprint Causes the .Ic delete @@ -921,9 +939,38 @@ commands. .It Ar quiet Suppresses the printing of the version when first invoked. .It Ar searchheaders -If this option is set, then a message-list specifier in the form ``/x:y'' -will expand to all messages containing the substring ``y'' in the header -field ``x''. The string search is case insensitive. +If this option is set, then a message-list specifier in the form +.Dq Li / Ns Ar x Ns Li : Ns Ar y +will expand to all messages containing the substring +.Dq Ar y +in the header field +.Dq Ar x . +The string search is case insensitive. +If +.Dq Ar x +is ommitted, it will default to the +.Dq Li Subject +header field. +The form +.Dq Li /to: Ns Ar y +is a special case, and will expand +to all messages containing the substring +.Dq Ar y +in the +.Dq Li To , +.Dq Li Cc +or +.Dq Li Bcc +header fields. +The check for +.Qq Li "to" +is case sensitive, so that +.Dq Li /to: Ns Ar y +can be used to limit the search for +.Dq Ar y +to just the +.Dq Li To: +field. .It Ar verbose Setting the option .Ar verbose @@ -963,7 +1010,7 @@ If set, will be used to initialize the Reply-To field for outgoing messages. .It Ev SHELL Pathname of the shell to use in the -.Ic !\& +.Ic \&! command and the .Ic \&~! escape. @@ -1040,6 +1087,9 @@ Post office. User's old mail. .It Pa ~/.mailrc File giving initial mail commands. +This can be overridden by setting the +.Ev MAILRC +environment variable. .It Pa /tmp/R* Temporary files. .It Pa /usr/share/misc/mail.*help @@ -1081,3 +1131,9 @@ Usually, is just a link to .Nm Mail , which can be confusing. +.Pp +The name of the +.Ic alternates +list is incorrect English (it should be +.Dq alternatives ) , +but is retained for compatibility. diff --git a/usr.bin/mail/main.c b/usr.bin/mail/main.c index 3707903..a95c705 100644 --- a/usr.bin/mail/main.c +++ b/usr.bin/mail/main.c @@ -39,7 +39,7 @@ static char copyright[] = #ifndef lint #if 0 -static char sccsid[] = "@(#)main.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)main.c 8.2 (Berkeley) 4/20/95"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -67,7 +67,7 @@ main(argc, argv) int i; struct name *to, *cc, *bcc, *smopts; char *subject, *replyto; - char *ef; + char *ef, *rc; char nosrc = 0; sig_t prevint; @@ -228,7 +228,9 @@ Usage: %s [-EiInv] [-s subject] [-c cc-addr] [-b bcc-addr] to-addr ...\n\ * Expand returns a savestr, but load only uses the file name * for fopen, so it's safe to do this. */ - load(expand("~/.mailrc")); + if ((rc = getenv("MAILRC")) == NULL) + rc = "~/.mailrc"; + load(expand(rc)); replyto = value("REPLYTO"); if (!rcvmode) { @@ -290,16 +292,16 @@ hdrstop(signo) void setscreensize() { + struct termios tbuf; struct winsize ws; - struct termios tio; - speed_t speed = 0; + speed_t speed; if (ioctl(1, TIOCGWINSZ, (char *)&ws) < 0) ws.ws_col = ws.ws_row = 0; - if (tcgetattr(1, &tio) != -1) - speed = cfgetospeed(&tio); - if (speed <= 0) + if (tcgetattr(1, &tbuf) < 0) speed = B9600; + else + speed = cfgetospeed(&tbuf); if (speed < B1200) screenheight = 9; else if (speed == B1200) diff --git a/usr.bin/mail/names.c b/usr.bin/mail/names.c index 8d4bb42..976bfa4 100644 --- a/usr.bin/mail/names.c +++ b/usr.bin/mail/names.c @@ -296,6 +296,7 @@ outof(names, fo, hp) if (ispipe) { int pid; char *sh; + sigset_t nset; /* * XXX @@ -306,9 +307,12 @@ outof(names, fo, hp) */ if ((sh = value("SHELL")) == NULL) sh = _PATH_CSHELL; - pid = start_command(sh, - sigmask(SIGHUP)|sigmask(SIGINT)|sigmask(SIGQUIT), - image, -1, "-c", fname, NULL); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, SIGHUP); + (void)sigaddset(&nset, SIGINT); + (void)sigaddset(&nset, SIGQUIT); + pid = start_command(sh, &nset, image, -1, "-c", fname, + NULL); if (pid < 0) { senderr++; goto cant; diff --git a/usr.bin/mail/popen.c b/usr.bin/mail/popen.c index e8ee364..bbb2c11 100644 --- a/usr.bin/mail/popen.c +++ b/usr.bin/mail/popen.c @@ -110,6 +110,7 @@ Popen(cmd, mode) int p[2]; int myside, hisside, fd0, fd1; int pid; + sigset_t nset; FILE *fp; if (pipe(p) < 0) @@ -125,7 +126,8 @@ Popen(cmd, mode) hisside = fd0 = p[READ]; fd1 = -1; } - if ((pid = start_command(cmd, 0, fd0, fd1, NULL, NULL, NULL)) < 0) { + (void)sigemptyset(&nset); + if ((pid = start_command(cmd, &nset, fd0, fd1, NULL, NULL, NULL)) < 0) { (void)close(p[READ]); (void)close(p[WRITE]); return (NULL); @@ -141,14 +143,17 @@ Pclose(ptr) FILE *ptr; { int i; - int omask; + sigset_t nset, oset; i = file_pid(ptr); unregister_file(ptr); (void)fclose(ptr); - omask = sigblock(sigmask(SIGINT)|sigmask(SIGHUP)); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, SIGINT); + (void)sigaddset(&nset, SIGHUP); + (void)sigprocmask(SIG_BLOCK, &nset, &oset); i = wait_child(i); - (void)sigsetmask(omask); + (void)sigprocmask(SIG_SETMASK, &oset, NULL); return (i); } @@ -219,7 +224,8 @@ file_pid(fp) int run_command(cmd, mask, infd, outfd, a0, a1, a2) char *cmd; - int mask, infd, outfd; + sigset_t *mask; + int infd, outfd; char *a0, *a1, *a2; { int pid; @@ -233,7 +239,8 @@ run_command(cmd, mask, infd, outfd, a0, a1, a2) int start_command(cmd, mask, infd, outfd, a0, a1, a2) char *cmd; - int mask, infd, outfd; + sigset_t *mask; + int infd, outfd; char *a0, *a1, *a2; { int pid; @@ -259,10 +266,12 @@ start_command(cmd, mask, infd, outfd, a0, a1, a2) } void -prepare_child(mask, infd, outfd) - int mask, infd, outfd; +prepare_child(nset, infd, outfd) + sigset_t *nset; + int infd, outfd; { int i; + sigset_t eset; /* * All file descriptors other than 0, 1, and 2 are supposed to be @@ -272,12 +281,13 @@ prepare_child(mask, infd, outfd) dup2(infd, 0); if (outfd >= 0) dup2(outfd, 1); - for (i = 1; i <= NSIG; i++) - if (mask & sigmask(i)) + for (i = 1; i < NSIG; i++) + if (nset != NULL && sigismember(nset, i)) (void)signal(i, SIG_IGN); - if ((mask & sigmask(SIGINT)) == 0) + if (nset == NULL || !sigismember(nset, SIGINT)) (void)signal(SIGINT, SIG_DFL); - (void)sigsetmask(0); + (void)sigemptyset(&eset); + (void)sigprocmask(SIG_SETMASK, &eset, NULL); } int @@ -353,14 +363,18 @@ int wait_child(pid) int pid; { - int mask = sigblock(sigmask(SIGCHLD)); + sigset_t nset, oset; struct child *cp = findchild(pid); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, SIGCHLD); + (void)sigprocmask(SIG_BLOCK, &nset, &oset); + while (!cp->done) - sigpause(mask); + (void)sigsuspend(&oset); wait_status = cp->status; delchild(cp); - (void)sigsetmask(mask); + (void)sigprocmask(SIG_SETMASK, &oset, NULL); return ((WIFEXITED(wait_status) && WEXITSTATUS(wait_status)) ? -1 : 0); } @@ -371,12 +385,16 @@ void free_child(pid) int pid; { - int mask = sigblock(sigmask(SIGCHLD)); + sigset_t nset, oset; struct child *cp = findchild(pid); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, SIGCHLD); + (void)sigprocmask(SIG_BLOCK, &nset, &oset); + if (cp->done) delchild(cp); else cp->free = 1; - (void)sigsetmask(mask); + (void)sigprocmask(SIG_SETMASK, &oset, NULL); } diff --git a/usr.bin/mail/quit.c b/usr.bin/mail/quit.c index 7831bb3..ea92dab 100644 --- a/usr.bin/mail/quit.c +++ b/usr.bin/mail/quit.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)quit.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)quit.c 8.2 (Berkeley) 4/28/95"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -274,8 +274,8 @@ quit() c = getc(ibuf); } (void)Fclose(ibuf); - (void)fflush(obuf); } + (void)fflush(obuf); trunc(obuf); if (ferror(obuf)) { warn("%s", mbox); diff --git a/usr.bin/mail/send.c b/usr.bin/mail/send.c index 42dd65e..58f029a 100644 --- a/usr.bin/mail/send.c +++ b/usr.bin/mail/send.c @@ -315,9 +315,12 @@ mail1(hp, printheaders) if ((mtf = collect(hp, printheaders)) == NULL) return; if (value("interactive") != NULL) { - if (value("askcc") != NULL) - grabh(hp, GCC); - else { + if (value("askcc") != NULL || value("askbcc") != NULL) { + if (value("askcc") != NULL) + grabh(hp, GCC); + if (value("askbcc") != NULL) + grabh(hp, GBCC); + } else { printf("EOT\n"); (void)fflush(stdout); } @@ -380,9 +383,15 @@ mail1(hp, printheaders) goto out; } if (pid == 0) { - prepare_child(sigmask(SIGHUP)|sigmask(SIGINT)|sigmask(SIGQUIT)| - sigmask(SIGTSTP)|sigmask(SIGTTIN)|sigmask(SIGTTOU), - fileno(mtf), -1); + sigset_t nset; + (void)sigemptyset(&nset); + (void)sigaddset(&nset, SIGHUP); + (void)sigaddset(&nset, SIGINT); + (void)sigaddset(&nset, SIGQUIT); + (void)sigaddset(&nset, SIGTSTP); + (void)sigaddset(&nset, SIGTTIN); + (void)sigaddset(&nset, SIGTTOU); + prepare_child(&nset, fileno(mtf), -1); if ((cp = value("sendmail")) != NULL) cp = expand(cp); else @@ -414,6 +423,9 @@ fixhead(hp, tolist) hp->h_cc = NULL; hp->h_bcc = NULL; for (np = tolist; np != NULL; np = np->n_flink) + /* Don't copy deleted addresses to the header */ + if (np->n_type & GDEL) + continue; if ((np->n_type & GMASK) == GTO) hp->h_to = cat(hp->h_to, nalloc(np->n_name, np->n_type)); diff --git a/usr.bin/mail/tty.c b/usr.bin/mail/tty.c index 687ce59..c1e19d7 100644 --- a/usr.bin/mail/tty.c +++ b/usr.bin/mail/tty.c @@ -33,7 +33,7 @@ #ifndef lint #if 0 -static char sccsid[] = "@(#)tty.c 8.1 (Berkeley) 6/6/93"; +static char sccsid[] = "@(#)tty.c 8.2 (Berkeley) 6/6/93"; #endif static const char rcsid[] = "$FreeBSD$"; @@ -48,8 +48,8 @@ static const char rcsid[] = #include "rcv.h" #include "extern.h" -static int c_erase; /* Current erase char */ -static int c_kill; /* Current kill char */ +static cc_t c_erase; /* Current erase char */ +static cc_t c_kill; /* Current kill char */ static jmp_buf rewrite; /* Place to go when continued */ static jmp_buf intjmp; /* Place to go when interrupted */ #ifndef TIOCSTI @@ -65,15 +65,19 @@ grabh(hp, gflags) struct header *hp; int gflags; { - struct termios tio; + struct termios ttybuf; sig_t saveint; -#ifndef TIOCSTI - sig_t savequit; -#endif sig_t savetstp; sig_t savettou; sig_t savettin; int errs; +#ifndef TIOCSTI + sig_t savequit; +#else +# ifdef TIOCEXT + int extproc, flag; +# endif /* TIOCEXT */ +#endif /* TIOCSTI */ savetstp = signal(SIGTSTP, SIG_DFL); savettou = signal(SIGTTOU, SIG_DFL); @@ -82,20 +86,28 @@ grabh(hp, gflags) #ifndef TIOCSTI ttyset = 0; #endif - if (tcgetattr(fileno(stdin), &tio) < 0) { + if (tcgetattr(fileno(stdin), &ttybuf) < 0) { warn("tcgetattr(stdin)"); return (-1); } - c_erase = tio.c_cc[VERASE]; - c_kill = tio.c_cc[VKILL]; + c_erase = ttybuf.c_cc[VERASE]; + c_kill = ttybuf.c_cc[VKILL]; #ifndef TIOCSTI - tio.c_cc[VERASE] = 0; - tio.c_cc[VKILL] = 0; + ttybuf.c_cc[VERASE] = _POSIX_VDISABLE; + ttybuf.c_cc[VKILL] = _POSIX_VDISABLE; if ((saveint = signal(SIGINT, SIG_IGN)) == SIG_DFL) (void)signal(SIGINT, SIG_DFL); if ((savequit = signal(SIGQUIT, SIG_IGN)) == SIG_DFL) (void)signal(SIGQUIT, SIG_DFL); #else +# ifdef TIOCEXT + extproc = ((ttybuf.c_lflag & EXTPROC) ? 1 : 0); + if (extproc) { + flag = 0; + if (ioctl(fileno(stdin), TIOCEXT, &flag) < 0) + warn("TIOCEXT: off"); + } +# endif /* TIOCEXT */ if (setjmp(intjmp)) goto out; saveint = signal(SIGINT, ttyint); @@ -103,7 +115,7 @@ grabh(hp, gflags) if (gflags & GTO) { #ifndef TIOCSTI if (!ttyset && hp->h_to != NULL) - ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &tio); + ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &ttybuf); #endif hp->h_to = extract(readtty("To: ", detract(hp->h_to, 0)), GTO); @@ -111,14 +123,14 @@ grabh(hp, gflags) if (gflags & GSUBJECT) { #ifndef TIOCSTI if (!ttyset && hp->h_subject != NULL) - ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &tio); + ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &ttybuf); #endif hp->h_subject = readtty("Subject: ", hp->h_subject); } if (gflags & GCC) { #ifndef TIOCSTI if (!ttyset && hp->h_cc != NULL) - ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &tio); + ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &ttybuf); #endif hp->h_cc = extract(readtty("Cc: ", detract(hp->h_cc, 0)), GCC); @@ -126,7 +138,7 @@ grabh(hp, gflags) if (gflags & GBCC) { #ifndef TIOCSTI if (!ttyset && hp->h_bcc != NULL) - ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &tio); + ttyset++, tcsetattr(fileno(stdin), TCSADRAIN, &ttybuf); #endif hp->h_bcc = extract(readtty("Bcc: ", detract(hp->h_bcc, 0)), GBCC); @@ -136,11 +148,19 @@ out: (void)signal(SIGTTOU, savettou); (void)signal(SIGTTIN, savettin); #ifndef TIOCSTI - tio.c_cc[VERASE] = c_erase; - tio.c_cc[VKILL] = c_kill; + ttybuf.c_cc[VERASE] = c_erase; + ttybuf.c_cc[VKILL] = c_kill; if (ttyset) - tcsetattr(fileno(stdin), TCSADRAIN, &tio); + tcsetattr(fileno(stdin), TCSADRAIN, &ttybuf); (void)signal(SIGQUIT, savequit); +#else +# ifdef TIOCEXT + if (extproc) { + flag = 1; + if (ioctl(fileno(stdin), TIOCEXT, &flag) < 0) + warn("TIOCEXT: on"); + } +# endif /* TIOCEXT */ #endif (void)signal(SIGINT, saveint); return (errs); @@ -178,7 +198,8 @@ readtty(pr, src) #else cp = src == NULL ? "" : src; while ((c = *cp++) != '\0') { - if (c == c_erase || c == c_kill) { + if ((c_erase != _POSIX_VDISABLE && c == c_erase) || + (c_kill != _POSIX_VDISABLE && c == c_kill)) { ch = '\\'; ioctl(0, TIOCSTI, &ch); } @@ -222,7 +243,7 @@ redo: return (strlen(canonb) > 0 ? savestr(canonb) : NULL); while (*cp != '\0') { c = *cp++; - if (c == c_erase) { + if (c_erase != _POSIX_VDISABLE && c == c_erase) { if (cp2 == canonb) continue; if (cp2[-1] == '\\') { @@ -232,7 +253,7 @@ redo: cp2--; continue; } - if (c == c_kill) { + if (c_kill != _POSIX_VDISABLE && c == c_kill) { if (cp2 == canonb) continue; if (cp2[-1] == '\\') { @@ -259,10 +280,13 @@ ttystop(s) int s; { sig_t old_action = signal(s, SIG_DFL); + sigset_t nset; - (void)sigsetmask(sigblock(0) & ~sigmask(s)); - (void)kill(0, s); - (void)sigblock(sigmask(s)); + (void)sigemptyset(&nset); + (void)sigaddset(&nset, s); + (void)sigprocmask(SIG_BLOCK, &nset, NULL); + kill(0, s); + (void)sigprocmask(SIG_UNBLOCK, &nset, NULL); (void)signal(s, old_action); longjmp(rewrite, 1); } |