home *** CD-ROM | disk | FTP | other *** search
/ PC Online 1998 September / PCO_0998.ISO / filesbbs / dos / sbbs_src.exe / SBBS / CON_IN.C < prev    next >
Encoding:
C/C++ Source or Header  |  1997-07-02  |  17.9 KB  |  661 lines

  1. #line 1 "CON_IN.C"
  2.  
  3. /* Developed 1990-1997 by Rob Swindell; PO Box 501, Yorba Linda, CA 92885 */
  4.  
  5. #include "sbbs.h"
  6.  
  7. #define LAST_STAT_LINE 16
  8.  
  9. #ifdef __WIN32__
  10.  
  11. #include <windows.h>
  12.  
  13. uint lkbrd(int mode)
  14. {
  15.     uint c;
  16.  
  17. if(mode)
  18.     return(kbhit());
  19. c=getch();
  20. if(!c)
  21.     c=(getch()<<8);
  22. return(c);
  23. }
  24.  
  25. int  lclaes(void)
  26. {
  27. return(0);
  28. }
  29.  
  30. #elif defined(__OS2__)
  31.  
  32. void fixkbdmode(void)
  33. {
  34.     KBDINFO     kbd;
  35.  
  36. /* Disable Ctrl-C/Ctrl-P processing by OS/2 */
  37. KbdGetStatus(&kbd,0);
  38. if(kbd.fsMask&KEYBOARD_ASCII_MODE) {
  39.     kbd.fsMask|=KEYBOARD_BINARY_MODE;
  40.     kbd.fsMask&=~KEYBOARD_ASCII_MODE;
  41.     KbdSetStatus(&kbd,0); }
  42. }
  43.  
  44. uint lkbrd(int leave)
  45. {
  46.     KBDKEYINFO    key;
  47.  
  48. if(leave)
  49.     KbdPeek(&key,0);
  50. else
  51.     KbdCharIn(&key,IO_NOWAIT,0);
  52. if(!(key.fbStatus&KBDTRF_FINAL_CHAR_IN))
  53.     return(0);
  54. if(!(key.fbStatus&0x02) || key.chScan==0xE0)
  55.     return(key.chChar);
  56. return(key.chScan<<8);
  57. }
  58.  
  59. #endif
  60.  
  61. /****************************************************************************/
  62. /* Returns character if a key has been hit locally or remotely and responds */
  63. /* to local ctrl/function keys. Does not print character.                     */
  64. /* Called from functions getkey, msgabort and main_sec                        */
  65. /****************************************************************************/
  66. char inkey(int mode)
  67. {
  68.     static inside;
  69.     uchar str[512],*scrnbuf,x,y,c,atr,*gurubuf,ch=0,*helpbuf;
  70.     int file,con=console;
  71.     uint i,j;
  72.     long l,length;
  73.  
  74. if(!(node_misc&NM_NO_LKBRD) && (lkbrd(1) || sys_status&SS_FINPUT)) {
  75.     if(sys_status&SS_FINPUT) {
  76.         if(lkbrd(1)==0xff00) {
  77.             close(inputfile);
  78.             sys_status^=SS_FINPUT;
  79.             return(0); }
  80.         if(read(inputfile,&c,1)!=1) {
  81.             close(inputfile);
  82.             sys_status^=SS_FINPUT;
  83.             return(0); }
  84.         if(c)    /* Regular character */
  85.            i=c;
  86.         else {    /* Scan code */
  87.             if(read(inputfile,&c,1)!=1) {
  88.                 close(inputfile);
  89.                 sys_status^=SS_FINPUT;
  90.                 return(0); }
  91.             i=c<<8; } }
  92.     else
  93.         i=lkbrd(0);
  94.     if(sys_status&SS_LCHAT && curatr!=color[clr_chatlocal])
  95.         attr(color[clr_chatlocal]);
  96.     if(i&0xff)
  97.         ch=i&0xff;
  98.     else {                 /* Alt or Function key hit */
  99.         i>>=8;
  100.         /*         F1 - F10            Shift-F1 - Alt-F10            F11 - Alt-F12    */
  101.         if((i>=0x3b &&i<=0x44) || (i>=0x54 &&i<=0x71) || (i>=0x85 &&i<=0x8c)) {
  102.             if(sys_status&SS_FINPUT)
  103.                 return(0);                            /* MACROS */
  104.             sprintf(str,"%s%sF%d.MAC",text_dir
  105.                 ,i<0x45 || (i>=0x85 && i<=0x86) ? nulstr
  106.                 :i<0x5e || (i>=0x87 && i<=0x88) ? "SHFT-"
  107.                 :i<0x68 || (i>=0x89 && i<=0x8a) ? "CTRL-" : "ALT-"
  108.                 ,i<0x45 ? i-0x3a : i<0x5e ? i-0x53 : i<0x68 ? i-0x5d
  109.                 :i<0x72 ? i-0x67 : i<0x87 ? i-0x7a : i<0x89 ? i-0x7c
  110.                 :i<0x8b ? i-0x7e : i-0x80);
  111.             if((inputfile=nopen(str,O_RDONLY))!=-1)
  112.                 sys_status|=SS_FINPUT;
  113.             return(0); }
  114.         if(i>=0x78 && i<=0x81) {            /* Alt-# Quick Validation */
  115.             if(!(sys_status&SS_USERON)        /* can't quick-validate if not */
  116.                 || !useron.number
  117.                 || !(sys_misc&SM_QVALKEYS)) { /* or not valid user number */
  118.                 beep(100,500);                     /* online yet */
  119.                 nosound();
  120.                 return(0); }
  121.             if((node_misc&NM_SYSPW || SYSOP) && !chksyspass(1))
  122.                 return(0);
  123.             beep(1000,100);
  124.             beep(1500,100);
  125.             nosound();
  126.             if(i==0x81)
  127.                 i=0;
  128.             else
  129.                 i-=0x77;
  130.             useron.level=val_level[i];
  131.             useron.flags1=val_flags1[i];
  132.             useron.flags2=val_flags2[i];
  133.             useron.flags3=val_flags3[i];
  134.             useron.flags4=val_flags4[i];
  135.             useron.exempt=val_exempt[i];
  136.             useron.rest=val_rest[i];
  137.             now=time(NULL);
  138.             if(useron.expire<now && val_expire[i])
  139.                 useron.expire=now+((long)val_expire[i]*24L*60L*60L);
  140.             else
  141.                 useron.expire+=((long)val_expire[i]*24L*60L*60L);
  142.             putuserrec(useron.number,U_LEVEL,2,itoa(useron.level,str,10));
  143.             putuserrec(useron.number,U_FLAGS1,8,ultoa(useron.flags1,str,16));
  144.             putuserrec(useron.number,U_FLAGS2,8,ultoa(useron.flags2,str,16));
  145.             putuserrec(useron.number,U_FLAGS3,8,ultoa(useron.flags3,str,16));
  146.             putuserrec(useron.number,U_FLAGS4,8,ultoa(useron.flags4,str,16));
  147.             putuserrec(useron.number,U_EXEMPT,8
  148.                 ,ultoa(useron.exempt,str,16));
  149.             putuserrec(useron.number,U_REST,8
  150.                 ,ultoa(useron.rest,str,16));
  151.             putuserrec(useron.number,U_EXPIRE,8
  152.                 ,ultoa(useron.expire,str,16));
  153.             useron.cdt=adjustuserrec(useron.number,U_CDT,10,val_cdt[i]);
  154.             statusline();
  155.             return(0); }
  156.         switch(i) {
  157.             case 0x16:      /* Alt-U    - Runs Uedit local only with user online */
  158.                 sprintf(str,"%.*s",lbuflen,lbuf);
  159.                 waitforsysop(1);
  160.                 if((scrnbuf=MALLOC((node_scrnlen*80L)*2L))==NULL) {
  161.                     errormsg(WHERE,ERR_ALLOC,nulstr,(node_scrnlen*80L)*2L);
  162.                     return(CR); }
  163.                 gettext(1,1,80,node_scrnlen-1,scrnbuf);
  164.                 x=lclwx();
  165.                 y=lclwy();
  166.                 console&=~(CON_R_ECHO|CON_R_INPUT);
  167.                 i=(sys_status&SS_TMPSYSOP);
  168.                 if(!SYSOP) sys_status|=SS_TMPSYSOP;
  169.                 useredit(0,1);
  170.                 if(!i) sys_status&=~SS_TMPSYSOP;
  171.                 lputc(FF);
  172.                 puttext(1,1,80,node_scrnlen-1,scrnbuf);
  173.                 FREE(scrnbuf);
  174.                 lclxy(x,y);
  175.                 statusline();
  176.                 if(online==ON_REMOTE)
  177.                     rioctl(IOFI);                    /* flush input buffer */
  178.                 console=con;
  179.                 waitforsysop(0);
  180.                 strcpy(lbuf,str);
  181.                 lbuflen=strlen(lbuf);
  182.                 return(0);
  183.             case 0x1f:      /* Alt-S    - Toggles Spinning Cursor */
  184.                 useron.misc^=SPIN;
  185.                 return(0);
  186.             case 0x12:      /* Alt-E     - Toggle Remote echo and input */
  187.                 if(online!=ON_REMOTE) return(0);
  188.                 if(console&CON_R_ECHO) {
  189.                     beep(500,50);
  190.                     beep(1000,50);
  191.                     nosound();
  192.                     waitforsysop(1);
  193.                     console&=~(CON_R_ECHO|CON_R_INPUT);
  194.                     j=bstrlen(text[Wait]);
  195.                     for(i=0;i<j;i++)
  196.                         bputs("\b \b"); }
  197.                 else {
  198.                     beep(1000,50);
  199.                     beep(500,50);
  200.                     nosound();
  201.                     j=bstrlen(text[Wait]);
  202.                     for(i=0;i<j;i++)
  203.                         outchar(SP);
  204.                     console|=(CON_R_ECHO|CON_R_INPUT);
  205.                     rioctl(IOFI);                /* flush input buffer */
  206.                     waitforsysop(0); }
  207.                 return(0);
  208.             case 0x10:      /* Alt-Q     - Toggles remote input */
  209.                 if(online!=ON_REMOTE)
  210.                     return(0);
  211.                 console^=CON_R_INPUT;
  212.                 if(console&CON_R_INPUT) {
  213.                     beep(1000,50);
  214.                     beep(500,50);
  215.                     nosound();
  216.                     rioctl(IOSM|PAUSE|ABORT); }
  217.                 else {
  218.                     beep(500,50);
  219.                     beep(1000,50);
  220.                     nosound();
  221.                     rioctl(IOCM|PAUSE|ABORT); }
  222.                 rioctl(IOFI);            /* flush input buffer */
  223.                 return(0);
  224.             case 0x19:        /* Alt-P   - Turns off sysop page */
  225.                 nosound();
  226.                 sys_status&=~SS_SYSPAGE;
  227.                 return(0);
  228.             case 0x23:        /* Alt-H   - Hangs up on user */
  229.                 hangup();
  230.                 return(0);
  231.             case 0x1e:        /* Alt-A   - Alert Sysop when User's done */
  232.                 sys_status^=SS_SYSALERT;
  233.                 statusline();
  234.                 return(0);
  235.             case 0x82:        /* Alt--   - Sub Time (5 min) */
  236.                 starttime-=300;
  237.                 return(0);
  238.             case 0x83:        /* Alt-+   - Add time (5 min)*/
  239.                 starttime+=300;
  240.                 return(0);
  241.             case 0x14:        /* Alt-T   - Temp SysOp */
  242.                 if(!(sys_status&SS_TMPSYSOP) && node_misc&NM_SYSPW
  243.                     && !chksyspass(1))
  244.                     return(0);
  245.                 if(sys_misc&SM_L_SYSOP)
  246.                     sys_status^=SS_TMPSYSOP;
  247.                 statusline();
  248.                 return(0);
  249.             case 0x2c:        /* Alt-Z    - Menu of local keys */
  250.                 if((scrnbuf=MALLOC((node_scrnlen*80L)*2L))==NULL) {
  251.                     errormsg(WHERE,ERR_ALLOC,nulstr,(node_scrnlen*80L)*2L);
  252.                     return(CR); }
  253.                 gettext(1,1,80,node_scrnlen,scrnbuf);
  254.                 sprintf(str,"%sSBBSHELP.DAB",exec_dir);
  255.                 if((file=nopen(str,O_RDONLY))==-1)
  256.                     lputs("\7Can't open SBBSHELP");
  257.                 else {
  258.                     length=filelength(file);
  259.                     if((helpbuf=MALLOC(length))==NULL)
  260.                         lputs("\7Can't allocate for SBBSHELP");
  261.                     else {
  262.                         read(file,helpbuf,length);
  263.                         close(file);
  264.                         puttext(13,1,66,24,helpbuf);
  265.                         FREE(helpbuf); } }
  266.                 while(!lkbrd(1)) mswait(1);
  267.                 if(lkbrd(1)==0x2c00)    /* suck up the alt-z */
  268.                     lkbrd(0);
  269.                 puttext(1,1,80,node_scrnlen,scrnbuf);
  270.                 FREE(scrnbuf);
  271.                 return(0);
  272.             case 0x2e:        /* Alt-C    - Sysop Chat */
  273.                 if(sys_status&SS_LCHAT) {
  274.                     sys_status^=SS_LCHAT;
  275.                     return(CR); }
  276.                 else {
  277.                     sys_status|=SS_LCHAT;
  278.                     SAVELINE;
  279.                     localchat();
  280.                     return(0); }
  281.             case 0x2d:    /* Alt-X exit after logoff */
  282.                 getnodedat(node_num,&thisnode,1);
  283.                 thisnode.misc^=NODE_DOWN;
  284.                 putnodedat(node_num,thisnode);
  285.                 statusline();
  286.                 return(0);
  287.             case 0x47:    /* Home - Same as Ctrl-B */
  288.                 return(2);    /* ctrl-b beginning of line */
  289.             case 0x8d:    /* Ctrl-Up Arrow - decrement statusline */
  290.                 if(statline) {
  291.                     statline--;
  292.                     statusline(); }
  293.                 return(0);
  294.             case 0x77:    /* Ctrl-Home up - top of status line info */
  295.                 statline=1;
  296.                 statusline();
  297.                 return(0);
  298.             case 0x4b:        /* Left Arrow - same as ctrl-] */
  299.                 return(0x1d);
  300.             case 0x4d:        /* Right Arrow - same as ctrl-f */
  301.                 return(6);
  302.             case 0x48:        /* Up arrow - same as ctrl-^ */
  303.                 return(0x1e);
  304.             case 0x50:        /* Down arrow - same as Ctrl-J */
  305.                 return(LF);
  306.             case 0x4f:      /* End      - same as Ctrl-E */
  307.                 return(5);    /* ctrl-e - end of line */
  308.             case 0x91:      /* Ctrl-Dn Arrow - increment statusline */
  309.                 if(statline<LAST_STAT_LINE) {
  310.                     statline++;
  311.                     statusline(); }
  312.                 return(0);
  313.             case 0x75:    /* Ctrl-End - end of status line info */
  314.                 statline=LAST_STAT_LINE;
  315.                 statusline();
  316.                 return(0);
  317.             case 0x52:    /* Insert */
  318.                 return(0x1f);    /* ctrl-minus - insert mode */
  319.             case 0x53:    /* Delete */
  320.                 return(0x7f);    /* ctrl-bkspc - del cur char */
  321.             case 0x26:    /* Alt-L  - Capture to cap_fname */
  322.                 if(lclaes())
  323.                     return(0);
  324.                 if(sys_status&SS_CAP) {
  325.                     sys_status^=SS_CAP;
  326.                     fclose(capfile);
  327. #ifdef __MSDOS__
  328.                     freedosmem=farcoreleft();    /* fclose frees memory */
  329. #endif
  330.                     statusline();
  331.                     return(0); }
  332.                 x=lclwx();
  333.                 y=lclwy();
  334.                 atr=lclatr(LIGHTGRAY<<4);
  335.                 STATUSLINE;
  336.                 lclxy(1,node_scrnlen);
  337.                 lputs("  Filename: ");
  338.                 lputc(CLREOL);
  339.                 console&=~(CON_R_INPUT|CON_R_ECHO);
  340.                 getstr(cap_fname,40,K_UPPER|K_EDIT);
  341.                 TEXTWINDOW;
  342.                 lclxy(x,y);
  343.                 lclatr(atr);
  344.                 console=con;
  345.                 if(cap_fname[0] &&
  346.                     (capfile=fopen(cap_fname,"a"))==NULL)
  347.                     bprintf("Couldn't open %s.\r\n",cap_fname);
  348.                 else if(cap_fname[0]) {
  349. #ifdef __MSDOS__
  350.                     freedosmem=farcoreleft();    /* fnopen allocates memory */
  351. #endif
  352.                     sys_status|=SS_CAP; }
  353.                 statusline();
  354.                 return(0);
  355.             case 0x17:    /* Alt-I  - Interrupt node now */
  356.                 getnodedat(node_num,&thisnode,1);
  357.                 thisnode.misc^=NODE_INTR;
  358.                 putnodedat(node_num,thisnode);
  359.                 return(0);
  360.             case 0x13:    /* Alt-R  - Rerun node when caller hangs up */
  361.                 getnodedat(node_num,&thisnode,1);
  362.                 thisnode.misc^=NODE_RRUN;
  363.                 putnodedat(node_num,thisnode);
  364.                 statusline();
  365.                 return(0);
  366.             case 0x31:    /* Alt-N  - Lock this node */
  367.                 getnodedat(node_num,&thisnode,1);
  368.                 thisnode.misc^=NODE_LOCK;
  369.                 putnodedat(node_num,thisnode);
  370.                 statusline();
  371.                 return(0);
  372.             case 0x22:    /* Alt-G  - Guru Chat */
  373.                 if(sys_status&SS_GURUCHAT) {
  374.                     sys_status&=~SS_GURUCHAT;
  375.                     return(CR); }
  376.                 if(!total_gurus)
  377.                     break;
  378.                 for(i=0;i<total_gurus;i++)
  379.                     if(chk_ar(guru[i]->ar,useron))
  380.                         break;
  381.                 if(i>=total_gurus)
  382.                     i=0;
  383.                 sprintf(str,"%s%s.DAT",ctrl_dir,guru[i]->code);
  384.                 if((file=nopen(str,O_RDONLY))==-1) {
  385.                     errormsg(WHERE,ERR_OPEN,str,O_RDONLY);
  386.                     return(0); }
  387.                 if((gurubuf=MALLOC(filelength(file)+1L))==NULL) {
  388.                     close(file);
  389.                     errormsg(WHERE,ERR_ALLOC,str,filelength(file)+1L);
  390.                     return(0); }
  391.                 read(file,gurubuf,filelength(file));
  392.                 gurubuf[filelength(file)]=0;
  393.                 close(file);
  394.                 localguru(gurubuf,i);
  395.                 FREE(gurubuf);
  396.                 return(CR);
  397.             case 0x20:    /* Alt-D - Shell to DOS */
  398.                 sprintf(str,"%.*s",lbuflen,lbuf);
  399.                 waitforsysop(1);
  400.                 if((scrnbuf=MALLOC((node_scrnlen*80L)*2L))==NULL) {
  401.                     errormsg(WHERE,ERR_ALLOC,nulstr,(node_scrnlen*80L)*2L);
  402.                     return(CR); }
  403.                 gettext(1,1,80,node_scrnlen,scrnbuf);
  404.                 lclatr(LIGHTGRAY);
  405.                 x=lclwx();
  406.                 y=lclwy();
  407.                 lclini(node_scrnlen);
  408.                 lputc(FF);
  409.                 if(!(node_misc&NM_SYSPW) || chksyspass(1))
  410.                     external(comspec,0);
  411.                 lclini(node_scrnlen-1);
  412.                 puttext(1,1,80,node_scrnlen,scrnbuf);
  413.                 FREE(scrnbuf);
  414.                 lclxy(x,y);
  415.                 if(online==ON_REMOTE)
  416.                     rioctl(IOFI);    /* flush input buffer */
  417.                 waitforsysop(0);
  418.                 strcpy(lbuf,str);
  419.                 lbuflen=strlen(lbuf);
  420.                 timeout=time(NULL);
  421.                 return(0);
  422.             case 0x49:    /* PgUp - local ASCII upload */
  423.                 if(sys_status&SS_FINPUT || lclaes() || inside)
  424.                     return(0);
  425.                 inside=1;
  426.                 x=lclwx();
  427.                 y=lclwy();
  428.                 atr=lclatr(LIGHTGRAY<<4);
  429.                 STATUSLINE;
  430.                 lclxy(1,node_scrnlen);
  431.                 lputs("  Filename: ");
  432.                 lputc(CLREOL);
  433.                 console&=~(CON_R_INPUT|CON_R_ECHO);
  434.                 getstr(str,60,K_UPPER);
  435.                 if(str[0] && (inputfile=nopen(str,O_RDONLY))!=-1)
  436.                     sys_status|=SS_FINPUT;
  437.                 statusline();
  438.                 lclxy(x,y);
  439.                 lclatr(atr);
  440.                 console=con;
  441.                 inside=0;
  442.                 return(0);
  443.             case 0xff:    /* ctrl-break - bail immediately */
  444.                 lputs("\r\nTerminate BBS (y/N) ? ");
  445.                 while((i=lkbrd(0))==0);
  446.                 if(toupper(i&0xff)=='Y') {  /* Ctrl-brk yes/no */
  447.                     lputs("Yes\r\n");
  448.                     bail(0); }
  449.                 lputs("No\r\n");
  450.                 sys_status|=SS_ABORT;
  451.                 return(0); }
  452.         return(0); } }
  453.  
  454. if(!ch && console&CON_R_INPUT && rioctl(RXBC)) {
  455.     if(sys_status&SS_LCHAT && curatr!=color[clr_chatremote])
  456.         attr(color[clr_chatremote]);
  457.     ch=incom();
  458.     if(node_misc&NM_7BITONLY
  459.         && (!(sys_status&SS_USERON) || useron.misc&NO_EXASCII))
  460.         ch&=0x7f; }
  461. if(ch)
  462.     timeout=time(NULL);
  463. if(ch==3) {  /* Ctrl-C Abort */
  464.     sys_status|=SS_ABORT;
  465.     if(mode&K_SPIN) /* back space once if on spinning cursor */
  466.         bputs("\b \b");
  467.     return(0); }
  468. if(ch==26 && action!=NODE_PCHT) {     /* Ctrl-Z toggle raw input mode */
  469.     if(mode&K_SPIN)
  470.         bputs("\b ");
  471.     SAVELINE;
  472.     attr(LIGHTGRAY);
  473.     CRLF;
  474.     bputs(text[RawMsgInputModeIsNow]);
  475.     if(console&CON_RAW_IN)
  476.         bputs(text[OFF]);
  477.     else
  478.         bputs(text[ON]);
  479.     console^=CON_RAW_IN;
  480.     CRLF;
  481.     CRLF;
  482.     RESTORELINE;
  483.     lncntr=0;
  484.     if(action!=NODE_MAIN && action!=NODE_XFER)
  485.         return(26);
  486.     return(0); }
  487. if(console&CON_RAW_IN)    /* ignore ctrl-key commands if in raw mode */
  488.     return(ch);
  489. if(ch<SP) {                 /* Control chars */
  490.     if(ch==LF)                /* ignore LF's in not in raw mode */
  491.         return(0);
  492.     if(ch==15) {    /* Ctrl-O toggles pause temporarily */
  493.         useron.misc^=UPAUSE;
  494.         return(0); }
  495.     if(ch==0x10) {    /* Ctrl-P Private node-node comm */
  496.         if(!(sys_status&SS_USERON))
  497.             return(0);             /* keep from being recursive */
  498.         if(mode&K_SPIN)
  499.             bputs("\b ");
  500.         if(sys_status&SS_SPLITP) {
  501.             if((scrnbuf=MALLOC((24L*80L)*2L))==NULL) {
  502.                 errormsg(WHERE,ERR_ALLOC,nulstr,(24L*80L)*2L);
  503.                 return(CR); }
  504.             gettext(1,1,80,24,scrnbuf);
  505.             x=lclwx();
  506.             y=lclwy();
  507.             CLS; }
  508.         else {
  509.             SAVELINE;
  510.             attr(LIGHTGRAY);
  511.             CRLF; }
  512.         nodesync();     /* read any waiting messages */
  513.         nodemsg();        /* send a message */
  514.         SYNC;
  515.         if(sys_status&SS_SPLITP) {
  516.             lncntr=0;
  517.             CLS;
  518.             for(i=0;i<((24*80)-1)*2;i+=2) {
  519.                 if(scrnbuf[i+1]!=curatr)
  520.                     attr(scrnbuf[i+1]);
  521.                 outchar(scrnbuf[i]); }
  522.             FREE(scrnbuf);
  523.             GOTOXY(x,y); }
  524.         else {
  525.             CRLF;
  526.             RESTORELINE; }
  527.         lncntr=0;
  528.         return(0); }
  529.  
  530.     if(ch==21) { /* Ctrl-U Users online */
  531.         if(!(sys_status&SS_USERON))
  532.             return(0);
  533.         if(mode&K_SPIN)
  534.             bputs("\b ");
  535.         if(sys_status&SS_SPLITP) {
  536.             if((scrnbuf=MALLOC((24L*80L)*2L))==NULL) {
  537.                 errormsg(WHERE,ERR_ALLOC,nulstr,(24L*80L)*2L);
  538.                 return(CR); }
  539.             gettext(1,1,80,24,scrnbuf);
  540.             x=lclwx();
  541.             y=lclwy();
  542.             CLS; }
  543.         else {
  544.             SAVELINE;
  545.             attr(LIGHTGRAY);
  546.             CRLF; }
  547.         whos_online(1);     /* list users */
  548.         ASYNC;
  549.         if(sys_status&SS_SPLITP) {
  550.             CRLF;
  551.             nodesync();
  552.             pause();
  553.             CLS;
  554.             for(i=0;i<((24*80)-1)*2;i+=2) {
  555.                 if(scrnbuf[i+1]!=curatr)
  556.                     attr(scrnbuf[i+1]);
  557.                 outchar(scrnbuf[i]); }
  558.             FREE(scrnbuf);
  559.             GOTOXY(x,y); }
  560.         else {
  561.             CRLF;
  562.             RESTORELINE; }
  563.         lncntr=0;
  564.         return(0); }
  565.     if(ch==20 && !(sys_status&SS_SPLITP)) { /* Ctrl-T Time information */
  566.         if(!(sys_status&SS_USERON))
  567.             return(0);
  568.         if(mode&K_SPIN)
  569.             bputs("\b ");
  570.         SAVELINE;
  571.         attr(LIGHTGRAY);
  572.         now=time(NULL);
  573.         bprintf(text[TiLogon],timestr(&logontime));
  574.         bprintf(text[TiNow],timestr(&now));
  575.         bprintf(text[TiTimeon]
  576.             ,sectostr(now-logontime,tmp));
  577.         bprintf(text[TiTimeLeft]
  578.             ,sectostr(timeleft,tmp));
  579.         SYNC;
  580.         RESTORELINE;
  581.         lncntr=0;
  582.         return(0); }
  583.     if(ch==11 && !(sys_status&SS_SPLITP)) {  /*  Ctrl-k Control key menu */
  584.         if(!(sys_status&SS_USERON))
  585.             return(0);
  586.         if(mode&K_SPIN)
  587.             bputs("\b ");
  588.         SAVELINE;
  589.         attr(LIGHTGRAY);
  590.         lncntr=0;
  591.         bputs(text[ControlKeyMenu]);
  592.         ASYNC;
  593.         RESTORELINE;
  594.         lncntr=0;
  595.         return(0); }
  596.  
  597.     if(ch==ESC && console&CON_R_INPUT) {
  598.         for(i=0;i<20 && !rioctl(RXBC);i++)
  599.             mswait(1);
  600.         if(i==20)
  601.             return(ESC);
  602.         ch=incom();
  603.         if(ch!='[') {
  604.             ungetkey(ESC);
  605.             ungetkey(ch);
  606.             return(0); }
  607.         i=j=0;
  608.         autoterm|=ANSI;             /* <ESC>[x means they have ANSI */
  609.         if(!(useron.misc&ANSI) && useron.misc&AUTOTERM && sys_status&SS_USERON
  610.             && useron.number) {
  611.             useron.misc|=ANSI;
  612.             putuserrec(useron.number,U_MISC,8,ultoa(useron.misc,str,16)); }
  613.         while(i<10 && j<30) {        /* up to 3 seconds */
  614.             if(rioctl(RXBC)) {
  615.                 ch=incom();
  616.                 if(ch!=';' && !isdigit(ch) && ch!='R') {    /* other ANSI */
  617.                     switch(ch) {
  618.                         case 'A':
  619.                             return(0x1e);    /* ctrl-^ (up arrow) */
  620.                         case 'B':
  621.                             return(LF);     /* ctrl-j (dn arrow) */
  622.                         case 'C':
  623.                             return(0x6);    /* ctrl-f (rt arrow) */
  624.                         case 'D':
  625.                             return(0x1d);    /* ctrl-] (lf arrow) */
  626.                         case 'H':
  627.                             return(0x2);    /* ctrl-b (beg line) */
  628.                         case 'K':
  629.                             return(0x5);    /* ctrl-e (end line) */
  630.                         }
  631.                     ungetkey(ESC);
  632.                     ungetkey('[');
  633.                     for(j=0;j<i;j++)
  634.                         ungetkey(str[j]);
  635.                     ungetkey(ch);
  636.                     return(0); }
  637.                 if(ch=='R') {       /* cursor position report */
  638.                     if(i && !(useron.rows)) {    /* auto-detect rows */
  639.                         str[i]=0;
  640.                         rows=atoi(str);
  641.                         if(rows<5 || rows>99) rows=24; }
  642.                     return(0); }
  643.                 str[i++]=ch; }
  644.             else {
  645.                 mswait(100);
  646.                 j++; } }
  647.  
  648.         ungetkey(ESC);        /* should only get here if time-out */
  649.         ungetkey('[');
  650.         for(j=0;j<i;j++)
  651.             ungetkey(str[j]);
  652.         return(0); }
  653.  
  654.         }    /* end of control chars */
  655.  
  656. if(!ch && (!(mode&K_GETSTR) || mode&K_LOWPRIO || node_misc&NM_LOWPRIO))
  657.     mswait(0);
  658. return(ch);
  659. }
  660.  
  661.