home *** CD-ROM | disk | FTP | other *** search
/ Network PC / Network PC.iso / amiga utilities / communication / bbs / termv4.6 / extras / source / term-source.lha / Remember.c < prev    next >
Encoding:
C/C++ Source or Header  |  1996-03-18  |  10.0 KB  |  538 lines

  1. /*
  2. **    Remember.c
  3. **
  4. **    Login learn routines
  5. **
  6. **    Copyright © 1990-1996 by Olaf `Olsen' Barthel
  7. **        All Rights Reserved
  8. **
  9. **    :ts=4
  10. */
  11.  
  12. #ifndef _GLOBAL_H
  13. #include "Global.h"
  14. #endif
  15.  
  16.     /* How many characters to remember. */
  17.  
  18. #define REMEMBER_OUT    40
  19. #define REMEMBER_IN        256
  20.  
  21.     /* Yet another node variant. */
  22.  
  23. struct RecordNode
  24. {
  25.     struct Node        Node;
  26.     struct timeval    Time;
  27. };
  28.  
  29.     /* What type of text was recorded. */
  30.  
  31. enum    {    RECORD_OUTPUT,RECORD_INPUT };
  32.  
  33.     /* The last ten bytes received. */
  34.  
  35. STATIC UBYTE             RememberOutputData[2 * REMEMBER_OUT + 10];
  36. STATIC WORD                 RememberOutputSize;
  37.  
  38.     /* The last 256 bytes sent. */
  39.  
  40. STATIC UBYTE             RememberInputData[2 * REMEMBER_IN + 10];
  41. STATIC WORD                 RememberInputSize;
  42.  
  43.     /* The name of the BBS we are currently recording for. */
  44.  
  45. STATIC UBYTE             RecordName[50];
  46.  
  47.     /* Recorded lines. */
  48.  
  49. STATIC struct List        *RecordList;
  50. STATIC LONG                 RecordCount;
  51.  
  52.     /* Auxilary data. */
  53.  
  54. STATIC STRPTR             RecordAuxBuffer;
  55.  
  56.     /* Start of recording. */
  57.  
  58. STATIC struct timeval     RecordTime;
  59.  
  60.     /* FinishRecord():
  61.      *
  62.      *    Finish the recording process, store the
  63.      *    recorded data in a file.
  64.      */
  65.  
  66. VOID
  67. FinishRecord()
  68. {
  69.     if(RecordCount)
  70.     {
  71.         UBYTE                     DummyBuffer[MAX_FILENAME_LENGTH];
  72.         struct FileRequester    *FileRequest;
  73.  
  74.         BlockWindows();
  75.  
  76.         Recording = RecordingLine = FALSE;
  77.  
  78.         Status = STATUS_READY;
  79.  
  80.         if(RecordName[0])
  81.             strcpy(DummyBuffer,RecordName);
  82.         else
  83.         {
  84.             strcpy(DummyBuffer,LocaleString(MSG_SCREENPANEL_UNKNOWN_TXT));
  85.  
  86.             strcpy(RecordName,DummyBuffer);
  87.         }
  88.  
  89.         FixName(DummyBuffer);
  90.  
  91.         DummyBuffer[27] = 0;
  92.  
  93.         strcat(DummyBuffer,".term");
  94.  
  95.         if(FileRequest = GetFile(Window,LocaleString(MSG_SAVE_RECORDED_FILE_TXT),"",DummyBuffer,DummyBuffer,"#?.(term|rexx)",TRUE,FALSE,FALSE,LocaleString(MSG_GLOBAL_SAVE_GAD),TRUE))
  96.         {
  97.             BPTR            FileHandle;
  98.             LONG            Error = 0;
  99.             struct timeval    Delta = { 0,0 };
  100.  
  101.             if(FileHandle = Open(DummyBuffer,MODE_NEWFILE))
  102.             {
  103.                 SetIoErr(0);
  104.  
  105.                 if(FPrintf(FileHandle,LocaleString(MSG_RECORDFILE_HEADER_TXT),RecordName) < 1)
  106.                     Error = IoErr();
  107.  
  108.                 if(!Error)
  109.                 {
  110.                     struct RecordNode *Node = (struct RecordNode *)RecordList->lh_Head;
  111.                     BOOL UsesSpace,UsesQuotes;
  112.                     STRPTR Header;
  113.                     LONG i,Len;
  114.  
  115.                     while(Node->Node.ln_Succ && !Error)
  116.                     {
  117.                         if(Delta.tv_secs != Node->Time.tv_secs)
  118.                         {
  119.                             LONG Secs;
  120.  
  121.                             Secs = (3 * Node->Time.tv_secs) / 2 + (3 * Node->Time.tv_micro) / 2000000;
  122.  
  123.                             SetIoErr(0);
  124.  
  125.                             if(FPrintf(FileHandle,"TIMEOUT %ld\n",Secs) < 1)
  126.                             {
  127.                                 Error = IoErr();
  128.  
  129.                                 break;
  130.                             }
  131.                             else
  132.                                 Delta = Node->Time;
  133.                         }
  134.  
  135.                         SetIoErr(0);
  136.  
  137.                             // Now things get a little difficult. As the ARexx
  138.                             // parser is bound to get into trouble with trailing
  139.                             // and leading spaces and `trouble' will appear like
  140.                             // a picnic if a double quote shows up in the text,
  141.                             // we need to find out about these exceptions.
  142.  
  143.                         Len = strlen(Node->Node.ln_Name);
  144.  
  145.                         for(i = 0, UsesSpace = UsesQuotes = FALSE ; i < Len ; i++)
  146.                         {
  147.                             if(Node->Node.ln_Name[i] == ' ' && (i == 0 || i == Len - 1))
  148.                             {
  149.                                 UsesSpace = TRUE;
  150.  
  151.                                 if(UsesQuotes)
  152.                                     break;
  153.                             }
  154.  
  155.                             if(Node->Node.ln_Name[i] == '\"')
  156.                             {
  157.                                 UsesQuotes = TRUE;
  158.  
  159.                                 if(UsesSpace)
  160.                                     break;
  161.                             }
  162.                         }
  163.  
  164.                         if(Node->Node.ln_Type == RECORD_OUTPUT)
  165.                             Header = "WAIT";
  166.                         else
  167.                             Header = "SEND";
  168.  
  169.                         if(FPrintf(FileHandle,"%s TEXT \"",Header) < 1)
  170.                             Error = IoErr();
  171.                         else
  172.                         {
  173.                             if(UsesSpace || UsesQuotes)
  174.                             {
  175.                                 STRPTR From,String,First,Last;
  176.                                 UBYTE c;
  177.  
  178.                                 From = String = (STRPTR)Node->Node.ln_Name;
  179.  
  180.                                 First = String;
  181.                                 Last = String + Len - 1;
  182.  
  183.                                 c = 0;
  184.  
  185.                                 while(*String)
  186.                                 {
  187.                                     switch(*String)
  188.                                     {
  189.                                         case ' ':
  190.  
  191.                                             if(String == First || String == Last)
  192.                                                 c = ' ';
  193.  
  194.                                             break;
  195.  
  196.                                         case '\"':
  197.  
  198.                                             c = '\"';
  199.                                             break;
  200.                                     }
  201.  
  202.                                     if(c)
  203.                                     {
  204.                                         STRPTR Code;
  205.  
  206.                                         if(From < String)
  207.                                         {
  208.                                             LONG Len = (LONG)(String - From);
  209.  
  210.                                             if(FWrite(FileHandle,From,Len,1) != 1)
  211.                                             {
  212.                                                 Error = IoErr();
  213.                                                 break;
  214.                                             }
  215.                                         }
  216.  
  217.                                         if(c == ' ')
  218.                                             Code = "\\*32";
  219.                                         else
  220.                                             Code = "\\*34";
  221.  
  222.                                         if(FPrintf(FileHandle,Code) < 1)
  223.                                         {
  224.                                             Error = IoErr();
  225.                                             break;
  226.                                         }
  227.  
  228.                                         From = String + 1;
  229.                                         c = 0;
  230.                                     }
  231.  
  232.                                     String++;
  233.                                 }
  234.  
  235.                                 if(!Error && From < String)
  236.                                 {
  237.                                     LONG Len = (LONG)(String - From);
  238.  
  239.                                     if(FWrite(FileHandle,From,Len,1) != 1)
  240.                                         Error = IoErr();
  241.                                 }
  242.                             }
  243.                             else
  244.                             {
  245.                                 if(FPrintf(FileHandle,Node->Node.ln_Name) < 1)
  246.                                     Error = IoErr();
  247.                             }
  248.  
  249.                             if(!Error)
  250.                             {
  251.                                 if(FPrintf(FileHandle,"\"\n") < 1)
  252.                                     Error = IoErr();
  253.                             }
  254.                         }
  255.  
  256.                         Node = (struct RecordNode *)Node->Node. ln_Succ;
  257.                     }
  258.                 }
  259.  
  260.                 Close(FileHandle);
  261.  
  262.                 ObtainSemaphore(&PatternSemaphore);
  263.  
  264.                 if(ChosenEntry)
  265.                 {
  266.                     if(ShowRequest(Window,LocaleString(MSG_USE_AS_LOGIN_SCRIPT_TXT),LocaleString(MSG_GLOBAL_YES_NO_TXT),ChosenEntry->Header->Name))
  267.                     {
  268.                         if(!ChosenEntry->Config->CommandConfig)
  269.                         {
  270.                             if(!CreateConfigEntry(ChosenEntry->Config,PREF_COMMAND))
  271.                                 ShowError(Window,ERR_NO_MEM,NULL,NULL);
  272.                         }
  273.  
  274.                         if(ChosenEntry->Config->CommandConfig)
  275.                         {
  276.                             PhonebookChanged = TRUE;
  277.  
  278.                             SPrintf(ChosenEntry->Config->CommandConfig->LoginMacro,"\\a %s",DummyBuffer);
  279.                         }
  280.                     }
  281.                 }
  282.  
  283.                 ReleaseSemaphore(&PatternSemaphore);
  284.             }
  285.             else
  286.                 Error = IoErr();
  287.  
  288.             if(!Error && Config->MiscConfig->CreateIcons && IconBase)
  289.             {
  290.                 struct DiskObject *Icon;
  291.  
  292.                 if(!(Icon = GetDiskObject("ENV:def_term")))
  293.                 {
  294.                     if(!(Icon = GetDiskObject("ENV:def_rexx")))
  295.                     {
  296.                         if(Icon = GetDefDiskObject(WBPROJECT))
  297.                             Icon->do_DefaultTool = "RX";
  298.                     }
  299.                 }
  300.  
  301.                 if(Icon)
  302.                 {
  303.                     Icon->do_CurrentX = Icon->do_CurrentY = NO_ICON_POSITION;
  304.  
  305.                     PutDiskObject(DummyBuffer,Icon);
  306.  
  307.                     FreeDiskObject(Icon);
  308.                 }
  309.             }
  310.  
  311.             if(Error)
  312.                 ShowError(Window,ERR_SAVE_ERROR,Error,DummyBuffer);
  313.  
  314.             FreeAslRequest(FileRequest);
  315.         }
  316.  
  317.         DeleteRecord();
  318.  
  319.         ReleaseWindows();
  320.     }
  321. }
  322.  
  323.     /* CreateRecord(STRPTR BBSName):
  324.      *
  325.      *    Start recording incoming and outgoing text.
  326.      */
  327.  
  328. BOOL
  329. CreateRecord(STRPTR BBSName)
  330. {
  331.     DeleteRecord();
  332.  
  333.     if(RecordList = (struct List *)AllocVecPooled(sizeof(struct List),MEMF_ANY))
  334.     {
  335.         if(RecordAuxBuffer = (STRPTR)AllocVecPooled(1024,MEMF_ANY))
  336.         {
  337.             strcpy(RecordName,BBSName);
  338.  
  339.             NewList(RecordList);
  340.  
  341.             GetSysTime(&RecordTime);
  342.  
  343.             return(TRUE);
  344.         }
  345.  
  346.         FreeVecPooled(RecordList);
  347.  
  348.         RecordList = NULL;
  349.     }
  350.  
  351.     return(FALSE);
  352. }
  353.  
  354.     /* DeleteRecord():
  355.      *
  356.      *    Stop recording, free auxilary buffers.
  357.      */
  358.  
  359. VOID
  360. DeleteRecord()
  361. {
  362.     FreeVecPooled(RecordAuxBuffer);
  363.     RecordAuxBuffer = NULL;
  364.  
  365.     DeleteList(RecordList);
  366.     RecordList = NULL;
  367.  
  368.     RecordCount = 0;
  369. }
  370.  
  371.     /* RememberResetOutput():
  372.      *
  373.      *    Reset output monitoring.
  374.      */
  375.  
  376. VOID
  377. RememberResetOutput()
  378. {
  379.     RememberOutputSize = 0;
  380. }
  381.  
  382.     /* RememberOutputText(register STRPTR String,register LONG Size):
  383.      *
  384.      *    Remember the last ten characters received.
  385.      */
  386.  
  387. VOID
  388. RememberOutputText(register STRPTR String,register LONG Size)
  389. {
  390.     if(Size >= REMEMBER_OUT)
  391.     {
  392.         CopyMem(String + Size - REMEMBER_OUT,RememberOutputData,REMEMBER_OUT);
  393.  
  394.         RememberOutputSize = REMEMBER_OUT;
  395.     }
  396.     else
  397.     {
  398.         if(RememberOutputSize + Size > REMEMBER_OUT)
  399.         {
  400.             LONG Delta = RememberOutputSize + Size - REMEMBER_OUT,i;
  401.  
  402.             for(i = 0 ; i < RememberOutputSize - Delta ; i++)
  403.                 RememberOutputData[i] = RememberOutputData[Delta + i];
  404.  
  405.             while(i < REMEMBER_OUT)
  406.                 RememberOutputData[i++] = *String++;
  407.  
  408.             RememberOutputSize = REMEMBER_OUT;
  409.         }
  410.         else
  411.         {
  412.             CopyMem(String,&RememberOutputData[RememberOutputSize],Size);
  413.  
  414.             RememberOutputSize += Size;
  415.         }
  416.     }
  417. }
  418.  
  419.     /* RememberResetInput():
  420.      *
  421.      *    Reset input monitoring.
  422.      */
  423.  
  424. VOID
  425. RememberResetInput()
  426. {
  427.     RememberInputSize = 0;
  428. }
  429.  
  430.     /* RememberInputText(register STRPTR String,register LONG Size):
  431.      *
  432.      *    Remember the last 256 characters sent.
  433.      */
  434.  
  435. VOID
  436. RememberInputText(register STRPTR String,register LONG Size)
  437. {
  438.     if(Size >= REMEMBER_IN)
  439.     {
  440.         CopyMem(String + Size - REMEMBER_IN,RememberInputData,REMEMBER_IN);
  441.  
  442.         RememberInputSize = REMEMBER_IN;
  443.     }
  444.     else
  445.     {
  446.         if(RememberInputSize + Size > REMEMBER_IN)
  447.         {
  448.             LONG Delta = RememberInputSize + Size - REMEMBER_IN,i;
  449.  
  450.             for(i = 0 ; i < RememberInputSize - Delta ; i++)
  451.                 RememberInputData[i] = RememberInputData[Delta + i];
  452.  
  453.             while(i < REMEMBER_IN)
  454.                 RememberInputData[i++] = *String++;
  455.  
  456.             RememberInputSize = REMEMBER_IN;
  457.         }
  458.         else
  459.         {
  460.             CopyMem(String,&RememberInputData[RememberInputSize],Size);
  461.  
  462.             RememberInputSize += Size;
  463.         }
  464.     }
  465. }
  466.  
  467.     /* RememberSpill():
  468.      *
  469.      *    `Spill' the collected text, put it into the list.
  470.      */
  471.  
  472. VOID
  473. RememberSpill()
  474. {
  475.     if(RecordList)
  476.     {
  477.         struct RecordNode    *Node;
  478.         struct timeval         Delta,Backup;
  479.  
  480.             /* Calculate the difference in time
  481.              * between the last line stored and this
  482.              * line getting stored.
  483.              */
  484.  
  485.         GetSysTime(&Backup);
  486.  
  487.         Delta = Backup;
  488.         SubTime(&Delta,&RecordTime);
  489.  
  490.         RecordTime = Backup;
  491.  
  492.         if(!Delta.tv_secs)
  493.             Delta.tv_secs = 1;
  494.  
  495.         Delta.tv_micro = 0;
  496.  
  497.         if(RememberOutputSize)
  498.         {
  499.             TranslateBack(RememberOutputData,RememberOutputSize,RecordAuxBuffer);
  500.  
  501.             if(Node = (struct RecordNode *)AllocVecPooled(sizeof(struct RecordNode) + strlen(RecordAuxBuffer) + 1,MEMF_ANY))
  502.             {
  503.                 Node->Node.ln_Name = (STRPTR)(Node + 1);
  504.                 Node->Node.ln_Type = RECORD_OUTPUT;
  505.  
  506.                 strcpy(Node->Node.ln_Name,RecordAuxBuffer);
  507.  
  508.                 Node->Time = Delta;
  509.  
  510.                 AddTail(RecordList,(struct Node *)Node);
  511.  
  512.                 RecordCount++;
  513.             }
  514.         }
  515.  
  516.         if(RememberInputSize)
  517.         {
  518.             TranslateBack(RememberInputData,RememberInputSize,RecordAuxBuffer);
  519.  
  520.             if(Node = (struct RecordNode *)AllocVecPooled(sizeof(struct RecordNode) + strlen(RecordAuxBuffer) + 1,MEMF_ANY))
  521.             {
  522.                 Node->Node.ln_Name = (STRPTR)(Node + 1);
  523.                 Node->Node.ln_Type = RECORD_INPUT;
  524.  
  525.                 strcpy(Node->Node.ln_Name,RecordAuxBuffer);
  526.  
  527.                 Node->Time = Delta;
  528.  
  529.                 AddTail(RecordList,(struct Node *)Node);
  530.  
  531.                 RecordCount++;
  532.             }
  533.         }
  534.     }
  535.  
  536.     RememberOutputSize = RememberInputSize = 0;
  537. }
  538.