rsalz@uunet.uu.net (Rich Salz) (04/13/89)
Submitted-by: dsinc!syd@uunet.UU.NET (Syd Weinstein) Posting-number: Volume 18, Issue 97 Archive-name: elm2.2/part18 #!/bin/sh # this is part 18 of a multipart archive # do not concatenate these parts, unpack them in order with /bin/sh # file src/opt_utils.c continued # CurArch=18 if test ! -r s2_seq_.tmp then echo "Please unpack part 1 first!" exit 1; fi ( read Scheck if test "$Scheck" != $CurArch then echo "Please unpack part $Scheck next!" exit 1; else exit 0; fi ) < s2_seq_.tmp || exit 1 echo "x - Continuing file src/opt_utils.c" sed 's/^X//' << 'SHAR_EOF' >> src/opt_utils.c Xint size; X{ X /** Return the name of the current host machine. **/ X X#ifdef XENIX X char buf[32]; X FILE *fp; X char *p; X char *strchr(); X X if ((fp = fopen("/etc/systemid", "r")) != 0) { X fgets(buf, sizeof(buf) - 1, fp); X fclose(fp); X if ((p = strchr(buf, '\n')) != NULL) X *p = '\0'; X (void) strncpy(hostname, buf, size - 1); X hostname[size - 1] = '\0'; X return 0; X } X X#else /* XENIX */ X X#ifdef DOUNAME X /** This routine compliments of Scott McGregor at the HP X Corporate Computing Center **/ X X int uname(); X struct utsname name; X X (void) uname(&name); X (void) strncpy(hostname,name.nodename,size-1); X#else X (void) strncpy(hostname, HOSTNAME, size-1); X#endif /* DOUNAME */ X X hostname[size - 1] = '\0'; X return 0; X X#endif /* XENIX */ X} X X#endif /* GETHOSTNAME */ X X Xgethostdomain(hostdom, size) /* get domain of current host */ Xchar *hostdom; Xint size; X{ X char buf[32]; X FILE *fp; X char *p; X char *strchr(); X X if ((fp = fopen(hostdomfile, "r")) != 0) { X fgets(buf, sizeof(buf) - 1, fp); X fclose(fp); X if ((p = strchr(buf, '\n')) != NULL) X *p = '\0'; X if (buf[0] != '.') { X *hostdom++ = '.'; X --size; X } X (void) strncpy(hostdom, buf, size - 1); X hostdom[size - 1] = '\0'; X } X else { X (void) strncpy(hostdom, DEFAULT_DOMAIN, size - 1); X hostdom[size - 1] = '\0'; X } X X return 0; X} X X X#ifdef NEED_CUSERID X Xchar *cuserid(uname) X char *uname; X{ X /** Added for compatibility with Bell systems, this is the last-ditch X attempt to get the users login name, after getlogin() fails. It X instantiates "uname" to the name of the user...(it also tries X to use "getlogin" again, just for luck) X **/ X /** This wasn't really compatible. According to our man page, X ** It was inconsistent. If the parameter is NULL then you return X ** the name in a static area. Else the ptr is supposed to be a X ** pointer to l_cuserid bytes of memory [probally 9 bytes]... X ** It's not mention what it should return if you copy the name X ** into the array, so I chose NULL. X ** Sept 20, 1988 X ** **WJL** X **/ X X struct passwd *password_entry, *getpwuid(); X char *name, *getlogin(); X static char buf[10]; X register returnonly = 0; X X if (uname == NULL) ++returnonly; X X if ((name = getlogin()) != NULL) { X if (returnonly) { X return(name); X } else { X strcpy(uname, name); X return name; X } X } X else X if (( password_entry = getpwuid(getuid())) != NULL) X { X if (returnonly) X { X return(password_entry->pw_name); X } X else X { X strcpy(uname, password_entry->pw_name); X return name; X } X } X else X { X return NULL; X } X} X X#endif X X#ifdef BSD X X/** some supplementary string functions for Berkeley Unix systems **/ X Xint Xtolower(ch) Xchar ch; X{ X /** This should be a macro call, but if you use this as a macro X calls to 'tolower' where the argument is a function call will X cause the function to be called TWICE which is obviously the X wrong behaviour. On the other hand, to just blindly translate X assuming the character is always uppercase can cause BIG X problems, so... X **/ X X return ( isupper(ch) ? ch - 'A' + 'a' : ch ); X} X Xint Xtoupper(ch) Xchar ch; X{ X /** see comment for above routine - tolower() **/ X X return ( islower(ch) ? ch - 'a' + 'A' : ch ); X} X Xstrspn(source, keys) Xchar *source, *keys; X{ X /** This function returns the length of the substring of X 'source' (starting at zero) that consists ENTIRELY of X characters from 'keys'. This is used to skip over a X defined set of characters with parsing, usually. X **/ X X register int loc = 0, key_index = 0; X X while (source[loc] != '\0') { X key_index = 0; X while (keys[key_index] != source[loc]) X if (keys[key_index++] == '\0') X return(loc); X loc++; X } X X return(loc); X} X Xstrcspn(source, keys) Xchar *source, *keys; X{ X /** This function returns the length of the substring of X 'source' (starting at zero) that consists entirely of X characters NOT from 'keys'. This is used to skip to a X defined set of characters with parsing, usually. X NOTE that this is the opposite of strspn() above X **/ X X register int loc = 0, key_index = 0; X X while (source[loc] != '\0') { X key_index = 0; X while (keys[key_index] != '\0') X if (keys[key_index++] == source[loc]) X return(loc); X loc++; X } X X return(loc); X} X Xchar *strtok(source, keys) Xchar *source, *keys; X{ X /** This function returns a pointer to the next word in source X with the string considered broken up at the characters X contained in 'keys'. Source should be a character pointer X when this routine is first called, then NULL subsequently. X When strtok has exhausted the source string, it will X return NULL as the next word. X X WARNING: This routine will DESTROY the string pointed to X by 'source' when first invoked. If you want to keep the X string, make a copy before using this routine!! X **/ X X register int last_ch; X static char *sourceptr; X char *return_value; X X if (source != NULL) X sourceptr = source; X X if (*sourceptr == '\0') X return(NULL); /* we hit end-of-string last time!? */ X X sourceptr += strspn(sourceptr, keys); /* skip leading crap */ X X if (*sourceptr == '\0') X return(NULL); /* we've hit end-of-string */ X X last_ch = strcspn(sourceptr, keys); /* end of good stuff */ X X return_value = sourceptr; /* and get the ret */ X X sourceptr += last_ch; /* ...value */ X X if (*sourceptr != '\0') /* don't forget if we're at END! */ X sourceptr++; /* and skipping for next time */ X X return_value[last_ch] = '\0'; /* ..ending right */ X X return((char *) return_value); /* and we're outta here! */ X} X Xchar *strpbrk(source, keys) Xchar *source, *keys; X{ X /** Returns a pointer to the first character of source that is any X of the specified keys, or NULL if none of the keys are present X in the source string. X **/ X X register int loc = 0, key_index = 0; X X while (source[loc] != '\0') { X key_index = 0; X while (keys[key_index] != '\0') X if (keys[key_index++] == source[loc]) X return((char *) (source + loc)); X loc++; X } X X return(NULL); X} X Xchar *strchr(buffer, ch) Xchar *buffer, ch; X{ X /** Returns a pointer to the first occurance of the character X 'ch' in the specified string or NULL if it doesn't occur **/ X X char *address; X X address = buffer; X X while (*address != ch) { X if (*address == '\0') X return (NULL); X address++; X } X X return ( (char *) address); X} X Xchar *strrchr(buffer, ch) Xchar *buffer, ch; X{ X /** Returns a pointer to the last occurance of the character X 'ch' in the specified string or NULL if it doesn't occur **/ X X char *address; X X address = buffer + strlen(buffer) - 1; X X while (*address != ch) { X if (address == buffer) X return (NULL); X address--; X } X X return ( (char *) address); X} X X#endif X X#ifndef TEMPNAM X/* and a tempnam for temporary files */ Xstatic int cnt = 0; X Xchar *tempnam( dir, pfx) X char *dir, *pfx; X{ X char space[SLEN]; X char *newspace; X X char *malloc(); X X if (dir == NULL) { X dir = "/usr/tmp"; X } else if (*dir == '\0') { X dir = "/usr/tmp"; X } X X if (pfx == NULL) { X pfx = ""; X } X X sprintf(space, "%s%s%d.%d", dir, pfx, getpid(), cnt); X cnt++; X X newspace = malloc(strlen(space) + 1); X if (newspace != NULL) { X strcpy(newspace, space); X } X return newspace; X} X X#endif X X#ifndef GETOPT X X/*LINTLIBRARY*/ X#define NULL 0 X#define EOF (-1) X#define ERR(s, c) if(opterr){\ X extern int strlen(), write();\ X char errbuf[2];\ X errbuf[0] = c; errbuf[1] = '\n';\ X (void) write(2, argv[0], (unsigned)strlen(argv[0]));\ X (void) write(2, s, (unsigned)strlen(s));\ X (void) write(2, errbuf, 2);} X Xextern int strcmp(); Xextern char *index(); X Xint opterr = 1; Xint optind = 1; Xint optopt; Xchar *optarg; X Xint Xgetopt(argc, argv, opts) Xint argc; Xchar **argv, *opts; X{ X static int sp = 1; X register int c; X register char *cp; X X if(sp == 1) X if(optind >= argc || X argv[optind][0] != '-' || argv[optind][1] == '\0') X return(EOF); X else if(strcmp(argv[optind], "--") == NULL) { X optind++; X return(EOF); X } X optopt = c = argv[optind][sp]; X if(c == ':' || (cp=index(opts, c)) == NULL) { X ERR(": illegal option -- ", c); X if(argv[optind][++sp] == '\0') { X optind++; X sp = 1; X } X return('?'); X } X if(*++cp == ':') { X if(argv[optind][sp+1] != '\0') X optarg = &argv[optind++][sp+1]; X else if(++optind >= argc) { X ERR(": option requires an argument -- ", c); X sp = 1; X return('?'); X } else X optarg = argv[optind++]; X sp = 1; X } else { X if(argv[optind][++sp] == '\0') { X sp = 1; X optind++; X } X optarg = NULL; X } X return(c); X} X X#endif X X#ifndef RENAME Xint rename(tmpfname, fname) Xchar *tmpfname, *fname; X{ X int status; X X (void) unlink(fname); X if ((status = link(tmpfname, fname)) != 0) X return(status); X (void) unlink(tmpfname); X return(0); X} X#endif SHAR_EOF echo "File src/opt_utils.c is complete" chmod 0444 src/opt_utils.c || echo "restore of src/opt_utils.c fails" echo "x - extracting src/options.c (Text)" sed 's/^X//' << 'SHAR_EOF' > src/options.c && X Xstatic char rcsid[] = "@(#)$Id: options.c,v 2.9 89/03/25 21:46:54 syd Exp $"; X X/******************************************************************************* X * The Elm Mail System - $Revision: 2.9 $ $State: Exp $ X * X * Copyright (c) 1986, 1987 Dave Taylor X * Copyright (c) 1988, 1989 USENET Community Trust X ******************************************************************************* X * Bug reports, patches, comments, suggestions should be sent to: X * X * Syd Weinstein, Elm Coordinator X * elm@dsinc.UUCP dsinc!elm X * X ******************************************************************************* X * $Log: options.c,v $ X * Revision 2.9 89/03/25 21:46:54 syd X * Initial 2.2 Release checkin X * X * X ******************************************************************************/ X X/** This set of routines allows the alteration of a number of paramaters X in the Elm mailer, including the following; X X calendar-file <where to put calendar entries> X display pager <how to page messages> X editor <name of composition editor> X folder-dir <folder directory> X sort-by <how to sort folders> X sent-mail <file to save outbound message copies to> X printmail <how to print messages> X full_username <your full user name for outgoing mail> X X arrow-cursor <on or off> X menu-display <on or off> X X user-level <BEGINNER|INTERMEDIATE|EXPERT> X names-only <on or off> X X And others as they seem useful. X X**/ X X#include "headers.h" X X#ifdef BSD X#undef tolower X#endif X X#undef onoff X#define onoff(n) (n == 1? "ON ":"OFF") X Xchar *one_liner_for(), *level_name(); Xunsigned long sleep(); X Xoptions() X{ X /** change options... **/ X /* return: X * > 0 if restort was done - to indicate we might need to X * change the page of our headers as a consequence X * of the new sort order X * < 0 if user entered 'x' to quit elm immediately X * 0 otherwise X */ X X int ch, X resort = 0; X char *strcpy(), X temp[SLEN]; /* needed when an option is run through X * expand_env(), because that function X * is destructive of the original X */ X X display_options(); X X clearerr(stdin); X X while(1) { X ClearLine(LINES-4); X X Centerline(LINES-4, X "Select first letter of option line, '>' to save, or 'i' to return to index."); X X PutLine0(LINES-2, 0, "Command: "); X X ch = ReadCh(); X ch = tolower(ch); X X clear_error(); /* remove possible "sorting" message etc... */ X X one_liner(one_liner_for(ch)); X X switch (ch) { X case 'c' : optionally_enter(raw_calendar_file, 2, 23, FALSE, FALSE); X strcpy(temp, raw_calendar_file); X expand_env(calendar_file, temp); X break; X case 'd' : optionally_enter(raw_pager, 3, 23, FALSE, FALSE); X strcpy(temp, raw_pager); X expand_env(pager, temp); X clear_pages = (equal(pager, "builtin+") || X equal(pager, "internal+")); X break; X case 'e' : optionally_enter(raw_editor, 4, 23, FALSE, FALSE); X strcpy(temp, raw_editor); X expand_env(editor, temp); X break; X case 'f' : optionally_enter(raw_folders, 5, 23, FALSE, FALSE); X strcpy(temp, raw_folders); X expand_env(folders, temp); X break; X case 's' : if(change_sort(6,23)) resort++; break; X case 'o' : optionally_enter(raw_sentmail, 7, 23, FALSE, FALSE); X strcpy(temp, raw_sentmail); X expand_env(sent_mail, temp); X break; X case 'p' : optionally_enter(raw_printout, 8, 23, FALSE, FALSE); X strcpy(temp, raw_printout); X expand_env(printout, temp); X break; X case 'y' : optionally_enter(full_username, 9, 23, FALSE, FALSE); X break; X case 'a' : on_or_off(&arrow_cursor, 12, 23); break; X case 'm' : on_or_off(&mini_menu, 13, 23); X headers_per_page = LINES - (mini_menu ? 13 : 8); break; X X case 'u' : switch_user_level(&user_level,15, 23); break; X case 'n' : on_or_off(&names_only, 16, 23); break; X X case '?' : options_help(); X PutLine0(LINES-2,0,"Command: "); break; X X case '>' : printf("Save options in .elm/elmrc..."); X fflush(stdout); save_options(); break; X X case 'x' : return(-1); /* exit elm */ X case 'q' : /* pop back up to previous level, in this case == 'i' */ X case 'i' : /* return to index screen */ X return(resort ? 1 : 0); X case ctrl('L'): display_options(); break; X default: error("Command unknown!"); X } X X } X} X Xdisplay_options() X{ X /** Display all the available options.. **/ X X char *sort_name(); X X ClearScreen(); X Centerline(0,"-- ELM Options Editor --"); X X#ifdef ENABLE_CALENDAR X PutLine1(2, 0, "C)alendar file : %s", raw_calendar_file); X#endif X PutLine1(3, 0, "D)isplay mail using : %s", raw_pager); X PutLine1(4, 0, "E)ditor : %s", raw_editor); X PutLine1(5, 0, "F)older directory : %s", raw_folders); X PutLine1(6, 0, "S)orting criteria : %s", sort_name(FULL)); X PutLine1(7, 0, "O)utbound mail saved : %s", raw_sentmail); X PutLine1(8, 0, "P)rint mail using : %s", raw_printout); X PutLine1(9, 0, "Y)our full name : %s", full_username); X X PutLine1(12,0, "A)rrow cursor : %s", onoff(arrow_cursor)); X PutLine1(13,0, "M)enu display : %s", onoff(mini_menu)); X X PutLine1(15,0, "U)ser level : %s", level_name(user_level)); X PutLine1(16,0, "N)ames only : %s", onoff(names_only)); X} X Xon_or_off(var, x, y) Xint *var, x,y; X{ X /** 'var' field at x.y toggles between on and off... **/ X X char ch; X X PutLine0(x, y+6, X "(use <space> to toggle, any other key to leave)"); X X MoveCursor(x,y+3); /* at end of value... */ X X do { X ch = ReadCh(); X X if (ch == SPACE) { X *var = ! *var; X PutLine0(x,y, onoff(*var)); X } X } while (ch == SPACE); X X MoveCursor(x,y+4); CleartoEOLN(); /* remove help prompt */ X} X X Xswitch_user_level(ulevel, x, y) Xint *ulevel, x, y; X{ X /** step through possible user levels... **/ X X PutLine0(x, y+20, "<space> to change"); X X MoveCursor(x,y); /* at end of value... */ X X while (ReadCh() == ' ') { X *ulevel = (*ulevel >= 2? 0 : *ulevel + 1); X PutLine1(x,y, "%s", level_name(*ulevel)); X } X X MoveCursor(x,y+20); CleartoEOLN(); /* remove help prompt */ X} X Xchange_sort(x, y) Xint x,y; X{ X /** change the sorting scheme... **/ X /** return !0 if new sort order, else 0 **/ X X int last_sortby, /* so we know if it changes... */ X sign = 1; /* are we reverse sorting?? */ X int ch; /* character typed in ... */ X X last_sortby = sortby; /* remember current ordering */ X X PutLine0(x, COLUMNS-29, "(SPACE for next, or R)everse)"); X sort_one_liner(sortby); X MoveCursor(x, y); X X do { X ch = ReadCh(); X ch = tolower(ch); X switch (ch) { X case SPACE : if (sortby < 0) { X sign = -1; X sortby = - sortby; X } X else sign = 1; /* insurance! */ X sortby = sign * ((sortby + 1) % (STATUS+2)); X if (sortby == 0) sortby = sign; /* snicker */ X PutLine0(x, y, sort_name(PAD)); X sort_one_liner(sortby); X MoveCursor(x, y); X break; X X case 'r' : sortby = - sortby; X PutLine0(x, y, sort_name(PAD)); X sort_one_liner(sortby); X MoveCursor(x, y); X } X } while (ch == SPACE || ch == 'r'); X X MoveCursor(x, COLUMNS-30); CleartoEOLN(); X X if (sortby != last_sortby) { X error("Resorting folder..."); X sleep(1); X sort_mailbox(message_count, 0); X } X ClearLine(LINES-2); /* clear sort_one_liner()! */ X return(sortby-last_sortby); X} X Xone_liner(string) Xchar *string; X{ X /** A single-line description of the selected item... **/ X X ClearLine(LINES-4); X Centerline(LINES-4, string); X} X Xsort_one_liner(sorting_by) Xint sorting_by; X{ X /** A one line summary of the particular sorting scheme... **/ X X ClearLine(LINES-2); X X switch (sorting_by) { X X case -SENT_DATE : Centerline(LINES-2, X"This sort will order most-recently-sent to least-recently-sent"); break; X case -RECEIVED_DATE : Centerline(LINES-2, X"This sort will order most-recently-received to least-recently-received"); X break; X case -MAILBOX_ORDER : Centerline(LINES-2, X"This sort will order most-recently-added-to-folder to least-recently"); X break; X case -SENDER : Centerline(LINES-2, X"This sort will order by sender name, in reverse alphabetical order"); break; X case -SIZE : Centerline(LINES-2, X"This sort will order messages by longest to shortest"); break; X case -SUBJECT : Centerline(LINES-2, X"This sort will order by subject, in reverse alphabetical order"); break; X case -STATUS : Centerline(LINES-2, X"This sort will order by reverse status - Deleted through Tagged..."); break; X X case SENT_DATE : Centerline(LINES-2, X"This sort will order least-recently-sent to most-recently-sent"); break; X case RECEIVED_DATE : Centerline(LINES-2, X"This sort will order least-recently-received to most-recently-received"); X break; X case MAILBOX_ORDER : Centerline(LINES-2, X"This sort will order least-recently-added-to-folder to most-recently"); X break; X case SENDER : Centerline(LINES-2, X "This sort will order by sender name"); break; X case SIZE : Centerline(LINES-2, X "This sort will order messages by shortest to longest"); X break; X case SUBJECT : Centerline(LINES-2, X "This sort will order messages by subject"); break; X case STATUS : Centerline(LINES-2, X"This sort will order by status - Tagged through Deleted..."); break; X } X} X Xchar *one_liner_for(c) Xchar c; X{ X /** returns the one-line description of the command char... **/ X X switch (c) { X case 'c' : return( X"This is the file where calendar entries from messages are saved."); X X case 'd' : return( X"This is the program invoked to display individual messages (try 'builtin')"); X X case 'e' : return( X"This is the editor that will be used for sending messages, etc."); X X case 'f' : return( X"This is the folders directory used when '=' (etc) is used in filenames"); X X case 'm' : return( X"This determines if you have the mini-menu displayed or not"); X X case 'n' : return( X"Whether to display the names and addresses on mail, or names only"); X case 'o' : return( X"This is where copies of outbound messages are saved automatically."); X X case 'p' : return( X"This is how printouts are generated. \"%s\" will be replaced by the filename."); X X case 's' : return( X"This is used to specify the sorting criteria for the folders"); X X case 'y' : return( X"When mail is sent out, this is what your full name will be recorded as."); X X case 'a' : return( X"This defines whether the ELM cursor is an arrow or a highlight bar."); X X case 'u' : return( X"The level of knowledge you have about the ELM mail system."); X X default : return(""); /* nothing if we don't know! */ X } X} X Xoptions_help() X{ X /** help menu for the options screen... **/ X X char c, *ptr; X X Centerline(LINES-3, X "Enter the key you want help on, '?' for a list, or '.' to exit help"); X X lower_prompt("Key : "); X X while ((c = ReadCh()) != '.') { X c = tolower(c); X if (c == '?') { X display_helpfile(OPTIONS_HELP); X display_options(); X return; X } X if ((ptr = one_liner_for(c)) != NULL) X error2("%c = %s.", c, ptr); X else X error1("%c isn't used in this section.", c); X lower_prompt("Key : "); X } X} X Xchar *level_name(n) Xint n; X{ X /** return the 'name' of the level... **/ X X switch (n) { X case 0 : return("Beginning User "); X case 1 : return("Intermediate User"); X default: return("Expert User "); X } X} SHAR_EOF chmod 0444 src/options.c || echo "restore of src/options.c fails" echo "x - extracting src/out_utils.c (Text)" sed 's/^X//' << 'SHAR_EOF' > src/out_utils.c && X Xstatic char rcsid[] = "@(#)$Id: out_utils.c,v 2.5 89/03/25 21:46:56 syd Exp $"; X X/******************************************************************************* X * The Elm Mail System - $Revision: 2.5 $ $State: Exp $ X * X * Copyright (c) 1986, 1987 Dave Taylor X * Copyright (c) 1988, 1989 USENET Community Trust X ******************************************************************************* X * Bug reports, patches, comments, suggestions should be sent to: X * X * Syd Weinstein, Elm Coordinator X * elm@dsinc.UUCP dsinc!elm X * X ******************************************************************************* X * $Log: out_utils.c,v $ X * Revision 2.5 89/03/25 21:46:56 syd X * Initial 2.2 Release checkin X * X * X ******************************************************************************/ X X/** This file contains routines used for output in the ELM program. X X**/ X X#include "headers.h" X X Xstatic char err_buffer[SLEN]; /* store last error message */ X Xstatic char central_message_buffer[SLEN]; X Xchar *strcpy(); X Xshow_last_error() X{ X /** rewrite last error message! **/ X X error(err_buffer); X} X Xclear_error() X{ X MoveCursor(LINES,0); X CleartoEOLN(); X err_buffer[0] = '\0'; X} X Xset_error(s) Xchar *s; X{ X strcpy(err_buffer, s); X} X Xerror(s) Xchar *s; X{ X /** outputs error 's' to screen at line 22, centered! **/ X X if(batch_only) X printf("%s\n\r", s); X else { X MoveCursor(LINES,0); X CleartoEOLN(); X PutLine0(LINES,(COLUMNS-strlen(s))/2,s); X fflush(stdout); X } X strcpy(err_buffer, s); /* save it too! */ X} X X/*VARARGS1*/ X Xerror1(s, a) Xchar *s, *a; X{ X /** same as error, but with a 'printf' argument **/ X char buffer[SLEN]; X X sprintf(buffer,s,a); X error(buffer); X} X X/*VARARGS1*/ X Xerror2(s, a1, a2) Xchar *s, *a1, *a2; X{ X /** same as error, but with two 'printf' arguments **/ X char buffer[SLEN]; X X sprintf(buffer,s, a1, a2); X error(buffer); X} X X/*VARARGS1*/ X Xerror3(s, a1, a2, a3) Xchar *s, *a1, *a2, *a3; X{ X /** same as error, but with three 'printf' arguments **/ X char buffer[SLEN]; X X sprintf(buffer,s, a1, a2, a3); X error(buffer); X} X Xlower_prompt(s) Xchar *s; X{ X /** prompt user for input on LINES-1 line, left justified **/ X X PutLine0(LINES-1,0,s); X CleartoEOLN(); X} X Xprompt(s) Xchar *s; X{ X /** prompt user for input on LINES-3 line, left justified **/ X X PutLine0(LINES-3,0,s); X CleartoEOLN(); X} X X Xset_central_message(string, arg) Xchar *string, *arg; X{ X /** set up the given message to be displayed in the center of X the current window **/ X X sprintf(central_message_buffer, string, arg); X} X Xdisplay_central_message() X{ X /** display the message if set... **/ X X if (central_message_buffer[0] != '\0') { X ClearLine(LINES-15); X Centerline(LINES-15, central_message_buffer); X fflush(stdout); X } X} X Xclear_central_message() X{ X /** clear the central message buffer **/ X X central_message_buffer[0] = '\0'; X} SHAR_EOF chmod 0444 src/out_utils.c || echo "restore of src/out_utils.c fails" echo "x - extracting src/pattern.c (Text)" sed 's/^X//' << 'SHAR_EOF' > src/pattern.c && X Xstatic char rcsid[] = "@(#)$Id: pattern.c,v 2.10 89/03/25 21:46:57 syd Exp $"; X X/******************************************************************************* X * The Elm Mail System - $Revision: 2.10 $ $State: Exp $ X * X * Copyright (c) 1986, 1987 Dave Taylor X * Copyright (c) 1988, 1989 USENET Community Trust X ******************************************************************************* X * Bug reports, patches, comments, suggestions should be sent to: X * X * Syd Weinstein, Elm Coordinator X * elm@dsinc.UUCP dsinc!elm X * X ******************************************************************************* X * $Log: pattern.c,v $ X * Revision 2.10 89/03/25 21:46:57 syd X * Initial 2.2 Release checkin X * X * X ******************************************************************************/ X X/** General pattern matching for the ELM mailer. X X**/ X X#include <errno.h> X X#include "headers.h" X Xstatic char pattern[SLEN] = { "" }; Xstatic char alt_pattern[SLEN] = { "" }; X Xextern int errno; X Xchar *error_name(), *shift_lower(), *strcpy(); X Xint Xmeta_match(function) Xint function; X{ X char ch; X X /** Perform specific function based on whether an entered string X matches either the From or Subject lines.. X Return TRUE if the current message was matched, else FALSE. X **/ X X register int i, tagged=0, count=0, curtag = 0; X static char meta_pattern[SLEN]; X X PutLine1(LINES-3, strlen("Command: "), X "%s messages that match pattern...", X function==TAGGED?"Tag": function==DELETED?"Delete":"Undelete"); X X if (function == TAGGED) { /* are messages already tagged??? */ X for (i=0; i < message_count; i++) X if (ison(headers[i]->status,TAGGED)) X tagged++; X X if (tagged) { X if (tagged > 2) X PutLine0(LINES-2,0, "Some messages are already tagged."); X else X PutLine0(LINES-2,0, "A message is already tagged."); X X Write_to_screen("Remove tag%s? y%c", 2, plural(tagged),BACKSPACE); X X ch = ReadCh(); X if (tolower(ch) != 'n') { /* remove tags... */ X Write_to_screen("Yes.", 0); X for (i=0; i < message_count; i++) { X clearit(headers[i]->status,TAGGED); X show_new_status(i); X } X } else X Write_to_screen("No.", 0); X } X } X X PutLine0(LINES-2,0, "Enter pattern: "); CleartoEOLN(); X X optionally_enter(meta_pattern, LINES-2, strlen("Enter pattern: "), X FALSE, FALSE); X X if (strlen(meta_pattern) == 0) { X ClearLine(LINES-2); X return(curtag); X } X X strcpy(meta_pattern, shift_lower(meta_pattern)); /* lowercase it */ X X for (i = 0; i < message_count; i++) { X if (from_matches(i, meta_pattern)) { X if ((selected && headers[i]->status & VISIBLE) || ! selected) { X if (function == UNDELETE) X clearit(headers[i]->status, DELETED); X else X setit(headers[i]->status, function); X show_new_status(i); X if(i == current - 1) curtag++; X count++; X } X } X else if (subject_matches(i, meta_pattern)) { X if ((selected && headers[i]->status & VISIBLE) || ! selected) { X if (function == UNDELETE) X clearit(headers[i]->status, DELETED); X else X setit(headers[i]->status, function); X show_new_status(i); X if(i == current - 1) curtag++; X count++; X } X } X } X X ClearLine(LINES-2); /* remove "pattern: " prompt */ X X if (count > 0) X error3("%s %d messsage%s.", X function==TAGGED? "Tagged" : X function==DELETED? "Marked for deletion" : "Undeleted", X count, plural(count)); X else X error1("No matches. No messages %s.", X function==TAGGED? "tagged" : X function==DELETED? "marked for deletion": "undeleted"); X X return(curtag); X} X Xint Xpattern_match() X{ X /** Get a pattern from the user and try to match it with the X from/subject lines being displayed. If matched (ignoring X case), move current message pointer to that message, if X not, error and return ZERO **/ X X register int i; X X PutLine0(LINES-3,40,"/ = Match anywhere in messages."); X X PutLine0(LINES-1,0, "Match pattern:"); X X if (pattern_enter(pattern, alt_pattern, LINES-1, 16, X "Match pattern (in entire folder):")) X if (strlen(alt_pattern) > 0) { X strcpy(alt_pattern, shift_lower(alt_pattern)); X return(match_in_message(alt_pattern)); X } X else X return(1); X X if (strlen(pattern) == 0) X return(0); X else X strcpy(pattern, shift_lower(pattern)); X X for (i = current; i < message_count; i++) { X if (from_matches(i, pattern)) { X if (!selected || (selected && headers[i]->status & VISIBLE)) { X current = ++i; X return(1); X } X } X else if (subject_matches(i, pattern)) { X if (!selected || (selected && headers[i]->status & VISIBLE)) { X current = ++i; X return(1); X } X } X } X X return(0); X} X Xint Xfrom_matches(message_number, pat) Xint message_number; Xchar *pat; X{ X /** Returns true iff the pattern occurs in it's entirety X in the from line of the indicated message **/ X X return( in_string(shift_lower(headers[message_number]->from), X pat) ); X} X Xint Xsubject_matches(message_number, pat) Xint message_number; Xchar *pat; X{ X /** Returns true iff the pattern occurs in it's entirety X in the subject line of the indicated message **/ X X return( in_string(shift_lower(headers[message_number]->subject), X pat) ); X} X Xmatch_in_message(pat) Xchar *pat; X{ X /** Match a string INSIDE a message...starting at the current X message read each line and try to find the pattern. As X soon as we do, set current and leave! X Returns 1 if found, 0 if not X **/ X X char buffer[LONG_STRING]; X int message_number, lines, line; X X message_number = current-1; X X error("Searching folder for pattern..."); X X while (message_number < message_count) { X X if (fseek(mailfile, headers[message_number]->offset, 0L) == -1) { X X dprint(1, (debugfile, X "Error: seek %ld bytes into file failed. errno %d (%s)\n", X headers[message_number]->offset, errno, X "match_in_message")); X error2("ELM [match] failed looking %ld bytes into file (%s).", X headers[message_number]->offset, error_name(errno)); X return(1); /* fake it out to avoid replacing error message */ X } X X line = 0; X lines = headers[message_number]->lines; X X while (fgets(buffer, LONG_STRING, mailfile) != NULL && line < lines) { X X if(buffer[strlen(buffer)-1] == '\n') line++; X X if (in_string(shift_lower(buffer), pat)) { X current = message_number+1; X clear_error(); X return(1); X } X } X X /** now we've passed the end of THIS message...increment and X continue the search with the next message! **/ X X message_number++; X } X X return(0); X} SHAR_EOF chmod 0444 src/pattern.c || echo "restore of src/pattern.c fails" echo "x - extracting src/pmalloc.c (Text)" sed 's/^X//' << 'SHAR_EOF' > src/pmalloc.c && X Xstatic char rcsid[] = "@(#)$Id: pmalloc.c,v 2.3 89/03/25 21:46:59 syd Exp $"; X X/******************************************************************************* X * The Elm Mail System - $Revision: 2.3 $ $State: Exp $ X * X * Copyright (c) 1986, 1987 Dave Taylor X * Copyright (c) 1988, 1989 USENET Community Trust X ******************************************************************************* X * Bug reports, patches, comments, suggestions should be sent to: X * X * Syd Weinstein, Elm Coordinator X * elm@dsinc.UUCP dsinc!elm X * X ******************************************************************************* X * $Log: pmalloc.c,v $ X * Revision 2.3 89/03/25 21:46:59 syd X * Initial 2.2 Release checkin X * X * X ******************************************************************************/ X X/** This routine contains a cheap permanent version of the malloc call to X speed up the initial allocation of the weedout headers and the uuname X data. X X This routine is originally from Jim Davis of HP Labs, with some X mods by me. X**/ X X#include <stdio.h> X#include "defs.h" X X/*VARARGS0*/ X Xchar *pmalloc(size) Xint size; X{ X /** return the address of a specified block **/ X X static char *our_block = NULL; X static int free_mem = 0; X X char *return_value, *malloc(); X X /** if bigger than our threshold, just do the real thing! **/ X X if (size > PMALLOC_THRESHOLD) X return(malloc(size)); X X /** if bigger than available space, get more, tossing what's left **/ X X if (size > free_mem) { X if ((our_block = malloc(PMALLOC_BUFFER_SIZE)) == NULL) { X fprintf(stderr, "\n\r\n\rCouldn't malloc %d bytes!!\n\r\n\r", X PMALLOC_BUFFER_SIZE); X leave(); X } X our_block += 4; /* just for safety, don't give back true address */ X free_mem = PMALLOC_BUFFER_SIZE-4; X } X X return_value = our_block; /* get the memory */ X size = ((size+3)/4)*4; /* Go to quad byte boundary */ X our_block += size; /* use it up */ X free_mem -= size; /* and decrement */ X X return( (char *) return_value); X} SHAR_EOF chmod 0444 src/pmalloc.c || echo "restore of src/pmalloc.c fails" echo "x - extracting src/quit.c (Text)" sed 's/^X//' << 'SHAR_EOF' > src/quit.c && X Xstatic char rcsid[] = "@(#)$Id: quit.c,v 2.15 89/03/25 21:47:00 syd Exp $"; X X/******************************************************************************* X * The Elm Mail System - $Revision: 2.15 $ $State: Exp $ X * X * Copyright (c) 1986, 1987 Dave Taylor X * Copyright (c) 1988, 1989 USENET Community Trust X ******************************************************************************* X * Bug reports, patches, comments, suggestions should be sent to: X * X * Syd Weinstein, Elm Coordinator X * elm@dsinc.UUCP dsinc!elm X * X ******************************************************************************* X * $Log: quit.c,v $ X * Revision 2.15 89/03/25 21:47:00 syd X * Initial 2.2 Release checkin X * X * X ******************************************************************************/ X X/** quit: leave the current folder and quit the program. X X**/ X X#include "headers.h" X Xlong bytes(); X Xquit(prompt) Xint prompt; X{ X /* a wonderfully short routine!! */ X X if (leave_mbox(FALSE, TRUE, prompt) == -1) X /* new mail - leave not done - can't change to another file yet X * check for change in mailfile_size in main() will do the work X * of calling newmbox to add in the new messages to the current X * file and fix the sorting sequence that leave_mbox may have X * changed for its own purposes */ X return; X X leave(); X} X Xint Xresync() X{ X /** Resync on the current folder. Leave current and read it back in. X Return indicates whether a redraw of the screen is needed. X **/ X X if(leave_mbox(TRUE, FALSE, TRUE) ==-1) X /* new mail - leave not done - can't change to another file yet X * check for change in mailfile_size in main() will do the work X * of calling newmbox to add in the new messages to the current X * file and fix the sorting sequence that leave_mbox may have X * changed for its own purposes */ X return(FALSE); X X newmbox(cur_folder, FALSE); X return(TRUE); X} X Xchange_file() X{ X /* Prompt user for name of folder to change to. X * If all okay with that folder, leave the current folder. X * If leave goes okay (i.e. no new messages in current folder), X * change to the folder that the user specified. X * X * Return value indicates whether a redraw is needed. X */ X X int redraw = FALSE; X char newfile[SLEN]; X static char helpmsg[LONG_STRING]; X X char *nameof(); X X X /* get new file name */ X X MoveCursor(LINES-3, 30); X CleartoEOS(); X PutLine0(LINES-3, 38, "(Use '?' for help/to list your folders.)"); X PutLine0(LINES-2,0,"Name of new folder: "); X while(1) { X newfile[0] = '\0'; X (void) optionally_enter(newfile, LINES-2, 21, FALSE, FALSE); X clear_error(); X X if(*newfile == '\0') { /* if user didn't enter a file name */ X MoveCursor(LINES-3, 30); /* abort changing file process */ X CleartoEOS(); X return(redraw); X X } else if (strcmp(newfile, "?") == 0) { X X /* user wants to list folders */ X if(!*helpmsg) /* format helpmsg if not yet done */ X X strcpy(helpmsg, X "\n\r\n\rEnter: <nothing> to not change to a new folder,"); X strcat(helpmsg, X "\n\r '!' to change to your incoming mailbox ("); X strcat(helpmsg, defaultfile); X strcat(helpmsg, X ")\n\r '>' to change to your \"received\" folder ("); X strcat(helpmsg, nameof(recvd_mail)); X strcat(helpmsg, X ")\n\r '<' to change to your \"sent\" folder ("); X strcat(helpmsg, nameof(sent_mail)); X strcat(helpmsg, ")\n\r or a filename"); X strcat(helpmsg, X " (leading '=' denotes your folder directory "); X strcat(helpmsg, folders); X strcat(helpmsg, ").\n\r"); X X list_folders(4, helpmsg); X PutLine0(LINES-2,0,"Name of new folder: "); /* reprompt */ X redraw = TRUE; /* we'll need to clean the screen */ X X } else { X X /* user entered a file name - expand it */ X if (! expand_filename(newfile, TRUE)) X continue; /* prompt again */ X X /* don't accept the same file as the current */ X if (strcmp(newfile, cur_folder) == 0) { X error("Already reading that folder!"); X continue; /* prompt again */ X } X X /* Make sure this is a file the user can open, unless it's the X * default mailfile, which is openable even if empty */ X if (strcmp(newfile, defaultfile) != 0) { X if (can_access(newfile, READ_ACCESS)) { X error1("Can't open folder '%s' for reading!", newfile); X continue; /* prompt again */ X } X } X break; /* exit loop - we got the name of a good file */ X } X } X X /* All's clear with the new file to go ahead and leave the current. */ X MoveCursor(LINES-3, 30); X CleartoEOS(); X X if(leave_mbox(FALSE, FALSE, TRUE) ==-1) { X /* new mail - leave not done - can't change to another file yet X * check for change in mailfile_size in main() will do the work X * of calling newmbox to add in the new messages to the current X * file and fix the sorting sequence that leave_mbox may have X * changed for its own purposes */ X return(redraw); X } X X redraw = 1; X newmbox(newfile, FALSE); X return(redraw); X} SHAR_EOF chmod 0444 src/quit.c || echo "restore of src/quit.c fails" echo "x - extracting src/read_rc.c (Text)" sed 's/^X//' << 'SHAR_EOF' > src/read_rc.c && X Xstatic char rcsid[] = "@(#)$Id: read_rc.c,v 2.26 89/03/29 15:47:27 syd Exp $"; X X/******************************************************************************* X * The Elm Mail System - $Revision: 2.26 $ $State: Exp $ X * X * Copyright (c) 1986, 1987 Dave Taylor X * Copyright (c) 1988, 1989 USENET Community Trust X ******************************************************************************* X * Bug reports, patches, comments, suggestions should be sent to: X * X * Syd Weinstein, Elm Coordinator X * elm@dsinc.UUCP dsinc!elm X * X ******************************************************************************* X * $Log: read_rc.c,v $ X * Revision 2.26 89/03/29 15:47:27 syd X * Enable backwards compatibility with the elmrc option "alwaysleave" X * that we obsoleted recently. X * From: Rob Bernardo <rob@pbhyf.PacBell.COM> X * X * Revision 2.25 89/03/25 21:47:01 syd X * Initial 2.2 Release checkin X * X * X ******************************************************************************/ X X/** This file contains programs to allow the user to have a .elm/elmrc file X in their home directory containing any of the following: X X fullname= <username string> X maildir = <directory> X sentmail = <file> X editor = <editor> X receviedmail= <file> X calendar= <calendar file name> X shell = <shell> X print = <print command> X weedout = <list of headers to weed out> X prefix = <copied message prefix string> X pager = <command to use for displaying messages> X X escape = <single character escape, default = '~' > X X-- X signature = <.signature file for all outbound mail> XOR: X localsignature = <.signature file for local mail> X remotesignature = <.signature file for non-local mail> X-- X X bounceback= <hop count threshold, or zero to disable> X timeout = <seconds for main menu timeout or zero to disable> X userlevel = <0=amateur, 1=okay, 2 or greater = expert!> X X sortby = <sent, received, from, size, subject, mailbox, status> X X alternatives = <list of addresses that forward to us> X X and/or the logical arguments: X X autocopy [on|off] X askcc [on|off] X copy [on|off] X resolve [on|off] X weed [on|off] X noheader [on|off] X titles [on|off] X savebyname [on|off] X movepage [on|off] X pointnew [on|off] X hpkeypad [on|off] X hpsoftkeys [on|off] X alwayskeep [on|off] X alwaysstore [on|off] X alwaysdel [on|off] X arrow [on|off] X menus [on|off] X forms [on|off] X warnings [on|off] X names [on|off] X ask [on|off] X keepempty [on|off] X promptafter[on|off] X X X Lines starting with '#' are considered comments and are not checked X any further! X X Modified 10/85 to know about "Environment" variables.. X Modified 12/85 for the 'prefix' option X Modified 2/86 for the new 3.3 flags X Modified 8/86 (was I supposed to be keeping this up to date?) X**/ X X#include <ctype.h> X#include "headers.h" X X#ifdef BSD X#undef tolower X#endif X Xextern char *pmalloc(); Xextern int errno; X Xchar *error_name(), *error_description(), *shift_lower(), X *strtok(), *getenv(), *strcpy(); Xvoid exit(); X X#define metachar(c) (c == '+' || c == '%' || c == '=') X X#define NOTWEEDOUT 0 X#define WEEDOUT 1 X#define ALTERNATIVES 2 X Xread_rc_file() X{ X /** this routine does all the actual work of reading in the X .rc file... **/ X X FILE *file; X char buffer[SLEN], filename[SLEN], *cp, word1[SLEN], word2[SLEN]; X register int i, last = NOTWEEDOUT, lineno = 0, ch, X rc_has_recvdmail = 0, rc_has_sentmail = 0, errors = 0; X X /* Establish some defaults in case elmrc is incomplete or not there. X * Defaults for other elmrc options were established in their X * declaration - in elm.h. And defaults for sent_mail and recvd_mail X * are established after the elmrc is read in since these default X * are based on the folders directory name, which may be given X * in the emrc. X * Also establish alternative_editor here since it is based on X * the default editor and not on the one that might be given in the X * elmrc. X */ X X default_weedlist(); X X alternative_addresses = NULL; /* none yet! */ X X raw_local_signature[0] = raw_remote_signature[0] = X local_signature[0] = remote_signature[0] = '\0'; X /* no defaults for those */ X X strcpy(raw_shell,((cp = getenv("SHELL")) == NULL)? default_shell : cp); X strcpy(shell, raw_shell); X X strcpy(raw_pager,((cp = getenv("PAGER")) == NULL)? default_pager : cp); X strcpy(pager, raw_pager); X X strcpy(raw_editor,((cp = getenv("EDITOR")) == NULL)? default_editor:cp); X strcpy(alternative_editor, raw_editor); X strcpy(editor, raw_editor); X X strcpy(raw_printout, default_printout); X strcpy(printout, raw_printout); X X sprintf(raw_folders, "%s/%s", home, default_folders); X strcpy(folders, raw_folders); X X sprintf(raw_calendar_file, "%s/%s", home, dflt_calendar_file); X strcpy(calendar_file, raw_calendar_file); X X /* see if the user has a $HOME/.elm directory */ X sprintf(filename, "%s/.elm", home); X if (access(filename, 00) == -1) { X if(batch_only) { X printf("\n\rNotice:\ X\n\rThis version of ELM requires the use of a .elm directory to store your\ X\n\relmrc and alias files. I'd like to create the directory .elm for you\ X\n\rand set it up, but I can't in \"batch mode\".\ X\n\rPlease run ELM in \"normal mode\" first.\n\r"); X exit(0); X } X X printf("\n\rNotice:\ X\n\rThis version of ELM requires the use of a .elm directory in your home\ X\n\rdirectory to store your elmrc and alias files. Shall I create the\ X\n\rdirectory .elm for you and set it up (y/n)? y%c",BACKSPACE); X X fflush(stdout); X ch=getchar(); X if (ch == 'n' || ch == 'N') { X printf("No.\n\rVery well. I won't create it.\ X \n\rBut, you may run into difficulties later.\n\r"); X sleep(4); X } X else { X printf("Yes.\n\rGreat! I'll do it now.\n\r"); X create_new_elmdir(); X } X } X X /* Look for the elmrc file */ X sprintf(filename,"%s/%s", home, elmrcfile); X if ((file = fopen(filename, "r")) == NULL) { X dprint(2,(debugfile,"Warning:User has no \".elm/elmrc\" file\n\n")); X X /* look for old-style .elmrc file in $HOME */ X sprintf(filename, "%s/.elmrc", home); X if (access(filename, 00) != -1) { X move_old_files_to_new(); X X /* try to open elmrc file again */ X sprintf(filename,"%s/%s", home, elmrcfile); X if((file = fopen(filename, "r")) == NULL) { X dprint(2, (debugfile, X "Warning: could not open new \".elm/elmrc\" file.\n")); X dprint(2, (debugfile, "** %s - %s **\n", error_name(errno), X error_description(errno))); X printf("Warning: could not open new \".elm/elmrc\" file!"); X printf(" Using default parameters.\n\r"); X sleep(4); X } X } X } X X if(file) { X while (fgets(buffer, SLEN, file) != NULL) { X lineno++; X no_ret(buffer); /* remove return */ X if (buffer[0] == '#') { /* comment */ X last = NOTWEEDOUT; X continue; X } X if (strlen(buffer) < 2) { /* empty line */ X last = NOTWEEDOUT; X continue; X } X X if(breakup(buffer, word1, word2) == -1) X continue; /* word2 is null - let default value stand */ X X strcpy(word1, shift_lower(word1)); /* to lower case */ X X if (equal(word1,"maildir") || equal(word1,"folders")) { X strcpy(raw_folders, word2); X expand_env(folders, word2); X last = NOTWEEDOUT; X } X else if (equal(word1, "fullname") || equal(word1,"username") || X equal(word1, "name")) { X strcpy(full_username, word2); X last = NOTWEEDOUT; X } X else if (equal(word1, "prefix")) { X for (i=0; i < strlen(word2); i++) X prefixchars[i] = (word2[i] == '_' ? ' ' : word2[i]); X prefixchars[i] = '\0'; X X last = NOTWEEDOUT; X } X else if (equal(word1, "shell")) { X strcpy(raw_shell, word2); X expand_env(shell, word2); X last = NOTWEEDOUT; X } X else if (equal(word1, "sort") || equal(word1, "sortby")) { X strcpy(word2, shift_lower(word2)); X if (equal(word2, "sent")) X sortby = SENT_DATE; X else if (equal(word2, "received") || equal(word2,"recieved")) X sortby = RECEIVED_DATE; X else if (equal(word2, "from") || equal(word2, "sender")) X sortby = SENDER; X else if (equal(word2, "size") || equal(word2, "lines")) X sortby = SIZE; X else if (equal(word2, "subject")) X sortby = SUBJECT; X else if (equal(word2, "mailbox") || equal(word2, "folder")) X sortby = MAILBOX_ORDER; X else if (equal(word2, "status")) X sortby = STATUS; X else if (equal(word2, "reverse-sent") || equal(word2,"rev-sent")) X sortby = - SENT_DATE; X else if (strncmp(word2, "reverse-rec",11) == 0 || X strncmp(word2,"rev-rec",7) == 0) X sortby = - RECEIVED_DATE; X else if (equal(word2, "reverse-from") || equal(word2, "rev-from") X || equal(word2,"reverse-sender")||equal(word2,"rev-sender")) X sortby = - SENDER; X else if (equal(word2, "reverse-size") || equal(word2, "rev-size") X || equal(word2, "reverse-lines")|| equal(word2,"rev-lines")) X sortby = - SIZE; X else if (equal(word2, "reverse-subject") || X equal(word2, "rev-subject")) X sortby = - SUBJECT; X else if (equal(word2, "reverse-mailbox") || X equal(word2, "rev-mailbox") || X equal(word2, "reverse-folder") || X equal(word2, "rev-folder")) X sortby = - MAILBOX_ORDER; X else if (equal(word2, "reverse-status") || X equal(word2, "rev-status")) X sortby = - STATUS; X else { X errors++; X printf( X "I can't understand sort key %s in line %d in your \".elm/elmrc\" file\n", X word2, lineno); X continue; X } X } X else if (equal (word1, "receivedmail") || equal(word1, "mailbox")) { X /* the last is an old name of this option - here for X * compatibility in case the user has never written out X * a new elmrc while in elm since the name change. X */ X rc_has_recvdmail = TRUE; SHAR_EOF echo "End of part 18" echo "File src/read_rc.c is continued in part 19" echo "19" > s2_seq_.tmp exit 0 -- Please send comp.sources.unix-related mail to rsalz@uunet.uu.net.