home *** CD-ROM | disk | FTP | other *** search
- Subject: v09i007: ELM Mail System, Part07/19
- Newsgroups: mod.sources
- Approved: rs@mirror.TMC.COM
-
- Submitted by: Dave Taylor <hplabs!taylor>
- Mod.sources: Volume 9, Issue 7
- Archive-name: elm2/Part07
-
- #! /bin/sh
- # This is a shell archive. Remove anything before this line,
- # then unpack it by saving it in a file and typing "sh file".
- # If this archive is complete, you will see the message:
- # "End of archive 7 (of 19)."
- # Contents: src/aliasdb.c src/domains.c src/initialize.c
- # utils/fastmail.c utils/newmail.c utils/wnewmail.c
- PATH=/bin:/usr/bin:/usr/ucb ; export PATH
- echo shar: Extracting \"src/aliasdb.c\" \(7752 characters\)
- if test -f src/aliasdb.c ; then
- echo shar: Will not over-write existing file \"src/aliasdb.c\"
- else
- sed "s/^X//" >src/aliasdb.c <<'END_OF_src/aliasdb.c'
- X/** aliasdb.c **/
- X
- X/** Alias database files...
- X
- X (C) Copyright 1986 Dave Taylor
- X**/
- X
- X
- X#include "headers.h"
- X
- X#include <sys/types.h>
- X#include <sys/stat.h>
- X#include <errno.h>
- X
- Xextern int errno;
- X
- X#ifdef USE_DBM
- X# include <dbm.h>
- X#endif
- X
- X#define absolute(x) ((x) > 0 ? x : -(x))
- X
- Xchar *shift_lower(), *find_path_to(), *strcat(), *strcpy();
- Xunsigned long sleep();
- X
- Xint findnode_has_been_initialized = FALSE;
- X
- Xfindnode(name, display_error)
- Xchar *name;
- Xint display_error;
- X{
- X /** break 'name' into machine!user or user@machine and then
- X see if you can find 'machine' in the path database..
- X If so, return name as the expanded address. If not,
- X return what was given to us! If display_error, then
- X do so...
- X **/
- X
- X#ifndef DONT_TOUCH_ADDRESSES
- X
- X char old_name[SLEN];
- X char address[SLEN];
- X
- X if (strlen(name) == 0)
- X return;
- X
- X if (! findnode_has_been_initialized) {
- X if (! mail_only)
- X error("initializing internal tables...");
- X#ifndef USE_DBM
- X get_connections();
- X open_domain_file();
- X#endif
- X init_findnode();
- X clear_error();
- X findnode_has_been_initialized = TRUE;
- X }
- X
- X strcpy(old_name, name); /* save what we were given */
- X
- X if (expand_site(name, address) == -1) {
- X if (display_error && name[0] != '!') {
- X dprint2(2,"Couldn't expand host %s in address. (%s)\n",
- X name, "findnode");
- X if (! check_only && warnings) { /* be silent if just checking */
- X if (mail_only)
- X printf("Warning: couldn't expand %s...\n\r", name);
- X else {
- X error1("Warning: couldn't expand %s...", name);
- X sleep(1);
- X }
- X }
- X }
- X strcpy(name, old_name); /* and restore... */
- X }
- X else
- X strcpy(name, address);
- X#endif
- X return;
- X}
- X
- Xint
- Xexpand_site(cryptic, expanded)
- Xchar *cryptic, *expanded;
- X{
- X
- X /** Given an address of the form 'xyz@site' or 'site!xyz'
- X return an address of the form <expanded address for site>
- X with 'xyz' embedded according to the path database entry.
- X Note that 'xyz' can be eiher a simple address (as in "joe")
- X or a complex address (as in "joe%xerox.parc@Xerox.ARPA")!
- X 0 = found, -1 return means unknown site code
- X
- X Modified to strip out parenthetical comments...
- X **/
- X
- X#ifdef ACSNET
- X
- X strcpy(expanded, cryptic); /* fast and simple */
- X return(0);
- X
- X#else
- X# ifdef USE_DBM
- X datum key, contents;
- X# endif
- X
- X char name[VERY_LONG_STRING], sitename[VERY_LONG_STRING],
- X temp[VERY_LONG_STRING], old_name[VERY_LONG_STRING],
- X comment[LONG_STRING];
- X char *expand_domain(), *addr;
- X register int i = 0, j = 0, domain_name;
- X
- X strcpy(old_name, cryptic); /* remember what we were given */
- X
- X /** break down **/
- X
- X /** first, rip out the comment, if any **/
- X
- X if ((i = chloc(cryptic, '(')) > -1) {
- X comment[j++] = ' '; /* leading space */
- X for ( ;cryptic[i] != ')'; i++)
- X comment[j++] = cryptic[i];
- X comment[j++] = ')';
- X comment[j] = '\0';
- X /* and remove this from cryptic string too... */
- X if (cryptic[(j = chloc(cryptic,'('))-1] == ' ')
- X cryptic[j-1] = '\0';
- X else
- X cryptic[j] = '\0';
- X }
- X else
- X comment[0] = '\0';
- X
- X i = j = 0; /* reset */
- X
- X while (cryptic[i] != AT_SIGN && cryptic[i] != BANG &&
- X cryptic[i] != '\0' && cryptic[i] != '(')
- X sitename[j++] = cryptic[i++];
- X
- X sitename[j++] = '\0';
- X
- X j = 0;
- X
- X if (cryptic[i] == '\0') return(-1); /* nothing to expand! */
- X
- X domain_name = (cryptic[i] == AT_SIGN);
- X
- X i++;
- X
- X while (cryptic[i] != '\0' && cryptic[i] != '(' &&
- X ! whitespace(cryptic[i]))
- X name[j++] = cryptic[i++];
- X
- X name[j] = '\0';
- X
- X if (domain_name) {
- X strcpy(temp, name);
- X strcpy(name, sitename);
- X strcpy(sitename, temp);
- X }
- X
- X dprint3(5,"\nBroke address into '%s' @ '%s' '%s'\n\n",
- X name, sitename, comment);
- X
- X#ifdef USE_DBM
- X
- X if (size_of_pathfd == 0)
- X return(-1);
- X
- X key.dptr = sitename;
- X key.dsize = strlen(sitename) + 1;
- X
- X contents = fetch(key);
- X
- X if (contents.dptr == 0)
- X return(-1); /* can't find it! */
- X
- X sprintf(expanded, contents.dptr, name);
- X strcat(expanded, " "); /* add a single space... */
- X strcat(expanded, comment); /* ...and add comment */
- X return(0);
- X#endif
- X
- X#ifndef LOOK_CLOSE_AFTER_SEARCH
- X
- X if (talk_to(sitename)) {
- X strcpy(expanded, old_name); /* restore! */
- X return(0);
- X }
- X#endif
- X
- X if ((addr = find_path_to(sitename, TRUE)) == NULL) {
- X
- X#ifdef LOOK_CLOSE_AFTER_SEARCH
- X
- X if (talk_to(sitename)) {
- X strcpy(expanded, old_name); /* restore! */
- X return(0);
- X }
- X else
- X#endif
- X if ((addr = expand_domain(cryptic)) != NULL) {
- X strcpy(expanded, addr); /* into THIS buffer */
- X strcat(expanded, comment); /* patch in comment */
- X return(0);
- X }
- X else if (size_of_pathfd == 0) { /* no path database! */
- X strcpy(expanded, old_name); /* restore! */
- X return(0);
- X }
- X else { /* We just can't get there! */
- X strcpy(expanded, old_name); /* restore! */
- X return(-1);
- X }
- X }
- X else { /* search succeeded */
- X sprintf(expanded, addr, name);
- X strcat(expanded, comment); /* add comment */
- X return(0);
- X }
- X#endif
- X}
- X
- Xint
- Xbinary_search(name, address)
- Xchar *name, *address;
- X{
- X /* binary search file for name. Return 0 if found, -1 if not */
- X
- X char machine[40];
- X register long first = 0, last, middle;
- X register int compare;
- X
- X address[0] = '\0';
- X
- X last = size_of_pathfd;
- X
- X do {
- X
- X middle = (long) ((first+last) / 2);
- X
- X get_entry(machine, address, pathfd, middle);
- X
- X compare = strcmp(name, machine);
- X
- X if (compare < 0)
- X last = middle - 1;
- X else if (compare == 0)
- X return(0);
- X else /* greater */
- X first = middle + 1;
- X } while (absolute(last) - absolute(first) > FIND_DELTA);
- X
- X return(-1);
- X}
- X
- Xget_entry(machine, address, fileid, offset)
- Xchar *machine, *address;
- XFILE *fileid;
- Xlong offset;
- X{
- X /** get entry...return machine and address immediately
- X following given offset in fileid. **/
- X
- X fseek(fileid, offset, 0);
- X
- X /* read until we hit an end-of-line */
- X
- X while (getc(fileid) != '\n')
- X ;
- X
- X fscanf(fileid, "%s\t%s", machine, address);
- X}
- X
- Xinit_findnode()
- X{
- X /** Initialize the FILE and 'size_of_file' values for the
- X findnode procedure **/
- X
- X struct stat buffer;
- X
- X if (stat(pathfile, &buffer) == -1) {
- X dprint2(1, "Warning: No pathalias file [filename %s] found! (%s)\n",
- X pathfile, "init_findnode");
- X size_of_pathfd = 0;
- X return;
- X }
- X
- X size_of_pathfd = (long) buffer.st_size;
- X
- X#ifdef USE_DBM
- X
- X if (dbminit(pathfile) != 0) {
- X dprint1(1, "Warning: couldn't initialize DBM database %s\n",
- X pathfile);
- X dprint2(1, "** %s - %s **\n\n", error_name(errno),
- X error_description(errno));
- X size_of_pathfd = 0; /* error flag, in this case */
- X return;
- X }
- X
- X return;
- X#else
- X
- X if ((pathfd = fopen(pathfile,"r")) == NULL) {
- X dprint2(1, "Warning: Can't read pathalias file [filename %s] (%s)\n",
- X pathfile, "init_findnode");
- X size_of_pathfd = 0;
- X }
- X else
- X dprint2(2, "\nOpened file '%s' as path alias database. (%s)\n\n",
- X pathfile, "init_findnode");
- X#endif
- X}
- X
- Xchar *find_path_to(machine, printf_format)
- Xchar *machine;
- Xint printf_format;
- X{
- X /** Returns either the path to the specified machine or NULL if
- X not found. If "printf_format" is TRUE, then it leaves the
- X '%s' intact, otherwise it assumes that the address is a uucp
- X address for the domain expansion program and removes the
- X last three characters of the expanded name ("!%s") since
- X they're redundant with the expansion!
- X **/
- X
- X static char buffer[LONG_SLEN]; /* space for path */
- X
- X if (size_of_pathfd > 0)
- X if (binary_search(machine, buffer) != -1) { /* found it! */
- X if (! printf_format && strlen(buffer) > 3)
- X buffer[strlen(buffer)-3] = '\0';
- X return( (char *) buffer);
- X }
- X
- X return(NULL); /* failed if it's here! */
- X}
- END_OF_src/aliasdb.c
- if test 7752 -ne `wc -c <src/aliasdb.c`; then
- echo shar: \"src/aliasdb.c\" unpacked with wrong size!?
- fi
- # end of overwriting check
- fi
- echo shar: Extracting \"src/domains.c\" \(7773 characters\)
- if test -f src/domains.c ; then
- echo shar: Will not over-write existing file \"src/domains.c\"
- else
- sed "s/^X//" >src/domains.c <<'END_OF_src/domains.c'
- X/** domains.c **/
- X
- X/** This file contains all the code dealing with the expansion of
- X domain based addresses in Elm. It uses the file "domains" as
- X defined in the sysdefs.h file.
- X
- X (C) Copyright 1986 Dave Taylor
- X
- X From a file format and idea in "uumail" - designed by Stan Barber.
- X**/
- X
- X#include <stdio.h>
- X#include <ctype.h>
- X
- X#include "headers.h"
- X
- X#ifdef BSD
- X# undef toupper
- X# undef tolower
- X#endif
- X
- X/** define the various characters that we can encounter after a "%" sign
- X in the template file...
- X**/
- X
- X#define USERNAME 'U' /* %U = the name of the remote user */
- X#define HOSTNAME 'N' /* %N = the remote machine name */
- X#define FULLNAME 'D' /* %D = %N + domain info given */
- X#define NPATH 'R' /* %R = path to %N from pathalias */
- X#define PPATH 'P' /* %P = path to 'P' from pathalias */
- X#define OBSOLETE 'S' /* %S = (used to be suffix string) */
- X
- X/** and finally some characters that are allowed in user/machine names **/
- X
- X#define okay_others(c) (c == '-' || c == '^' || c == '$' || c == '_')
- X
- X/** and some allowed ONLY in the username field **/
- X
- X#define special_chars(c) (c == '%' || c == ':')
- X
- Xchar *find_path_to(), *expand_domain(), *match_and_expand_domain();
- Xchar *strcpy(), *strcat(), *strtok();
- Xunsigned long sleep();
- Xvoid rewind();
- X
- Xopen_domain_file()
- X{
- X if ((domainfd = fopen(domains, "r")) == NULL) {
- X dprint1(1, "Can't open file %s as domains file (open_domain_file)\n",
- X domains);
- X }
- X else {
- X dprint1(2,
- X "\nOpened '%s' as the domain database. (open_domain_file)\n\n",
- X domains);
- X }
- X
- X /* if it fails it'll instantiate domainfd to NULL which is
- X exactly what we want to have happen!! */
- X}
- X
- Xchar *expand_domain(buffer)
- Xchar *buffer;
- X{
- X /** Expand the address 'buffer' based on the domain information,
- X if any. Returns NULL if it can't expand it for any reason.
- X **/
- X
- X char name[2*NLEN], address[2*NLEN], domain[2*NLEN];
- X char *match_and_expand_domain();
- X
- X if (domainfd == NULL) return(NULL); /* no file present! */
- X
- X if (explode(buffer, name, address, domain))
- X return( match_and_expand_domain(domain, name, address) );
- X else { /* invalid format - not "user@host.domain" */
- X dprint1(3,
- X "Invalid format for domain expansion: %s (expand_domain)\n",
- X buffer);
- X return(NULL);
- X }
- X}
- X
- Xint
- Xexplode(buffer, name, address, domain)
- Xchar *buffer, *name, *address, *domain;
- X{
- X /** Break buffer, if in format name@machine.domain, into the
- X component parts, otherwise return ZERO and don't worry
- X about the values of the parameters!
- X **/
- X
- X register int i, j = 0;
- X
- X /** First get the name... **/
- X
- X for (i=0; buffer[i] != '@'; i++) {
- X if (! isalnum(buffer[i]) && ! okay_others(buffer[i]) && !
- X special_chars(buffer[i]))
- X return(0); /* invalid character in string! */
- X name[i] = buffer[i];
- X }
- X
- X name[i++] = '\0';
- X
- X /** now let's get the machinename **/
- X
- X while (buffer[i] != '.') {
- X if (! isalnum(buffer[i]) && ! okay_others(buffer[i]))
- X return(0); /* invalid character in string! */
- X address[j++] = buffer[i++];
- X }
- X address[j] = '\0';
- X
- X j = 0;
- X
- X /** finally let's get the domain information (there better be some!) **/
- X
- X while (buffer[i] != '\0') {
- X if (! isalnum(buffer[i]) && ! okay_others(buffer[i]) &&
- X buffer[i] != '.')
- X return(0); /* an you fail again, bozo! */
- X domain[j++] = toupper(buffer[i]);
- X i++;
- X }
- X
- X domain[j] = '\0';
- X
- X return(j); /* if j == 0 there's no domain info! */
- X}
- X
- Xchar *match_and_expand_domain(domain, name, machine)
- Xchar *domain, *name, *machine;
- X{
- X /** Given the domain, try to find it in the domain file and
- X if found expand the entry and return the result as a
- X character string...
- X **/
- X
- X static char address[SLEN];
- X char buffer[SLEN], domainbuff[NLEN];
- X char field1[2*NLEN], field2[2*NLEN], field3[2*NLEN];
- X char *path, *template, *expanded, *mydomain, *strtok();
- X int matched = 0, in_percent = 0;
- X register int i, j = 0;
- X
- X address[j] = '\0';
- X
- X domainbuff[0] = '\0';
- X mydomain = (char *) domainbuff; /* set up buffer etc */
- X
- X do {
- X rewind(domainfd); /* back to ground zero! */
- X
- X if (strlen(mydomain) > 0) { /* already in a domain! */
- X mydomain++; /* skip leading '.' */
- X while (*mydomain != '.' && *mydomain != ',')
- X mydomain++; /* next character */
- X if (*mydomain == ',')
- X return (NULL); /* didn't find domain! */
- X }
- X else
- X sprintf(mydomain, "%s,", domain); /* match ENTIRELY! */
- X
- X /* whip through file looking for the entry, please... */
- X
- X while (fgets(buffer, SLEN, domainfd) != NULL) {
- X if (buffer[0] == '#') /* skip comments */
- X continue;
- X if (strncmp(buffer, mydomain, strlen(mydomain)) == 0) { /* match? */
- X matched++; /* Gotcha! Remember this momentous event! */
- X break;
- X }
- X }
- X
- X if (! matched)
- X continue; /* Nothing. Not a sausage! Step through! */
- X
- X /** We've matched the domain! **/
- X
- X no_ret(buffer);
- X
- X (void) strtok(buffer, ","); /* skip the domain info */
- X
- X strcpy(field1, strtok(NULL, ",")); /* fun */
- X strcpy(field2, strtok(NULL, ",")); /* stuff */
- X strcpy(field3, strtok(NULL, ",")); /* eh? */
- X
- X path = (char *) NULL;
- X
- X /* now we merely need to figure out what permutation this is! */
- X
- X if (field3 == NULL || strlen(field3) == 0)
- X if (field2 == NULL || strlen(field2) == 0)
- X template = (char *) field1;
- X else {
- X path = (char *) field1;
- X template = (char *) field2;
- X }
- X else {
- X dprint1(2,"Domain info for %s from file broken into THREE fields!!\n",
- X domain);
- X dprint3(2, "-> %s\n-> %s\n-> %s\n", field1, field2, field3);
- X error1("Warning: domain %s uses a defunct field!!", domain);
- X sleep(2);
- X path = (char *) field1;
- X template = (char *) field3;
- X }
- X
- X if (strlen(path) > 0 && path[0] == '>')
- X path++; /* skip the '>' character, okay? */
- X
- X j = 0; /* address is zero, right now, right?? */
- X address[j] = '\0'; /* make sure string is too! */
- X
- X for (i=0; i < strlen(template); i++) {
- X if (template[i] == '%') {
- X if (! in_percent) /* just hit a NEW percent! */
- X in_percent = 1;
- X else { /* just another percent sign on the wall... */
- X address[j++] = '%';
- X address[j] = '\0'; /* ALWAYS NULL terminate */
- X in_percent = 0;
- X }
- X }
- X else if (in_percent) { /* Hey! a real command string */
- X in_percent = 0;
- X switch (template[i]) {
- X case USERNAME: strcat(address, name); break;
- X case HOSTNAME: strcat(address, machine); break;
- X case FULLNAME: strcat(address, machine);
- X strcat(address, domain); break;
- X case NPATH :
- X
- X if ((expanded = find_path_to(machine, FALSE)) == NULL) {
- X dprint2(3,"\nCouldn't expand system path '%s' (%s)\n\n",
- X machine, "domains");
- X error1("Couldn't find a path to %s!", machine);
- X sleep(2);
- X return(NULL); /* failed!! */
- X }
- X strcat(address, expanded); /* isn't this fun??? */
- X
- X break;
- X
- X case PPATH :
- X
- X if ((expanded = find_path_to(path, FALSE)) == NULL) {
- X dprint2(3,"\nCouldn't expand system path '%s' (%s)\n\n",
- X path, "domains");
- X error1("I Couldn't find a path to %s!", path);
- X sleep(2);
- X return(NULL); /* failed!! */
- X }
- X strcat(address, expanded); /* isn't this fun??? */
- X
- X break;
- X
- X case OBSOLETE: /* fall through.. */
- X default : dprint2(1,
- X "\nError: Bad sequence in template file for domain '%s': %%%c\n\n",
- X domain, template[i]);
- X }
- X j = strlen(address);
- X }
- X else {
- X address[j++] = template[i];
- X address[j] = '\0'; /* null terminate */
- X }
- X }
- X
- X address[j] = '\0';
- X
- X } while (strlen(address) < 1);
- X
- X return( (char *) address);
- X}
- END_OF_src/domains.c
- if test 7773 -ne `wc -c <src/domains.c`; then
- echo shar: \"src/domains.c\" unpacked with wrong size!?
- fi
- # end of overwriting check
- fi
- echo shar: Extracting \"src/initialize.c\" \(8292 characters\)
- if test -f src/initialize.c ; then
- echo shar: Will not over-write existing file \"src/initialize.c\"
- else
- sed "s/^X//" >src/initialize.c <<'END_OF_src/initialize.c'
- X/** initialize.c **/
- X
- X/***** Initialize - read in all the defaults etc etc
- X (C) Copyright 1985 Dave Taylor
- X*****/
- X
- X#include "headers.h"
- X
- X#ifdef BSD
- X# include <sgtty.h>
- X#else
- X# include <termio.h>
- X#endif
- X
- X#include <pwd.h>
- X
- X#ifdef BSD
- X# include <sys/time.h>
- X#else
- X# include <time.h>
- X#endif
- X
- X#include <signal.h>
- X#include <ctype.h>
- X#include <errno.h>
- X
- X#ifdef BSD
- X#undef toupper
- X#undef tolower
- X#endif
- X
- Xextern int errno; /* system error number on failure */
- X
- Xchar *error_name(), *error_description();
- X
- Xchar *expand_logname(), *getenv(), *getlogin(), *strcpy(), *strcat();
- Xunsigned short getgid(), getuid();
- Xvoid exit();
- X
- Xstruct header_rec *malloc();
- X
- Xinitialize(initscreen_too)
- Xint initscreen_too;
- X{
- X /** initialize the whole ball of wax. If "initscreen_too" then
- X call init_screen where appropriate..
- X **/
- X struct passwd *pass, *getpwnam();
- X
- X register int i, j;
- X int quit_signal(), term_signal(), ill_signal(),
- X fpe_signal(), bus_signal(), segv_signal(),
- X alarm_signal(), pipe_signal();
- X char buffer[SLEN], *cp;
- X
- X
- X userid = getuid();
- X groupid = getgid();
- X
- X strcpy(home,((cp = getenv("HOME")) == NULL)? "" : cp);
- X strcpy(shell,((cp = getenv("SHELL")) == NULL)? "" : cp);
- X strcpy(pager,((cp = getenv("PAGER")) == NULL)? default_pager : cp);
- X
- X if (debug) { /* setup for dprintf statements! */
- X char newfname[SLEN], filename[SLEN];
- X
- X sprintf(filename, "%s/%s", home, DEBUG);
- X if (access(filename, ACCESS_EXISTS) == 0) { /* already one! */
- X sprintf(newfname,"%s/%s", home, OLDEBUG);
- X (void) link(filename, newfname);
- X }
- X
- X /* Note what we just did up there: we always save the old
- X version of the debug file as OLDEBUG, so users can mail
- X copies of bug files without trashing 'em by starting up
- X the mailer. Dumb, subtle, but easy enough to do!
- X */
- X
- X if ((debugfile = fopen(filename, "w")) == NULL) {
- X debug = 0; /* otherwise 'leave' will try to log! */
- X leave(fprintf(stderr,"Could not open file %s for debug output!\n",
- X filename));
- X }
- X chown(filename, userid, groupid); /* file owned by user */
- X
- X fprintf(debugfile, "Debug output of the ELM program. Version %s\n\n",
- X VERSION);
- X }
- X
- X if (initscreen_too) /* don't set up unless we need to! */
- X InitScreen();
- X
- X if (debug < 2) { /* otherwise let the system trap 'em! */
- X signal(SIGINT, SIG_IGN);
- X signal(SIGQUIT, quit_signal); /* Quit signal */
- X signal(SIGTERM, term_signal); /* Terminate signal */
- X signal(SIGILL, ill_signal); /* Illegal instruction */
- X signal(SIGFPE, fpe_signal); /* Floating point exception */
- X signal(SIGBUS, bus_signal); /* Bus error */
- X signal(SIGSEGV, segv_signal); /* Segmentation Violation */
- X }
- X
- X signal(SIGALRM, alarm_signal); /* Process Timer Alarm */
- X signal(SIGPIPE, pipe_signal); /* Illegal Pipe Operation */
- X
- X get_term_chars();
- X
- X gethostname(hostname, sizeof(hostname));
- X
- X#ifdef BSD
- X if ((cp = getenv("USER")) == NULL)
- X#else
- X if ((cp = getenv("LOGNAME")) == NULL)
- X#endif
- X if ((cp = getlogin()) == NULL)
- X cuserid(username);
- X else
- X strcpy(username, cp);
- X else
- X strcpy(username, cp);
- X
- X /* now let's get the full username.. */
- X
- X if ((pass = getpwnam(username)) == NULL) {
- X error("Couldn't read password entry??");
- X strcpy(full_username, username);
- X }
- X else {
- X /* fix for this section from Don Joslyn of Nova University */
- X for (i=0,j=0; pass->pw_gecos[i] != '\0' && pass->pw_gecos[i] != ',';
- X i++)
- X if (pass->pw_gecos[i] == '&') {
- X full_username[j] = '\0';
- X strcat(full_username, expand_logname());
- X j = strlen(full_username);
- X }
- X else
- X full_username[j++] = pass->pw_gecos[i];
- X full_username[j] = '\0';
- X }
- X
- X if ((cp = getenv("EDITOR")) == NULL)
- X strcpy(editor,default_editor);
- X else
- X strcpy(editor, cp);
- X strcpy(alternative_editor, editor); /* this one can't be changed! */
- X
- X if (! mail_only) {
- X mailbox[0] = '\0';
- X strcpy(prefixchars, "> "); /* default message prefix */
- X sprintf(calendar_file, "%s/%s", home, dflt_calendar_file);
- X }
- X
- X local_signature[0] = remote_signature[0] = '\0'; /* NULL! */
- X
- X read_rc_file(); /* reading the .elmrc next... */
- X
- X /** now try to expand the specified filename... **/
- X
- X if (strlen(infile) > 0) {
- X (void) expand_filename(infile);
- X if ((errno = can_access(infile, READ_ACCESS))) {
- X dprint2(1,"Error: given file %s as mailbox - unreadable (%s)!\n",
- X infile, error_name(errno));
- X fprintf(stderr,"Can't open mailbox '%s' for reading!\n", infile);
- X exit(1);
- X }
- X }
- X
- X /** check to see if the user has defined a LINES or COLUMNS
- X value different to that in the termcap entry (for
- X windowing systems, of course!) **/
- X
- X ScreenSize(&LINES, &COLUMNS);
- X
- X if ((cp = getenv("LINES")) != NULL && isdigit(*cp)) {
- X sscanf(cp, "%d", &LINES);
- X LINES -= 1; /* kludge for HP Window system? ... */
- X }
- X
- X if ((cp = getenv("COLUMNS")) != NULL && isdigit(*cp))
- X sscanf(cp, "%d", &COLUMNS);
- X
- X /** fix the shell if needed **/
- X
- X if (shell[0] != '/') {
- X sprintf(buffer, "/bin/%s", shell);
- X strcpy(shell, buffer);
- X }
- X
- X if (! mail_only) {
- X mailbox_defined = (mailbox[0] != '\0');
- X
- X /* get the cursor control keys... */
- X
- X cursor_control = FALSE;
- X
- X if ((cp = return_value_of("ku")) != NULL)
- X if (strlen(cp) == 2) {
- X strcpy(up, cp);
- X if ((cp = return_value_of("kd")) == NULL)
- X cursor_control = FALSE;
- X else if (strlen(cp) != 2)
- X cursor_control = FALSE;
- X else {
- X strcpy(down, cp);
- X cursor_control = TRUE;
- X transmit_functions(ON);
- X }
- X }
- X
- X strcpy(start_highlight, "->");
- X end_highlight[0] = '\0';
- X
- X if (!arrow_cursor) { /* try to use inverse bar instead */
- X if ((cp = return_value_of("so")) != NULL) {
- X strcpy(start_highlight, cp);
- X if ((cp = return_value_of("se")) == NULL)
- X strcpy(start_highlight, "->");
- X else {
- X strcpy(end_highlight, cp);
- X has_highlighting = TRUE;
- X }
- X }
- X }
- X }
- X
- X /** allocate the first KLICK headers... **/
- X
- X if ((header_table = malloc(KLICK*sizeof(struct header_rec))) == NULL) {
- X fprintf(stderr,"\n\r\n\rCouldn't allocate initial headers!\n\r\n");
- X leave();
- X }
- X max_headers = KLICK; /* we have those preallocated */
- X
- X /** now cruise along... **/
- X
- X if (! mail_only) {
- X if (mini_menu)
- X headers_per_page = LINES - 13;
- X else
- X headers_per_page = LINES - 8; /* 5 more headers! */
- X
- X newmbox(1,FALSE, TRUE); /* read in the mailbox! */
- X }
- X
- X dprint0(2,"\n-- end of initialization phase --\n");
- X
- X dprint3(2,"\thostname = %s\n\tusername = %s\n\tfull_username = \"%s\"\n",
- X hostname, username, full_username);
- X
- X dprint3(2,"\thome = %s\n\teditor = %s\n\tmailbox = %s\n",
- X home, editor, mailbox);
- X
- X dprint3(2,"\tinfile = %s\n\tfolder-dir = %s\n\tprintout = \"%s\"\n",
- X infile, folders, printout);
- X
- X dprint3(2,"\tsavefile = %s\n\tprefix = \"%s\"\n\tshell = %s\n",
- X savefile, prefixchars, shell);
- X
- X if (signature)
- X dprint2(2,"\tlocal-signature = %s\n\tremote-signature = %s\n",
- X local_signature, remote_signature);
- X
- X dprint0(1,"-- beginning execution phase --\n\n");
- X}
- X
- Xget_term_chars()
- X{
- X /** This routine sucks out the special terminal characters
- X ERASE and KILL for use in the input routine. The meaning
- X of the characters are (dare I say it?) fairly obvious... **/
- X
- X#ifdef BSD
- X struct sgttyb term_buffer;
- X
- X# define TCGETA TIOCGETP
- X
- X#else
- X struct termio term_buffer;
- X#endif
- X
- X if (ioctl(STANDARD_INPUT, TCGETA, &term_buffer) == -1) {
- X dprint1(1,"Error: %s encountered on ioctl call (get_term_chars)\n",
- X error_name(errno));
- X /* set to defaults for terminal driver */
- X backspace = BACKSPACE;
- X kill_line = ctrl('U');
- X }
- X else {
- X#ifdef BSD
- X backspace = term_buffer.sg_erase;
- X kill_line = term_buffer.sg_kill;
- X#else
- X backspace = term_buffer.c_cc[VERASE];
- X kill_line = term_buffer.c_cc[VKILL];
- X#endif
- X }
- X}
- X
- Xchar *expand_logname()
- X{
- X /** Return logname in a nice format (for expanding "&" in the
- X /etc/passwd file) **/
- X
- X static char buffer[SLEN];
- X register int i;
- X
- X if (strlen(username) == 0)
- X buffer[0] = '\0';
- X else {
- X buffer[0] = toupper(username[0]);
- X
- X for (i=1; username[i] != '\0'; i++)
- X buffer[i] = tolower(username[i]);
- X
- X buffer[i] = '\0';
- X }
- X
- X return( (char *) buffer);
- X}
- END_OF_src/initialize.c
- if test 8292 -ne `wc -c <src/initialize.c`; then
- echo shar: \"src/initialize.c\" unpacked with wrong size!?
- fi
- # end of overwriting check
- fi
- echo shar: Extracting \"utils/fastmail.c\" \(8167 characters\)
- if test -f utils/fastmail.c ; then
- echo shar: Will not over-write existing file \"utils/fastmail.c\"
- else
- sed "s/^X//" >utils/fastmail.c <<'END_OF_utils/fastmail.c'
- X/** fastmail.c **/
- X
- X/** This program is specifically written for group mailing lists and
- X such batch type mail processing. It does NOT use aliases at all,
- X it does NOT read the /etc/password file to find the From: name
- X of the user and does NOT expand any addresses. It is meant
- X purely as a front-end for either /bin/mail or /usr/lib/sendmail
- X (according to what is available on the current system).
- X
- X **** This program should be used with CAUTION *****
- X
- X (C) Copyright 1985 Dave Taylor
- X**/
- X
- X/** The calling sequence for this program is:
- X
- X fastmail {args} filename full-email-address
- X
- X where args could be any (or all) of;
- X
- X -b bcc-list (Blind carbon copies to)
- X -c cc-list (carbon copies to)
- X -d (debug on)
- X -f from (from name)
- X -r reply-to-address (Reply-To:)
- X -s subject (subject of message)
- X**/
- X
- X#include <stdio.h>
- X
- X#ifdef BSD
- X# ifdef BSD4.1
- X# include <time.h>
- X# include <sys/types.h>
- X# include <sys/timeb.h>
- X# else
- X# include <sys/time.h>
- X# endif
- X#else
- X# include <time.h>
- X#endif
- X
- X#include "defs.h"
- X
- Xstatic char ident[] = { WHAT_STRING };
- X
- X#define binrmail "/bin/rmail"
- X#define temphome "/tmp/fastmail."
- X
- X#define DONE 0
- X#define ERROR -1
- X
- Xchar *optional_arg; /* optional argument as we go */
- Xint opt_index; /* argnum + 1 when we leave */
- X
- Xchar *arpa_dayname[] = { "Sun", "Mon", "Tue", "Wed", "Thu",
- X "Fri", "Sat", "" };
- X
- Xchar *arpa_monname[] = { "Jan", "Feb", "Mar", "Apr", "May", "Jun",
- X "Jul", "Aug", "Sep", "Oct", "Nov", "Dec", ""};
- X
- Xchar *get_arpa_date();
- X
- X#ifdef BSD
- X char *timezone();
- X#else
- X extern char *tzname[];
- X#endif
- X
- Xmain(argc, argv)
- Xint argc;
- Xchar *argv[];
- X{
- X
- X FILE *tempfile;
- X char hostname[NLEN], username[NLEN], from_string[SLEN], subject[SLEN];
- X char filename[SLEN], tempfilename[SLEN], command_buffer[256];
- X char replyto[SLEN], cc_list[SLEN], bcc_list[SLEN], to_list[SLEN];
- X int c, sendmail_available, debug = 0;
- X
- X replyto[0] = '\0';
- X cc_list[0] = '\0';
- X bcc_list[0] = '\0';
- X
- X while ((c = get_options(argc, argv, "b:c:df:r:s:")) > 0) {
- X switch (c) {
- X case 'b' : strcpy(bcc_list, optional_arg); break;
- X case 'c' : strcpy(cc_list, optional_arg); break;
- X case 'd' : debug++; break;
- X case 'f' : strcpy(from_string, optional_arg); break;
- X case 'r' : strcpy(replyto, optional_arg); break;
- X case 's' : strcpy(subject, optional_arg); break;
- X }
- X }
- X
- X if (c == ERROR) {
- X fprintf(stderr,"Usage: fastmail {args} filename address(es)\n");
- X fprintf(stderr, " where {args} can be;\n");
- X fprintf(stderr,"\t-b bcc-list\n\t-c cc-list\n\t-d\n\t-f from-name\n");
- X fprintf(stderr, "\t-r reply-to\n\t-s subject\n\n");
- X exit(1);
- X }
- X
- X if (opt_index > argc) {
- X fprintf(stderr,"Usage: fastmail {args} filename address(es)\n");
- X fprintf(stderr, " where {args} can be;\n");
- X fprintf(stderr,"\t-b bcc-list\n\t-c cc-list\n\t-d\n\t-f from-name\n");
- X fprintf(stderr, "\t-r reply-to\n\t-s subject\n\n");
- X exit(1);
- X }
- X
- X strcpy(filename, argv[opt_index++]);
- X
- X if (opt_index > argc) {
- X fprintf(stderr,"Usage: fastmail {args} filename address(es)\n");
- X fprintf(stderr, " where {args} can be;\n");
- X fprintf(stderr,"\t-b bcc-list\n\t-c cc-list\n\t-d\n\t-f from-name\n");
- X fprintf(stderr, "\t-r reply-to\n\t-s subject\n\n");
- X exit(1);
- X }
- X
- X gethostname(hostname, sizeof(hostname));
- X strcpy(username, getlogin());
- X if (strlen(username) == 0)
- X cuserid(username);
- X
- X if (access(filename, READ_ACCESS) == -1)
- X exit(fprintf(stderr, "Error: can't find file %s!\n", filename));
- X
- X sprintf(tempfilename, "%s%d", temphome, getpid());
- X
- X if ((tempfile = fopen(tempfilename, "w")) == NULL)
- X exit(fprintf(stderr, "Couldn't open temp file %s\n", tempfilename));
- X
- X if (strlen(from_string) > 0)
- X fprintf(tempfile, "From: %s!%s (%s)\n",
- X hostname, username, from_string);
- X else
- X fprintf(tempfile, "From: %s!%s\n", hostname, username);
- X
- X fprintf(tempfile, "Date: %s\n", get_arpa_date());
- X
- X if (strlen(subject) > 0)
- X fprintf(tempfile, "Subject: %s\n", subject);
- X
- X if (strlen(replyto) > 0)
- X fprintf(tempfile, "Reply-To: %s\n", replyto);
- X
- X while (opt_index < argc)
- X sprintf(to_list, "%s%s%s", to_list, (strlen(to_list) > 0? ", ":""),
- X argv[opt_index++]);
- X
- X fprintf(tempfile, "To: %s\n", to_list);
- X
- X if (strlen(cc_list) > 0)
- X fprintf(tempfile, "Cc: %s\n", cc_list);
- X
- X if (strlen(bcc_list) > 0)
- X fprintf(tempfile, "Bcc: %s\n", bcc_list); /* trust xport */
- X
- X fprintf(tempfile, "X-Mailer: fastmail [version %s]\n", VERSION);
- X fprintf(tempfile, "\n");
- X
- X fclose(tempfile);
- X
- X /** now we'll cat both files to /bin/rmail or sendmail... **/
- X
- X sendmail_available = (access(sendmail, EXECUTE_ACCESS) != -1);
- X
- X printf("Mailing to %s%s%s%s%s [via %s]\n", to_list,
- X (strlen(cc_list) > 0 ? " ":""), cc_list,
- X (strlen(bcc_list) > 0 ? " ":""), bcc_list,
- X sendmail_available? "sendmail" : "rmail");
- X
- X sprintf(command_buffer, "cat %s %s | %s '%s %s %s'",
- X tempfilename, filename,
- X sendmail_available? sendmail : mailer,
- X to_list, cc_list, bcc_list);
- X
- X if (debug)
- X printf("%s\n", command_buffer);
- X
- X system(command_buffer);
- X
- X unlink(tempfilename);
- X}
- X
- X
- Xchar *get_arpa_date()
- X{
- X /** returns an ARPA standard date. The format for the date
- X according to DARPA document RFC-822 is exemplified by;
- X
- X Mon, 12 Aug 85 6:29:08 MST
- X
- X **/
- X
- X static char buffer[SLEN]; /* static character buffer */
- X struct tm *the_time, /* Time structure, see CTIME(3C) */
- X *localtime();
- X long junk; /* time in seconds.... */
- X#ifdef BSD
- X# ifdef BSD4.1
- X struct timeb loc_time; /* of course this is different! */
- X# else
- X struct timeval time_val;
- X struct timezone time_zone;
- X# endif
- X#endif
- X
- X#ifdef BSD
- X# ifdef BSD4.1
- X junk = (long) time((long *) 0);
- X ftime(&loc_time);
- X# else
- X gettimeofday(&time_val, &time_zone);
- X junk = time_val.tv_sec;
- X# endif
- X#else
- X junk = time(0); /* this must be here for it to work! */
- X#endif
- X the_time = localtime(&junk);
- X
- X sprintf(buffer, "%s, %d %s %d %d:%02d:%02d %s",
- X arpa_dayname[the_time->tm_wday],
- X the_time->tm_mday % 32,
- X arpa_monname[the_time->tm_mon],
- X the_time->tm_year % 100,
- X the_time->tm_hour % 24,
- X the_time->tm_min % 61,
- X the_time->tm_sec % 61,
- X#ifdef BSD
- X# ifdef BSD4.1
- X timezone(loc_time.time_zone, the_time->tz_isdst));
- X# else
- X timezone(time_zone.tz_minuteswest, time_zone.tz_dsttime));
- X# endif
- X#else
- X tzname[the_time->tm_isdst]);
- X#endif
- X
- X return( (char *) buffer);
- X}
- X
- X/** Starting argument parsing routine.
- X
- X Called as "get_options(argc, argv, options)" where options is a string
- X of the form "abc:d" indicating that 'a' 'b' and 'd' are flags and
- X 'c' is a flag with a trailing argument. Optional arguments are
- X returned in the external char * variable "optional_arg", and the
- X external int "opt_index" is set to the first entry in the argv list
- X that wasn't processed (ie after the flags).
- X
- X For example, the C compiler would have something of the form
- X getopt(argc, argv, "Oo:l:") to allow "cc -O -o output -l lib file.c"
- X
- X (C) Copyright 1986, Dave Taylor
- X**/
- X
- Xint _indx = 1, _argnum = 1;
- X
- Xint
- Xget_options(argc, argv, options)
- Xint argc;
- Xchar *argv[], *options;
- X{
- X /** Returns the character argument next, and optionally instantiates
- X "argument" to the argument associated with the particular option
- X **/
- X
- X char *word, *strchr();
- X
- X if (_indx >= strlen(argv[_argnum])) {
- X _argnum++;
- X _indx = 1; /* zeroeth char is '-' */
- X }
- X
- X if (_argnum >= argc) {
- X opt_index = argc;
- X return(DONE);
- X }
- X
- X if (argv[_argnum][0] != '-') {
- X opt_index = _argnum;
- X return(DONE);
- X }
- X
- X word = strchr(options, argv[_argnum][_indx++]);
- X
- X if (strlen(word) == 0)
- X return(ERROR);
- X
- X if (word[1] == ':') {
- X
- X /** Two possibilities - either tailing end of this argument or the
- X next argument in the list **/
- X
- X if (_indx < strlen(argv[_argnum])) { /* first possibility */
- X optional_arg = (char *) (argv[_argnum] + _indx);
- X _argnum++;
- X _indx = 1;
- X }
- X else { /* second choice */
- X if (++_argnum >= argc)
- X return(ERROR); /* no argument!! */
- X
- X optional_arg = (char *) argv[_argnum++];
- X _indx = 1;
- X }
- X }
- X
- X return((int) word[0]);
- X}
- END_OF_utils/fastmail.c
- if test 8167 -ne `wc -c <utils/fastmail.c`; then
- echo shar: \"utils/fastmail.c\" unpacked with wrong size!?
- fi
- # end of overwriting check
- fi
- echo shar: Extracting \"utils/newmail.c\" \(7989 characters\)
- if test -f utils/newmail.c ; then
- echo shar: Will not over-write existing file \"utils/newmail.c\"
- else
- sed "s/^X//" >utils/newmail.c <<'END_OF_utils/newmail.c'
- X/** newmail.c **/
- X
- X/** Keep track of the mail for the current user...if new mail
- X arrives, output a line of the form;
- X
- X New mail from <name> - <subject>
- X
- X where <name> is either the persons full name, or machine!login.
- X If there is no subject, it will say.
- X
- X Added: you can specify a file other than the mailbox to keep
- X track of - if an argument is given, the program will try
- X to use it as a filename...
- X
- X Also, the program will quit when you log off of the machine.
- X
- X (C) Copyright 1986, Dave Taylor
- X**/
- X
- X#include <stdio.h>
- X#include <sys/types.h>
- X#include <sys/stat.h>
- X
- X#include "defs.h"
- X
- X#ifdef AUTO_BACKGROUND
- X#include <signal.h> /* background jobs ignore some signals... */
- X#endif
- X
- Xstatic char ident[] = { WHAT_STRING };
- X
- X#define LINEFEED (char) 10
- X#define BEGINNING 0 /* seek fseek(3S) */
- X#define SLEEP_TIME 60
- X
- X#define NO_SUBJECT "(No Subject Specified)"
- X
- XFILE *mailfile;
- X
- Xlong bytes();
- X
- Xmain(argc, argv)
- Xint argc;
- Xchar *argv[];
- X{
- X char filename[LONG_SLEN];
- X long size, newsize;
- X
- X if (argc > 2)
- X fprintf(stderr, "Usage: %s [filename] &\n", argv[0]);
- X else if (argc == 2) {
- X strcpy(filename, argv[1]);
- X if (access(filename, ACCESS_EXISTS) == -1) {
- X fprintf(stderr,"%s: Can't open file %s to keep track of!\n",
- X argv[0], filename);
- X exit(1);
- X }
- X }
- X else
- X sprintf(filename,"%s%s",mailhome, getlogin());
- X
- X#ifdef AUTO_BACKGROUND
- X if (fork()) /* automatically puts this task in background! */
- X exit(0);
- X
- X signal(SIGINT, SIG_IGN);
- X signal(SIGQUIT, SIG_IGN);
- X signal(SIGHUP, SIG_DFL); /* so we exit when logged out */
- X#endif
- X
- X size = bytes(filename);
- X
- X mailfile = (FILE *) NULL;
- X
- X while (1) {
- X
- X#ifndef AUTO_BACKGROUND /* won't work if we're nested this deep! */
- X if (getppid() == 1) /* we've lost our shell! */
- X exit();
- X#endif
- X if (! isatty(1)) /* we're not sending output to a tty any more */
- X exit();
- X
- X /** Note the lack of error checking on the fopen() (Philip Peake
- X did!) - this is okay since if it fails we don't have any
- X mail and we can sleep(60) and try again later...
- X **/
- X
- X if (mailfile == (FILE *) NULL)
- X mailfile = fopen(filename,"r");
- X
- X if ((newsize = bytes(filename)) > size) { /* new mail */
- X fseek(mailfile, size, BEGINNING); /* skip all current mail */
- X size = newsize;
- X printf("\n\r"); /* blank lines surrounding message */
- X read_headers();
- X printf("\n\r");
- X }
- X else if (newsize != size) {
- X size = newsize; /* mail's been removed... */
- X (void) fclose(mailfile); /* close it and ... */
- X mailfile = (FILE *) NULL; /* let's reopen the file */
- X }
- X
- X sleep(SLEEP_TIME);
- X }
- X}
- X
- Xint
- Xread_headers()
- X{
- X /** read the headers, output as found **/
- X
- X char buffer[LONG_SLEN], from_whom[SLEN], subject[SLEN];
- X register int subj = 0, in_header = 1, count = 0, priority=0;
- X
- X while (fgets(buffer, LONG_SLEN, mailfile) != NULL) {
- X if (first_word(buffer,"From ")) {
- X if (real_from(buffer, from_whom)) {
- X subj = 0;
- X in_header = 1;
- X }
- X }
- X else if (in_header) {
- X if (first_word(buffer,">From"))
- X forwarded(buffer, from_whom); /* return address */
- X else if (first_word(buffer,"Subject:") ||
- X first_word(buffer,"Re:")) {
- X if (! subj++) {
- X remove_first_word(buffer);
- X strcpy(subject, buffer);
- X }
- X }
- X else if (first_word(buffer,"Priority:"))
- X priority++;
- X else if (first_word(buffer,"From:"))
- X parse_arpa_from(buffer, from_whom);
- X else if (buffer[0] == LINEFEED) {
- X in_header = 0; /* in body of message! */
- X show_header(priority, from_whom, subject);
- X from_whom[0] = 0;
- X subject[0] = 0;
- X count++;
- X }
- X }
- X }
- X return(count);
- X}
- X
- Xint
- Xreal_from(buffer, who)
- Xchar *buffer, *who;
- X{
- X /***** returns true iff 's' has the seven 'from' fields,
- X initializing the who to the sender *****/
- X
- X char junk[80];
- X
- X junk[0] = '\0';
- X sscanf(buffer, "%*s %s %*s %*s %*s %*s %s",
- X who, junk);
- X return(junk[0] != '\0');
- X}
- X
- Xforwarded(buffer, who)
- Xchar *buffer, *who;
- X{
- X /** change 'from' and date fields to reflect the ORIGINATOR of
- X the message by iteratively parsing the >From fields... **/
- X
- X char machine[80], buff[80];
- X
- X machine[0] = '\0';
- X sscanf(buffer, "%*s %s %*s %*s %*s %*s %*s %*s %*s %s",
- X who, machine);
- X
- X if (machine[0] == '\0') /* try for srm address */
- X sscanf(buffer, "%*s %s %*s %*s %*s %*s %*s %*s %s",
- X who, machine);
- X
- X if (machine[0] == '\0')
- X sprintf(buff,"anonymous");
- X else
- X sprintf(buff,"%s!%s", machine, who);
- X
- X strncpy(who, buff, 80);
- X}
- X
- X
- Xremove_first_word(string)
- Xchar *string;
- X{ /** removes first word of string, ie up to first non-white space
- X following a white space! **/
- X
- X register int loc;
- X
- X for (loc = 0; string[loc] != ' ' && string[loc] != '\0'; loc++)
- X ;
- X
- X while (string[loc] == ' ' || string[loc] == '\t')
- X loc++;
- X
- X move_left(string, loc);
- X}
- X
- Xmove_left(string, chars)
- Xchar string[];
- Xint chars;
- X{
- X /** moves string chars characters to the left DESTRUCTIVELY **/
- X
- X register int i;
- X
- X chars--; /* index starting at zero! */
- X
- X for (i=chars; string[i] != '\0' && string[i] != '\n'; i++)
- X string[i-chars] = string[i];
- X
- X string[i-chars] = '\0';
- X}
- X
- Xshow_header(priority, from, subject)
- Xint priority;
- Xchar *from, *subject;
- X{
- X /** output header in clean format, including abbreviation
- X of return address if more than one machine name is
- X contained within it! **/
- X char buffer[SLEN];
- X int loc, i=0, exc=0;
- X
- X#ifdef PREFER_UUCP
- X
- X if (chloc(from, '!') != -1 && in_string(from, BOGUS_INTERNET))
- X from[strlen(from) - strlen(BOGUS_INTERNET)] = '\0';
- X
- X#endif
- X
- X loc = strlen(from);
- X
- X while (exc < 2 && loc > 0)
- X if (from[--loc] == '!')
- X exc++;
- X
- X if (exc == 2) { /* lots of machine names! Get last one */
- X loc++;
- X while (loc < strlen(from) && loc < SLEN)
- X buffer[i++] = from[loc++];
- X buffer[i] = '\0';
- X strcpy(from, buffer);
- X }
- X
- X if (strlen(subject) < 2)
- X strcpy(subject, NO_SUBJECT);
- X
- X printf(">> %s mail from %s - %s\n\r",
- X priority? "PRIORITY" : "New", from, subject);
- X}
- X
- Xparse_arpa_from(buffer, newfrom)
- Xchar *buffer, *newfrom;
- X{
- X /** try to parse the 'From:' line given... It can be in one of
- X two formats:
- X From: Dave Taylor <hpcnou!dat>
- X or From: hpcnou!dat (Dave Taylor)
- X Change 'newfrom' ONLY if sucessfully parsed this entry and
- X the resulting name is non-null!
- X **/
- X
- X char temp_buffer[SLEN], *temp;
- X register int i, j = 0;
- X
- X temp = (char *) temp_buffer;
- X temp[0] = '\0';
- X
- X no_ret(buffer); /* blow away '\n' char! */
- X
- X if (lastch(buffer) == '>') {
- X for (i=strlen("From: "); buffer[i] != '\0' && buffer[i] != '<' &&
- X buffer[i] != '('; i++)
- X temp[j++] = buffer[i];
- X temp[j] = '\0';
- X }
- X else if (lastch(buffer) == ')') {
- X for (i=strlen(buffer)-2; buffer[i] != '\0' && buffer[i] != '(' &&
- X buffer[i] != '<'; i--)
- X temp[j++] = buffer[i];
- X temp[j] = '\0';
- X reverse(temp);
- X }
- X
- X if (strlen(temp) > 0) { /* mess with buffer... */
- X
- X /* remove leading spaces... */
- X
- X while (whitespace(temp[0]))
- X temp = (char *) (temp + 1); /* increment address! */
- X
- X /* remove trailing spaces... */
- X
- X i = strlen(temp) - 1;
- X
- X while (whitespace(temp[i]))
- X temp[i--] = '\0';
- X
- X /* if anything is left, let's change 'from' value! */
- X
- X if (strlen(temp) > 0)
- X strcpy(newfrom, temp);
- X }
- X}
- X
- Xreverse(string)
- Xchar *string;
- X{
- X /** reverse string... pretty trivial routine, actually! **/
- X
- X char buffer[SLEN];
- X register int i, j = 0;
- X
- X for (i = strlen(string)-1; i >= 0; i--)
- X buffer[j++] = string[i];
- X
- X buffer[j] = '\0';
- X
- X strcpy(string, buffer);
- X}
- X
- Xlong
- Xbytes(name)
- Xchar *name;
- X{
- X /** return the number of bytes in the specified file. This
- X is to check to see if new mail has arrived.... **/
- X
- X int ok = 1;
- X extern int errno; /* system error number! */
- X struct stat buffer;
- X
- X if (stat(name, &buffer) != 0)
- X if (errno != 2)
- X exit(fprintf(stderr,"Error %d attempting fstat on %s", errno, name));
- X else
- X ok = 0;
- X
- X return(ok ? buffer.st_size : 0);
- X}
- END_OF_utils/newmail.c
- if test 7989 -ne `wc -c <utils/newmail.c`; then
- echo shar: \"utils/newmail.c\" unpacked with wrong size!?
- fi
- # end of overwriting check
- fi
- echo shar: Extracting \"utils/wnewmail.c\" \(8080 characters\)
- if test -f utils/wnewmail.c ; then
- echo shar: Will not over-write existing file \"utils/wnewmail.c\"
- else
- sed "s/^X//" >utils/wnewmail.c <<'END_OF_utils/wnewmail.c'
- X/** wnewmail.c **/
- X
- X/** Same as newmail.c but for a windowing system...
- X
- X (C) Copyright 1986, Dave Taylor
- X**/
- X
- X#include <stdio.h>
- X#include <sys/types.h>
- X#include <sys/stat.h>
- X
- X#include "defs.h"
- X
- X#ifdef AUTO_BACKGROUND
- X#include <signal.h> /* background jobs ignore some signals... */
- X#endif
- X
- Xstatic char ident[] = { WHAT_STRING };
- X
- X#define LINEFEED (char) 10
- X#define BEGINNING 0 /* seek fseek(3S) */
- X#define SLEEP_TIME 10
- X
- X#define NO_SUBJECT "(No Subject Specified)"
- X
- XFILE *mailfile;
- X
- Xlong bytes();
- Xchar *getusername();
- X
- Xmain(argc, argv)
- Xint argc;
- Xchar *argv[];
- X{
- X char filename[LONG_SLEN];
- X long size, newsize;
- X
- X if (argc > 2)
- X fprintf(stderr, "Usage: %s [filename] &\n", argv[0]);
- X else if (argc == 2) {
- X strcpy(filename, argv[1]);
- X if (access(filename, ACCESS_EXISTS) == -1) {
- X fprintf(stderr,
- X "%s: Can't open file %s to keep track of incoming mail.\n",
- X argv[0], filename);
- X exit(1);
- X }
- X }
- X else
- X sprintf(filename,"%s%s",mailhome, getusername());
- X
- X#ifdef AUTO_BACKGROUND
- X if (fork()) /* automatically puts this task in background! */
- X exit(0);
- X
- X signal(SIGINT, SIG_IGN);
- X signal(SIGQUIT, SIG_IGN);
- X signal(SIGHUP, SIG_DFL); /* so we exit when logged out */
- X#endif
- X
- X size = bytes(filename);
- X
- X mailfile = (FILE *) NULL;
- X
- X printf("Incoming Mail;\n");
- X
- X while (1) {
- X
- X#ifndef AUTO_BACKGROUND /* won't work if we're nested this deep! */
- X if (getppid() == 1) /* we've lost our shell! */
- X exit();
- X#endif
- X if (! isatty(1)) /* we're not talking to the screen any more */
- X exit();
- X
- X /** Note the lack of error checking on the fopen() (Philip Peake
- X did!) - this is okay since if it fails we don't have any
- X mail and we can sleep(60) and try again later...
- X **/
- X
- X if (mailfile == (FILE *) NULL)
- X mailfile = fopen(filename,"r");
- X
- X if ((newsize = bytes(filename)) > size) { /* new mail */
- X fseek(mailfile, size, BEGINNING); /* skip all current mail */
- X size = newsize;
- X printf("%c", 007); /* beep for new mail! */
- X read_headers();
- X }
- X else if (newsize != size) {
- X size = newsize; /* mail's been removed... */
- X (void) fclose(mailfile); /* close it and ... */
- X mailfile = (FILE *) NULL; /* let's reopen the file */
- X }
- X
- X sleep(SLEEP_TIME);
- X }
- X}
- X
- Xint
- Xread_headers()
- X{
- X /** read the headers, output as found **/
- X
- X char buffer[LONG_SLEN], from_whom[SLEN], subject[SLEN];
- X register int subj = 0, in_header = 1, count = 0, priority = 0;
- X
- X while (fgets(buffer, LONG_SLEN, mailfile) != NULL) {
- X if (first_word(buffer,"From ")) {
- X if (real_from(buffer, from_whom)) {
- X subj = 0;
- X priority = 0;
- X in_header = 1;
- X }
- X }
- X else if (in_header) {
- X if (first_word(buffer,">From"))
- X forwarded(buffer, from_whom); /* return address */
- X else if (first_word(buffer,"Subject:") ||
- X first_word(buffer,"Re:")) {
- X if (! subj++) {
- X remove_first_word(buffer);
- X strcpy(subject, buffer);
- X }
- X }
- X else if (first_word(buffer,"From:"))
- X parse_arpa_from(buffer, from_whom);
- X else if (first_word(buffer, "Priority:"))
- X priority++;
- X else if (buffer[0] == LINEFEED) {
- X in_header = 0; /* in body of message! */
- X show_header(priority, from_whom, subject);
- X from_whom[0] = 0;
- X subject[0] = 0;
- X count++;
- X }
- X }
- X }
- X return(count);
- X}
- X
- Xint
- Xreal_from(buffer, who)
- Xchar *buffer, *who;
- X{
- X /***** returns true iff 's' has the seven 'from' fields,
- X initializing the who to the sender *****/
- X
- X char junk[80];
- X
- X junk[0] = '\0';
- X sscanf(buffer, "%*s %s %*s %*s %*s %*s %s",
- X who, junk);
- X return(junk[0] != '\0');
- X}
- X
- Xforwarded(buffer, who)
- Xchar *buffer, *who;
- X{
- X /** change 'from' and date fields to reflect the ORIGINATOR of
- X the message by iteratively parsing the >From fields... **/
- X
- X char machine[80], buff[80];
- X
- X machine[0] = '\0';
- X sscanf(buffer, "%*s %s %*s %*s %*s %*s %*s %*s %*s %s",
- X who, machine);
- X
- X if (machine[0] == '\0') /* try for srm address */
- X sscanf(buffer, "%*s %s %*s %*s %*s %*s %*s %*s %s",
- X who, machine);
- X
- X if (machine[0] == '\0')
- X sprintf(buff,"anonymous");
- X else
- X sprintf(buff,"%s!%s", machine, who);
- X
- X strncpy(who, buff, 80);
- X}
- X
- X
- Xremove_first_word(string)
- Xchar *string;
- X{ /** removes first word of string, ie up to first non-white space
- X following a white space! **/
- X
- X register int loc;
- X
- X for (loc = 0; string[loc] != ' ' && string[loc] != '\0'; loc++)
- X ;
- X
- X while (string[loc] == ' ' || string[loc] == '\t')
- X loc++;
- X
- X move_left(string, loc);
- X}
- X
- Xmove_left(string, chars)
- Xchar string[];
- Xint chars;
- X{
- X /** moves string chars characters to the left DESTRUCTIVELY **/
- X
- X register int i;
- X
- X chars--; /* index starting at zero! */
- X
- X for (i=chars; string[i] != '\0' && string[i] != '\n'; i++)
- X string[i-chars] = string[i];
- X
- X string[i-chars] = '\0';
- X}
- X
- Xshow_header(priority, from, subject)
- Xint priority;
- Xchar *from, *subject;
- X{
- X /** Output header in clean format, including abbreviation
- X of return address if more than one machine name is
- X contained within it! **/
- X
- X char buffer[SLEN];
- X int loc, i=0, exc=0;
- X
- X#ifdef PREFER_UUCP
- X
- X if (chloc(from,'!') != -1 && in_string(from, BOGUS_INTERNET))
- X from[strlen(from) - strlen(BOGUS_INTERNET)] = '\0';
- X
- X#endif
- X
- X loc = strlen(from);
- X
- X while (exc < 2 && loc > 0)
- X if (from[--loc] == '!')
- X exc++;
- X
- X if (exc == 2) { /* lots of machine names! Get last one */
- X loc++;
- X while (loc < strlen(from) && loc < SLEN)
- X buffer[i++] = from[loc++];
- X buffer[i] = '\0';
- X strcpy(from, buffer);
- X }
- X
- X if (strlen(subject) < 2)
- X strcpy(subject, NO_SUBJECT);
- X
- X if (strlen(from) > 0) /* last final check... */
- X printf("%sMail from %s -- %s\n",
- X priority? "PRIORITY ": "", from, subject);
- X}
- X
- Xparse_arpa_from(buffer, newfrom)
- Xchar *buffer, *newfrom;
- X{
- X /** Try to parse the 'From:' line given... It can be in one of
- X two formats:
- X From: Dave Taylor <hpcnou!dat>
- X or From: hpcnou!dat (Dave Taylor)
- X Change 'newfrom' ONLY if sucessfully parsed this entry and
- X the resulting name is non-null!
- X **/
- X
- X char temp_buffer[SLEN], *temp;
- X register int i, j = 0;
- X
- X temp = (char *) temp_buffer;
- X temp[0] = '\0';
- X
- X no_ret(buffer); /* blow away '\n' char! */
- X
- X if (lastch(buffer) == '>') {
- X for (i=strlen("From: "); buffer[i] != '\0' && buffer[i] != '<' &&
- X buffer[i] != '('; i++)
- X temp[j++] = buffer[i];
- X temp[j] = '\0';
- X }
- X else if (lastch(buffer) == ')') {
- X for (i=strlen(buffer)-2; buffer[i] != '\0' && buffer[i] != '(' &&
- X buffer[i] != '<'; i--)
- X temp[j++] = buffer[i];
- X temp[j] = '\0';
- X reverse(temp);
- X }
- X
- X if (strlen(temp) > 0) { /* mess with buffer... */
- X
- X /* remove leading spaces... */
- X
- X while (whitespace(temp[0]))
- X temp = (char *) (temp + 1); /* increment address! */
- X
- X /* remove trailing spaces... */
- X
- X i = strlen(temp) - 1;
- X
- X while (whitespace(temp[i]))
- X temp[i--] = '\0';
- X
- X /* if anything is left, let's change 'from' value! */
- X
- X if (strlen(temp) > 0)
- X strcpy(newfrom, temp);
- X }
- X}
- X
- Xreverse(string)
- Xchar *string;
- X{
- X /** reverse string... pretty trivial routine, actually! **/
- X
- X char buffer[SLEN];
- X register int i, j = 0;
- X
- X for (i = strlen(string)-1; i >= 0; i--)
- X buffer[j++] = string[i];
- X
- X buffer[j] = '\0';
- X
- X strcpy(string, buffer);
- X}
- X
- Xlong
- Xbytes(name)
- Xchar *name;
- X{
- X /** return the number of bytes in the specified file. This
- X is to check to see if new mail has arrived.... **/
- X
- X int ok = 1;
- X extern int errno; /* system error number! */
- X struct stat buffer;
- X
- X if (stat(name, &buffer) != 0)
- X if (errno != 2)
- X exit(fprintf(stderr,"Error %d attempting fstat on %s", errno, name));
- X else
- X ok = 0;
- X
- X return(ok ? (long) buffer.st_size : 0L);
- X}
- X
- Xchar *getusername()
- X{
- X /** Getting the username on some systems is a real pain, so...
- X This routine is guaranteed to return a usable username **/
- X
- X char *return_value, *cuserid(), *getlogin();
- X
- X if ((return_value = cuserid(NULL)) == NULL)
- X if ((return_value = getlogin()) == NULL)
- X exit(printf("Newmail: I can't get username!\n"));
- X
- X return( (char *) return_value);
- X}
- END_OF_utils/wnewmail.c
- if test 8080 -ne `wc -c <utils/wnewmail.c`; then
- echo shar: \"utils/wnewmail.c\" unpacked with wrong size!?
- fi
- # end of overwriting check
- fi
- echo shar: End of archive 7 \(of 19\).
- cp /dev/null ark7isdone
- DONE=true
- for I in 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 ; do
- if test ! -f ark${I}isdone ; then
- echo shar: You still need to run archive ${I}.
- DONE=false
- fi
- done
- if test "$DONE" = "true" ; then
- echo You have unpacked all 19 archives.
- echo "See the Instructions file"
- rm -f ark[1-9]isdone ark[1-9][0-9]isdone
- fi
- ## End of shell archive.
- exit 0
-