garym@telesoft.UUCP (Gary Morris @favorite) (09/26/86)
This is a program I wrote called "checkmail". It summarizes the mail in your spool file for you, by displaying who it's from and subject. It allows you to select only new, unread or all mail. This program has only been tested on Sun Unix 2.3 (BSD 4.2), and I don't know what else it will run on. For you C hackers, please excuse the Ada-like syntax, I usually use Ada instead of C. Bugs and comments to "ucbvax!sdcsvax!telesoft!garym". Standard disclaimers apply. Gary Morris -- UUCP: seismo!s3sun!gould9!telesoft!garym N6FRT decvax!ucbvax!sdcsvax!telesoft!garym ARPA: telesoft!garym@sdcsvax.ARPA CIS: 76317,520 "Always listen to experts. They'll tell you what can't be done and why. Then do it." -- Lazarus Long #! /bin/sh # This is a shell archive, meaning: # 1. Remove everything above the #! /bin/sh line. # 2. Save the resulting text in a file. # 3. Execute the file with /bin/sh (not csh) to create the files: # Makefile # checkmail.1 # checkmail.c # This archive created: Thu Sep 25 22:01:19 1986 export PATH; PATH=/bin:$PATH echo shar: extracting "'Makefile'" '(55 characters)' if test -f 'Makefile' then echo shar: will not over-write existing file "'Makefile'" else cat << \SHAR_EOF > 'Makefile' checkmail: checkmail.c cc -O checkmail.c -o checkmail SHAR_EOF if test 55 -ne "`wc -c < 'Makefile'`" then echo shar: error transmitting "'Makefile'" '(should have been 55 characters)' fi fi # end of overwriting check echo shar: extracting "'checkmail.1'" '(2452 characters)' if test -f 'checkmail.1' then echo shar: will not over-write existing file "'checkmail.1'" else cat << \SHAR_EOF > 'checkmail.1' .TH CHECKMAIL 1 "March 4, 1986" "TeleSoft Inc." "UNIX User's Manual" .\" $Compile: iroff -man.new %f .SH NAME checkmail \- prints who your mail is from and the subjects .SH USAGE .B checkmail [-unaqo] [file] .SH DESCRIPTION .I checkmail is a program that will tell you about the mail in your mailbox. It lists who each letter is from (without path or domain), the date received, and the subject, one line per letter. Using options listed below you may check for new mail or list only new mail and also check files and mail folders other than your spool file. .I Checkmail with default options is similar to the .I from program except that subjects are also displayed. Normally a status of 0 is returned, unless the file isn't found in which case a status of 1 is returned. When the .I -q option is used a status of 0 is returned if there is mail and 1 if there isn't mail. .I Checkmail normally displays outgoing mail (mail you have sent) found in the file, you may choose ignore outgoing mail by using the .I -o option. .de OP .TP .B -\\$1 \\$2 .. .OP u List only unread mail. That is, mail that you haven't read yet. .OP n List only new mail. That is, mail that you haven't read or seen the header of. When you enter the mail program all the mail is marked as no longer new but still unread. .OP a List all mail, regardless of status (read, unread, or new). May be used to override an option already given on the command line. .OP o Exclude outgoing mail from the display or search. .OP q Quiet operation. Tells checkmail to only report whether it had any mail to display. The status result is 0 if there was mail and 1 if there wasn't any mail. Useful in combination with .I -n or .I -u option to check for new or unread mail in a .login script. .TP .B file Uses .I file instead of the default file /usr/spool/mail/$USER. You may specify a mail folder by prefixing the folder name with "+" as is done with the mail program. .SH "EXAMPLES" The following csh line could be used in your .login file to run the mail program only if you have unread mail in your spool file. if { checkmail -qu } mail Or the following could be used to display who new mail is from and the subjects: if { checkmail -qn } then echo '===== NEW MAIL =====' checkmail -n endif .SH "FILES" /usr/spool/mail/$USER \- your mail spool file (default file) .SH "SEE ALSO" from, mail .SH AUTHOR Gary Morris (sdcsvax!telesoft!gm) .SH BUGS n/a SHAR_EOF if test 2452 -ne "`wc -c < 'checkmail.1'`" then echo shar: error transmitting "'checkmail.1'" '(should have been 2452 characters)' fi fi # end of overwriting check echo shar: extracting "'checkmail.c'" '(6169 characters)' if test -f 'checkmail.c' then echo shar: will not over-write existing file "'checkmail.c'" else cat << \SHAR_EOF > 'checkmail.c' /************************************************************************/ /* checkmail [-unaoq] [file] */ /* */ /* This program lists the mail found in your mail spool file and */ /* tells you who it's from and the subject, one line per letter. */ /* */ /* -u causes it to only list the unread mail. */ /* -n causes it to only list the NEW mail. */ /* -a causes it to list all mail in the file. (default) */ /* -o causes it to skip outgoing mail (from yourself) */ /* -q causes it to work quietly, returns 0 exit status if */ /* have mail and 1 if you have no mail (-n applies here) */ /* file causes it to use a file other that your spool file */ /* use + in front of the name to indicate a folder */ /* */ /* Copyright 1986 Gary Morris. Unlimited non-commercial use permitted */ /* Author: ucbvax!sdcsvax!telesoft!gmorris */ /* $Header: RCS/checkmail.c,v 1.8 86/08/20 garym rel $ */ /************************************************************************/ #include <stdio.h> #include <strings.h> /* Defines for Ada-like syntax */ #define then { #define or_else } else { #define elsif } else if #define begin { #define end } #define endif } #define loop { #define endloop } #define endswitch } #define MAXLINE 1000 #define false 0 #define true 1 typedef enum { all_mail, new_mail, unread_mail } options; options option = all_mail; int show_outgoing = true; int quiet = false; /* set true if result reported via exit code */ char *USER; main(argc,argv) int argc; char **argv; begin FILE *fp, *fopen(); extern char *getenv(); extern int quiet; extern options option; extern char *USER; extern int show_outgoing; extern int optind; extern char *optarg; int argch; int have_mail = false; char mailbox[255]; USER = getenv("USER"); /*** default mailbox file ***/ strcpy( mailbox, "/usr/spool/mail/" ); strcat( mailbox, USER ); while ( (argch=getopt(argc,argv,"anuqo")) != EOF ) loop switch (argch) begin case 'o': show_outgoing = false; break; case 'a': option = all_mail; break; case 'n': option = new_mail; break; case 'u': option = unread_mail; break; case 'q': quiet = true; break; case '?': fprintf( stderr, "Usage: %s [-qnuao] [filename]\n", *argv ); exit(1); endswitch endloop if ( optind < argc ) then if ( argv[optind][0] == '+' ) then strcpy( mailbox, getenv("folder") ); strcat( mailbox, "/" ); strdel( argv[optind], 0, 1 ); strcat( mailbox, argv[optind] ); or_else strcpy( mailbox, argv[optind] ); endif endif if ( (fp=fopen(mailbox,"r")) != NULL ) then have_mail = HeaderCheck(fp); elsif ( ! quiet ) then /* ok to not find file, when -q, just no mail there since no file */ fprintf( stderr, "Error: File not found: %s\n", mailbox ); exit(1); endif exit( quiet && !have_mail ); end int HeaderCheck(fp) /* returns true if there is mail */ FILE *fp; begin extern options option; extern int quiet; extern char *USER; char input[MAXLINE]; /* current input line */ char output[MAXLINE]; /* current output line */ char who_from[80]; /* user name mail is from */ typedef enum { unknown = 0, in_header = 1, in_body = 2 } states; states state = unknown; char status = 'N'; /* statuses are: New, Old, Read */ int have_mail = false; int outgoing = false; char* p1; char* p2; while ( fgets(input,MAXLINE,fp) != NULL ) loop switch (input[0]) begin case 'F': if (strlen(input) >= 5) then if ( ((state==unknown) || (state==in_body)) && (input[1]=='r') && (input[2]=='o') && (input[3]=='m') && (input[4]==' ') ) then state = in_header; status = 'N'; strdel( input, strlen(input)-1, 1 ); /* delete any uucp path names in front of name */ while ( p1 = index( input, '!' ) ) loop strdel( input, 5, p1 - &input[5] + 1 ); endloop /* delete any domain type stuff after name */ if ( p1 = index( input, '@' ) ) then p2 = index( p1, ' ' ); if ( p2 == 0 ) p2 = index( p1, '\n' ); if ( p2 != 0 ) strdel( input, p1 - input, p2 - p1 ); endif /* see who it's from, if from self ignore it (maybe) */ p1 = index( &input[5], ' ' ); if ( p1 == 0 ) p1 = index( &input[5], '\n' ); strncpy( who_from, &input[5], p1 - &input[5] ); who_from[ p1-&input[5] ] = '\0'; outgoing = strcmp( who_from, USER ) == 0; strcpy( output, input ); endif endif break; case 'S': if (strlen(input) >= 9) then switch (input[1]) begin case 'u': if ( (state==in_header) && (input[1]=='u') && (input[2]=='b') && (input[3]=='j') && (input[4]=='e') && (input[5]=='c') && (input[6]=='t') && (input[7]==':') && (input[8]==' ') ) then strdel( input, 0, 9 ); /* del: Subject: */ strdel( input, strlen(input)-1, 1 ); strcat( output, " \"" ); strcat( output, input ); strcat( output, "\"" ); endif break; case 't': if ( (state==in_header) && (input[1]=='t') && (input[2]=='a') && (input[3]=='t') && (input[4]=='u') && (input[5]=='s') && (input[6]==':') && (input[7]==' ') ) then status = input[8]; endif break; endswitch endif break; case '\n': if (state == in_header) then state = in_body; if ( show_outgoing || !outgoing ) then if ( (option==new_mail && status=='N') || (option==unread_mail && (status=='N' || status=='O')) || (option==all_mail) ) then /* there is some mail (new or otherwise) */ have_mail = true; if ( quiet ) then return have_mail; or_else strcat( output, "\n" ); fputs( output, stdout ); endif endif endif endif break; default: break; endswitch endloop return have_mail; end strdel( s, index, length ) char *s; int index; int length; begin char *src = s+index+length; char *dest= s+index; int count = (strlen(s)+1)-(index+length); for (; count>0; count--) loop *dest++ = *src++; endloop end SHAR_EOF if test 6169 -ne "`wc -c < 'checkmail.c'`" then echo shar: error transmitting "'checkmail.c'" '(should have been 6169 characters)' fi fi # end of overwriting check # End of shell archive exit 0