/***************************************************************************
 *                                                                         *
 *   MONITOR.C                                                             *
 *                                                                         *
 *   Copyright (c) 1992-1997 Galacticomm, Inc.      All Rights Reserved.   *
 *                                                                         *
 *   Monitor-All screen code                                               *
 *                                                                         *
 *                                            - Robert A. Rose 02/10/92    *
 *                                                                         *
 *   Added C/S support for Remote Sysop Monitor                            *
 *                                                                         *
 *                                            - Joe Delekto    01/29/96    *
 *                                                                         *
 ***************************************************************************/

#include "gcomm.h"
#include "majorbbs.h"
#include "gcspsrv.h"
#include "oprlow.h"

#define FILREV "$Revision: 8 $"

                                        /* special response building ops   */
#define   clear(s) *(s)='\0'            /* set first char '0'              */
#define   cpyrsp(s) stlcpy(vdatmp,(s),min(MAXDPKV,vdasiz))
#define   delimiter() stlcat(vdatmp,"\t",min(MAXDPKV,vdasiz))
#define   catrsp(s) stlcat(vdatmp,(s),min(MAXDPKV,vdasiz))
#define   dynpak(x) "sa:"x         /* convert to full dynapak name         */

#define   GALRSY    "GALRSY"       /* App-ID of remote sysop application   */
#define   MONINF    "moninf"       /* Monitor info dynapak name            */

UINT monkey(UINT scncod);
VOID shomal(VOID);

extern INT stahdl;                 /* handle for the graph screen          */
INT mhdl;                          /* handle for the monitor screen        */
extern INT shdl;                   /* handle for the summary screen        */

INT manhue=0x1A,
    mbahue=0x1B,
    mashue=0x50;

struct scrnid monascn={
     "wgsm.bin",                   /* screen filename                      */
     3040,                         /* length of screen (4000 for full scrn)*/
     ALT_M,                        /* select scan code (from main screen)  */
                                   /* ala 'Keyboard Accelerator'           */
     NULL,                         /* screen going away routine            */
     NULL,                         /* screen repaint routine               */
     monkey,                       /* key handler routine                  */
     NULL,                         /* occasional update routine            */
     0,                            /* seconds between occasional updates   */
     0,                            /* seconds to go before next update     */
     NULL,                         /* called every cycle when displayed    */
     2,0,                          /* current cursor position on screen    */
     0,                            /* does cursor move?                    */
     1,                            /* should screen scroll?                */
     1,1,70,17,                    /* scrolling for window (default)       */
     NULL,                         /* perm. save buffer                    */
     NULL                          /* current location of screen           */
};

VOID (*shomal_hook)(VOID)=shomal;  /* replaceable hook into monitor info   */

UINT
monkey(                       /* Monitor screen keystroke handler routine  */
UINT scncod)                       /* keystroke hit                        */
{
     switch (scncod) {
     case TAB:
          scn2mai(shdl);
          break;
     case BAKTAB:
          scn2mai(stahdl);
          break;
     default:
          return(scncod);
     }
     return(0);
}

VOID
shomal(VOID)                  /* show "monitor all" channel status         */
{
     struct saunam rfdpk;
     INT i,rlen;
     CHAR *inptr,tmp[18];
     struct user *uptr;

     clear(vdatmp);
     if (status == CRSTG) {
          cpyrsp(uacoff(usrnum)->userid);
     }
     delimiter();
     catrsp("   ");
     catrsp(itoa(channel[usrnum],tmp,16));
     delimiter();
     catrsp("  ");
     catrsp(itoa(status,tmp,10));
     delimiter();
     switch(status) {
     case CRSTG:
          catrsp(input);
          break;
     case 6:
          catrsp("<User aborted output>");
          break;
     case 11:
          catrsp("<Lost Carrier>");
          break;
     case 13:
          catrsp("<Invalid Command>");
          break;
     case 251:
          catrsp("<Data Input Buffer Overflow>");
          break;
     case 252:
          catrsp("<Echo Output Buffer Overflow>");
          break;
     case 253:
          catrsp("<Data Output Buffer Overflow>");
          break;
     case 254:
          catrsp("<Status Input Buffer Overflow>");
          break;
     case 255:
          catrsp("<Command Output Buffer Overflow>");
          break;
     default:
          break;
     }
     prf("|%-9.9s| %02X |%3d |",uacoff(usrnum)->userid,channel[usrnum],status);
     if (status == CRSTG) {
          prf(" %-52.52s\r",input);
          if (inplen > 52) {
               prf("|         |    |    | %-52.52s\r",input+52);
               if (inplen > 104) {
                    prf("|         |    |    | %-52.52s\r",input+104);
                    if (inplen > 156) {
                         prf("|         |    |    | %-52.52s\r",input+156);
                    }
               }
          }
     }
     else {
          prf("\r");
     }
     for (i=0 ; i < nterms ; i++) {
          uptr=usroff(i);
          if ((uptr->flags&ISGCSU) && ((uptr->flags&MONALL) ||
              (uptr->flags&MONINP))) {
               if (qroom(i,NORMAL)) {
                    setmem(&rfdpk,sizeof(struct saunam),0);
                    stlcpy(rfdpk.sysid,msysid,SIDSIZ);
                    stlcpy(rfdpk.appid,GALRSY,AIDSIZ);
                    rfdpk.usrid[0]='\0';
                    stlcpy(rfdpk.suffix,MONINF,SFXSIZ);
                    senddpk(i,GALRSY,NORMAL,&rfdpk,STGLEN,vdatmp,NULL);
               }
          }
          else {
               if (btuoba(i) > (prfptr-prfbuf)) {
                    if ((uptr->flags&MONALL) ||
                        ((uptr->flags&MONINP) && status == CRSTG)) {
                         outprf(i);
                    }
               }
          }
     }
     clrprf();
     prf("");
     actvscn(mhdl);
     locate(70,17);
     if (status == CRSTG) {
          sstatr(manhue);
          printf("\n %02X ",channel[usrnum]);
          sstatr(mbahue);
          printf("%c",179);
          sstatr(manhue);
          printf("%3d ",status);
          sstatr(mbahue);
          printf("%c",179);
          sstatr(manhue);
          printf(" %.58s",input);
          for (rlen=inplen-58,inptr=input+58 ; rlen > 0 ; rlen-=58,inptr+=58) {
               sstatr(mbahue);
               printf("\n    %c    %c ",179,179);
               sstatr(manhue);
               printf("%.58s",inptr);
          }
     }
     else {
          sstatr(manhue);
          printf("\n");
          sstatr(mashue);
          printf(" %02X ",channel[usrnum]);
          sstatr(mbahue);
          printf("%c",179);
          sstatr(mashue);
          printf("%3d ",status);
          sstatr(mbahue);
          printf("%c ",179);
          sstatr(0x1A);
          switch (status) {
          case 251:
               printf("<Data Input Buffer Overflow>");
               break;
          case 252:
               printf("<Echo Output Buffer Overflow>");
               break;
          case 253:
               printf("<Data Output Buffer Overflow>");
               break;
          case 254:
               printf("<Status Input Buffer Overflow>");
               break;
          case 255:
               printf("<Command Output Buffer Overflow>");
               break;
          case 11:
               printf("<Lost Carrier>");
               break;
          case 13:
               printf("<Invalid Command>");
               break;
          case 6:
               printf("<User aborted output>");
               break;
          }
     }
}
