/***************************************************************** * Articles/Notes, Misc. other functions overlay * * File: MEMISC.C * * Metal and Metal Message System are Trademarks and * Copyright (c) 1984, 1985, 1986 Tim Gary * All Rights Reserved. * ****************************************************************** * * 1.50xx 04/12/86 Fixed features bug from lbr code conversion.. * 1.50xx 04/06/86 Sysop not prompted to leave comments for entering CP/M.. * library stuff added to articles routines. * 1.40xx 02/21/86 Start extended help command.. * 1.40xx 02/11/86 Time command changed a bit.. * 1.40xx 02/03/86 Fixed articles/features.. * 1.40xx 01/26/86 Fixed for new user/date stuff.. * 1.31a 10/13/85 Release version. Changes: * go_os() routine called from cpm().. * deleted 'readrange' routine (moved to MEREAD.C) * hangup() called when done (bye,g) * 1.30xx 6/23/85 Cosmetic change in getrange text. * 1.30xx 6/19/85 A very few changes in feature(), cpm(), etc.. * 1.30xx 5/05/85 Comments routine fixed. * 1.30xx 3/07/85 Fixed for chaining to BYE program on exit.. * 1.30xx 3/03/85 ZCPR stuff added.. * 1.20b 01/18/85 Showtime put here.. * 1.20b 01/16/85 Recursive use of notes/features allowed... * 1.20b 01/06/85 Allow 'Q' as in 'K' for read silent mode. * 1.20a 11/11/84 Comments messages made more universal, and Goodbye * routine made to not display info if G;N thing * typed. * 1.20a 11/07/84 Comments routine fixed for two CONSECUTIVE CR's * to stop. * 1.10e 11/01/84 Getrange now allows to read dead msgs. * 1.10e 10/29/84 Added chat(), cpm() and goodbye() to this overlay. * * 1.10c 10/12/84 Created from MEFEAT.C 4 parameters passed * to all of these routines. * ******************************************************************/ #include "xpm.h" /* CPMIO header file for i/o operations.*/ #include "megen.h" /* general defines */ #include "meglob.h" /* global variable definitions */ #include "meovfn.h" /* overlay function numbers */ #include "mefiles.h" /* file names */ #include "ctype.h" #define COMMHELP "MECOMM HLP" /* comments help info */ /********************************************************** * Overlay main program, dispatches to contained routines. **********************************************************/ ovmain(routine,p1) /* ,p2,p3,p4) */ int routine,p1; /* ,p2,p3,p4; */ { switch(routine) { case FEATURE: return feature(p1,(char *)0,1); case CHAT: return chat(p1); case GOODBYE: return goodbye(p1); case GOCPM: return cpm(p1); case SHOWTIME: return showtime(); case MEHELP: return more_help(); default: send("\nUnknown routine called for.\n"); break; } } /* ovmain */ /******************************************** * More extensive help stuff.. takes topics * from main library... ********************************************/ more_help() { int flag=FALSE; char temp[12],t[12]; /* 11 chars usable, +1 for null terminator */ if (!strloc) ltype(METHELP,"MEHELP "); /* display '?' list by default */ else flag=TRUE; do { if (user.flags&EXPERT) ask("\nSubject (or ?): ",temp,6,UP); else ask("\nWhat subject would you like help on (? for list)? ",temp,6,UP); if (!(*temp)) return; if (*temp=='?') strcpy(t,"MEHELP "); else sprintf(t,"ME%-6sHLP",temp); /* make exactly 11 chars */ putchar('\n'); if (ltype(METHELP,t)==ERROR) printf("\n[No help available for %s]\n",temp); } while (!flag); /* while */ } /***************************************** * Show current time, and time on system * *****************************************/ showtime() { if (O.RTC) { int mins; /* mins on system */ readclock(); mins=timecomp(time,user.time,date,user.date); printf("\nToday is %s. The time is %s.",ascdate(date),asctime(time)); printf("\nLogged in at %s (%d minutes ago).\n",asctime(user.time),mins); if (user.minutes) printf("You've used the system for %d minutes today.\n",mins+user.minutes); if (user.tot_hours || user.tot_mins) { unsigned hours; mins+=user.tot_mins; hours=user.tot_hours+(mins/60); mins%=60; printf("To date, you have spent %d hour(s) and %d minute(s) on the system.\n",hours,mins); } } else send("\nNo clock installed on this system.\n"); } /****************************************************************** * Articles function to list files in the Articles/Features ('A') * or Notes ('N') index file. Index file has a fixed format of: * * o filename/location of file (C format) * (my also be library: libname#membername (note '#'!!)) * o a space character (required!) * o rest of line = Description of file (displayed in the menu) * * Each line must have at least 6 characters in it. A standard text * editor may be used to create the index file. Each line is * the index for one file. A line may NOT exceed 128 chars. * * A maximum of 25 articles may be contained in the index files. * * If the line begins with a ';', it is considered a comment line * and will be ignored.. * * If the line starts with a * then the line is printed during * the menu display. * * Squeezed articles may be displayed, however menus may NOT be squeezed. * ******************************************************************/ feature(ch,file_name,level) int ch; char *file_name; int level; /* level number */ { char *in[25]; /* pointer array to each filename */ char level_name[81]; char name[32]; register int i,n; char tot,*tp,*space; FILE *indfile,*tf; int ret_flag; ret_flag=NULL; space=malloc(800); /* get space for filenames */ if (!space) return ERROR; /* error, return to previos level */ for (i=0; i<25; i++) in[i]=space+(32*i); /* setup pointer array */ tot=0; if (level==1) strcpy(level_name,"main"); else *level_name='\0'; do { *name='\0'; if (ch=='A') strcpy(name,FEATFILE); else { if (ch=='N') strcpy(name,NOTEFILE); else strcpy(name,file_name); } if (!index(name,'#')) /* if not library open */ { if ( (indfile=open(name,0)) == NULL) { send("\nSorry, nothing in menu.\n"); ret_flag=ERROR; break; /* free space, and return ERROR flag */ } } else { tp=index(name,'#'); *tp='\0'; if ( (indfile=lopen(name,tp+1)) == NULL ) { send("\nSorry, nothing in menu.\n"); ret_flag=ERROR; *tp='#'; break; } *tp='*'; } read(indfile,1); for (i=0; i<25; ++i) { int file_flag; do { file_flag=FALSE; /* flag for valid file to type.. */ if (fgets(buffer,indfile)==ERROR) break; for (tp=buffer; *tp=='\n' || *tp=='\r'; tp++); /* ignore cr/lf */ if (!ustrncmp(tp,";MENU ",6)) strcpy(level_name,tp+6); /* new level name */ if (*tp==';') continue; if (*tp=='*') /* display line in menu */ { putchar('\n'); if (send(tp+1)==ERROR) break; continue; } if (*tp<' ' || strlen(tp)<6) break; /* logical or phys. eof? */ strncpy(in[i],tp,index(tp,' ') ? (index(tp,' ')-tp) : 31); if (index(tp,' ')) { in[i][index(tp,' ')-tp]='\0'; tp=index(tp,' '); /* search to item descr. */ } else in[i][31]='\0'; /* make SURE it's terminated */ for ( ; tp && *tp==' '; tp++); sprintf(buffer,"\n%2d. %s",i+1,tp); if (!strloc) if (send(buffer)==ERROR) break; /* allow abort */ file_flag=TRUE; /* only ok at bottom of loop */ } while (!file_flag); if (!file_flag) break; /* true abort of menu... */ } /* for */ if (index(name,'#')) lclose(indfile); /* That's all we need here for now */ else close(indfile); if (i==0) /* nothing found */ { ret_flag=ERROR; break; } if (tottot) continue; if (n==0) { ret_flag=TRUE; break; } if (tp=index(in[n-1],'#')) { *tp='\0'; if (!(tf=lopen(in[n-1],tp+1)) ) { send("\nSorry, that item is empty (L).\n"); *tp='#'; continue; } *tp='#'; } else if (!(tf=open(in[n-1],0))) /* open file, test for ';MENU' */ { send("\nSorry, that item is empty.\n"); continue; } read(tf,0); for (i=0; i<6; i++) buffer[i]=getc(tf); if (!ustrncmp(buffer,";MENU",5)) { /* another menu, do recursive.. */ ret_flag=feature(0,in[n-1],level+1); /* recursive */ if (ret_flag==TRUE) break; /* massive withdrawl */ } else type_from(tf); /* type the file if not menu */ if (tp) lclose(tf); /* close lib, or normal file */ else close(tf); } while (1); /* just a loop forever */ free(space); return ret_flag; } /************************************ * Ask user if he wishes to leave comments to sysop ************************************/ askcomments(str) char *str; { char temp[5]; if (user.status==SYSOP) return NULL; if ( !(user.flags&EXPERT) && !strloc) ltype(METHELP,COMMHELP); do { if (!str) ask("\nLeave private comments to the Sysop (y/n)? ",temp,2,UP); else ask(str,temp,2,UP); if (*temp=='?') ltype(METHELP,COMMHELP); } while (*temp=='?'); /* while he's still confused.. */ if (*temp=='Y') ovovload(OVSEND,2,0); /* this in now priv msg to sysop */ else if (*temp!='N') { send("\n[Returning..]\n"); return ERROR; /* didn't want to leave */ } return NULL; } /******************* * chat with sysop * *******************/ chat(mode) int mode; { register int a,cfast; register char temp; int col; /* current column count for auto wrap */ if (mode) { /* display user if no 25th status line */ putchar('\n'); if (!O.STATUSLINE) printf("%s ",user.name); else wustat(" [CHAT]"); send("Paging Sysop "); globalchar='\0'; for (temp=0; temp<25; temp++) { if (send("\07 .\07 .\07 .")==ERROR) return; /* bell */ for (cfast=0; cfast<1000; cfast++) if (breakkey()) return; else if ((a=globalchar)==0x1b) /* ESC hit by sysop? */ { wustat(0); /* put back just user info */ send("\nThe Sysop is available, please go ahead...\n"); break; } if (send("\b\07\b\b\07\b\b\07")==ERROR) return; /* backup most of the way */ if (a==0x1b) break; /* ESCAPE is Sysop's "I'm here" char */ } if (!a) { send("\nThe Sysop is currently not available.\n"); askcomments("Would you like to leave a private message to the System Operator? "); return; } } /* end mode check... if mode=0 then just start chat mode */ globalchar=0; /* for next pass through */ send("\n** [^K to abort chat] **\n"); col=1; /* first column */ while((cfast=getchar())!=11) /* while not ^K */ { if (cfast=='\r') { col=1; putchar('\n'); } else if (cfast=='\b' || cfast==0x7f) { --col; send(" \b"); } else { if ( ( ++col>user.width-7 && (isspace(cfast) || ispunct(cfast)) ) || (col>user.width-1) ) { col=1; send("\n"); /* force CRLF */ } } } putchar('\n'); } /* Write user status line info (name, stat, time called, city).. */ wustat(s) char *s; { char buf[128]; sprintf(buf,"%8s -- %s - '%c' %s -- %s",s ? s : "",user.name, user.status,asctime(time),user.city); writestat(buf); } /******************* * jump to CP/M... * *******************/ cpm(mode) register int mode; /* if mode=1 then ask if leave comments */ { if (user.type_ptr->maxuser==0 || !index("+snxabcde",user.status) ) { send("\nYou don't have access to the operating system."); return; } if (mode==1) if (askcomments(0)==ERROR) return; /* didn't want to leave */ go_os(YES); } /******************************* * Leave the system *******************************/ goodbye(mode) register int mode; { if (mode==1) /* if 'g' entered. else no comments */ if (askcomments(0)==ERROR) return; /* didn't want to leave */ hangup(YES); /* display copyright and hangup.. */ } /* EOF MEMISC.C */