home *** CD-ROM | disk | FTP | other *** search
/ Amiga Elysian Archive / AmigaElysianArchive.iso / comm / term23_2.lha / Source_Code / XPRAscii / xprascii.c < prev    next >
C/C++ Source or Header  |  1992-05-09  |  19KB  |  976 lines

  1.  
  2.  
  3. #include "csource/xprascii.h"
  4.  
  5.  
  6. STATIC BOOL test(struct XPR_IO *io);
  7. STATIC BOOL setup(struct XPR_IO *io);
  8. STATIC VOID ParseConfigString(struct XPR_IO *io, char *buf);
  9. STATIC UBYTE *FindOption(UBYTE *buf, UBYTE option);
  10. STATIC LONG AtoL(UBYTE *);
  11. VOID myGetSysTime(ULONG *);
  12. VOID myGetDate(BPTR);
  13.  
  14.  
  15. LONG __saveds __asm XProtocolCleanup(register __a0 struct XPR_IO *io)
  16. {
  17.     struct XProtocolData *xdata = (struct XProtocolData *)io->xpr_data;
  18.  
  19.     if(xdata)
  20.     {
  21.         FreeMem(xdata, sizeof(struct XProtocolData));
  22.         io->xpr_data = NULL;
  23.     }
  24.  
  25.     return(XPRS_SUCCESS);
  26. }
  27.  
  28.  
  29. LONG __saveds __asm XProtocolSetup(register __a0 struct XPR_IO *io)
  30. {
  31.     struct XProtocolData *xdata;
  32.  
  33.     if(test(io) == FALSE)
  34.         return(XPRS_FAILURE);
  35.  
  36.     if(io->xpr_data == NULL)
  37.     {
  38.         if(setup(io) == FALSE)
  39.             return(XPRS_FAILURE);
  40.     }
  41.  
  42.     xdata = (struct XProtocolData *)io->xpr_data;
  43.  
  44.  
  45.     /* If setup string isn't handed to us, ask questions */
  46.  
  47.     if(io->xpr_filename == NULL)
  48.     {
  49.         if(io->xpr_options != NULL)
  50.         {
  51.             enum { OPT_HEADER=0, OPT_CHARDELAY, OPT_LINEDELAY, OPT_LF_CONVERT,
  52.                      OPT_CR_CONVERT, OPT_PROMPTCHAR, OPT_EXPANDBLANKS,
  53.                      /* OPT_UU_MODE,*/ OPT_STRIPHIBIT };
  54.             ULONG numopts;
  55.  
  56.         struct xpr_option {
  57.            char *xpro_description;      /* description of the option                  */
  58.            long  xpro_type;             /* type of option                             */
  59.            char *xpro_value;            /* pointer to a buffer with the current value */
  60.            long  xpro_length;           /* buffer size                                */
  61.         };
  62.             struct xpr_option *opti[10];
  63.             UBYTE charbuf[LONGLEN], linebuf[LONGLEN], lfbuf[CHARLEN],
  64.                     crbuf[CHARLEN], stripbuf[STRINGLEN], uubuf[STRINGLEN],
  65.                     expandbuf[STRINGLEN];
  66.  
  67.             struct xpr_option opt0;
  68.             struct xpr_option opt1;
  69.             struct xpr_option opt2;
  70.             struct xpr_option opt3;
  71.             struct xpr_option opt4;
  72.             struct xpr_option opt5;
  73.             struct xpr_option opt6;
  74.             struct xpr_option opt7;
  75.             struct xpr_option opt8;
  76.             struct xpr_option opt9;
  77.  
  78.             opti[0] = &opt0;
  79.             opti[1] = &opt1;
  80.             opti[2] = &opt2;
  81.             opti[3] = &opt3;
  82.             opti[4] = &opt4;
  83.             opti[5] = &opt5;
  84.             opti[6] = &opt6;
  85.             opti[7] = &opt7;
  86.             opti[8] = &opt8;
  87.             opti[9] = &opt9;
  88.  
  89.  
  90.             numopts = 0;
  91.  
  92.             opti[OPT_HEADER]->xpro_description    = "ASCII Options:";
  93.             opti[OPT_HEADER]->xpro_type    = XPRO_HEADER;
  94.             opti[OPT_HEADER]->xpro_value    = NULL;
  95.             opti[OPT_HEADER]->xpro_length    = NULL;
  96.  
  97. /* */
  98.  
  99.             numopts++;
  100.             opti[OPT_CHARDELAY]->xpro_description    = "Char Delay (ticks):";
  101.             opti[OPT_CHARDELAY]->xpro_type            = XPRO_LONG;
  102.             sprintf(charbuf, "%ld", xdata->CharDelay);
  103.             opti[OPT_CHARDELAY]->xpro_value            = charbuf;
  104.             opti[OPT_CHARDELAY]->xpro_length            = LONGLEN;
  105.  
  106. /* */
  107.  
  108.             numopts++;
  109.             opti[OPT_LINEDELAY]->xpro_description    = "Line Delay (ticks):";
  110.             opti[OPT_LINEDELAY]->xpro_type            = XPRO_LONG;
  111.             sprintf(linebuf, "%ld", xdata->LineDelay);
  112.             opti[OPT_LINEDELAY]->xpro_value            = linebuf;
  113.             opti[OPT_LINEDELAY]->xpro_length            = LONGLEN;
  114.  
  115. /* */
  116.  
  117.             numopts++;
  118.             switch(xdata->LF_Mode)
  119.             {
  120.                 case STRIP_MODE:
  121.                     lfbuf[0] = 'S';
  122.                 break;
  123.  
  124.                 case ADD_MODE:
  125.                     lfbuf[0] = 'A';
  126.                 break;
  127.  
  128.                 case EXCHANGE_MODE:
  129.                     lfbuf[0] = 'X';
  130.                 break;
  131.  
  132.                 default:
  133.                     lfbuf[0] = 'N';
  134.                 break;
  135.  
  136.             }
  137.             lfbuf[1] = '\0';
  138.  
  139.             opti[OPT_LF_CONVERT]->xpro_description    = "Convert `LF' (N,S,A,X)";
  140.             opti[OPT_LF_CONVERT]->xpro_type            = XPRO_STRING;
  141.             opti[OPT_LF_CONVERT]->xpro_value            = lfbuf;
  142.             opti[OPT_LF_CONVERT]->xpro_length        = CHARLEN;
  143.  
  144. /* */
  145.  
  146.             numopts++;
  147.             switch(xdata->CR_Mode)
  148.             {
  149.                 case STRIP_MODE:
  150.                     crbuf[0] = 'S';
  151.                 break;
  152.  
  153.                 case ADD_MODE:
  154.                     crbuf[0] = 'A';
  155.                 break;
  156.  
  157.                 case EXCHANGE_MODE:
  158.                     crbuf[0] = 'X';
  159.                 break;
  160.  
  161.                 default:
  162.                     crbuf[0] = 'N';
  163.                 break;
  164.  
  165.             }
  166.             crbuf[1] = '\0';
  167.  
  168.             opti[OPT_CR_CONVERT]->xpro_description    = "Convert `CR' (N,S,A,X)";
  169.             opti[OPT_CR_CONVERT]->xpro_type            = XPRO_STRING;
  170.             opti[OPT_CR_CONVERT]->xpro_value            = crbuf;
  171.             opti[OPT_CR_CONVERT]->xpro_length        = CHARLEN;
  172.  
  173. /* */
  174.  
  175.             numopts++;
  176.             opti[OPT_PROMPTCHAR]->xpro_description    = "Prompt Char:";
  177.             opti[OPT_PROMPTCHAR]->xpro_type            = XPRO_STRING;
  178.             opti[OPT_PROMPTCHAR]->xpro_value            = &xdata->PromptChar;
  179.             opti[OPT_PROMPTCHAR]->xpro_length        = CHARLEN;
  180.  
  181. /* */
  182. /*
  183. **            numopts++;
  184. **            if(xdata->UU_Mode)
  185. **                strcpy(uubuf, "on");
  186. **            else
  187. **                strcpy(uubuf, "off");
  188. **            opti[OPT_UU_MODE]->xpro_description    = "Use uuencode & decode:";
  189. **            opti[OPT_UU_MODE]->xpro_type            = XPRO_BOOLEAN;
  190. **            opti[OPT_UU_MODE]->xpro_value            = uubuf;
  191. **            opti[OPT_UU_MODE]->xpro_length        = STRINGLEN;
  192. */
  193. /* */
  194.  
  195.             numopts++;
  196.             if(xdata->ExpandBlanks)
  197.                 strcpy(expandbuf, "on");
  198.             else
  199.                 strcpy(expandbuf, "off");
  200.             opti[OPT_EXPANDBLANKS]->xpro_description    = "Expand Blank Lines:";
  201.             opti[OPT_EXPANDBLANKS]->xpro_type            = XPRO_BOOLEAN;
  202.             opti[OPT_EXPANDBLANKS]->xpro_value            = expandbuf;
  203.             opti[OPT_EXPANDBLANKS]->xpro_length            = STRINGLEN;
  204.  
  205. /* */
  206.  
  207.             numopts++;
  208.             if(xdata->StripHiBit)
  209.                 strcpy(stripbuf, "on");
  210.             else
  211.                 strcpy(stripbuf, "off");
  212.             opti[OPT_STRIPHIBIT]->xpro_description    = "Strip High Bit:";
  213.             opti[OPT_STRIPHIBIT]->xpro_type            = XPRO_BOOLEAN;
  214.             opti[OPT_STRIPHIBIT]->xpro_value            = stripbuf;
  215.             opti[OPT_STRIPHIBIT]->xpro_length        = STRINGLEN;
  216.  
  217.  
  218.             io->xpr_options(++numopts, opti); 
  219.  
  220.  
  221.             xdata->CharDelay = AtoL(charbuf);
  222.             if(xdata->CharDelay > 500)
  223.                 xdata->CharDelay = 500;
  224.  
  225.  
  226.             xdata->LineDelay = AtoL(linebuf);
  227.             if(xdata->LineDelay > 500)
  228.                 xdata->LineDelay = 500;
  229.  
  230.             switch(*lfbuf)
  231.             {
  232.                 case 's':
  233.                 case 'S':    /* Strip LF */
  234.                     xdata->LF_Mode = STRIP_MODE;
  235.                 break;
  236.  
  237.                 case 'a':
  238.                 case 'A':    /* Add CR */
  239.                     xdata->LF_Mode = ADD_MODE;
  240.                 break;
  241.  
  242.                 case 'x':
  243.                 case 'X':    /* LF -> CR */
  244.                     xdata->LF_Mode = EXCHANGE_MODE;
  245.                 break;
  246.  
  247.                 default:        /* None */
  248.                     xdata->LF_Mode = NONE_MODE;
  249.                 break;
  250.  
  251.             }
  252.  
  253.             switch(*crbuf)
  254.             {
  255.                 case 's':
  256.                 case 'S':    /* Strip CR */
  257.                     xdata->CR_Mode = STRIP_MODE;
  258.                 break;
  259.  
  260.                 case 'a':
  261.                 case 'A':    /* Add LF */
  262.                     xdata->CR_Mode = ADD_MODE;
  263.                 break;
  264.  
  265.                 case 'x':
  266.                 case 'X':    /* CR -> LF */
  267.                     xdata->CR_Mode = EXCHANGE_MODE;
  268.                 break;
  269.  
  270.                 default:        /* None */
  271.                     xdata->CR_Mode = NONE_MODE;
  272.                 break;
  273.  
  274.             }
  275.  
  276.             xdata->ExpandBlanks    = (!stricmp(expandbuf, "yes") ||
  277.                                             !stricmp(expandbuf, "on"));
  278.  
  279. /*
  280. **            xdata->UU_Mode            = (!stricmp(uubuf, "yes") ||
  281. **                                            !stricmp(uubuf, "on"));
  282. */
  283.             xdata->StripHiBit        = (!stricmp(stripbuf, "yes") ||
  284.                                             !stricmp(stripbuf, "on"));
  285.  
  286. /*            xdata->PromptChar updated sich selbst */
  287.         }
  288.         else
  289.         {
  290.             if(io->xpr_gets != NULL)
  291.             {
  292.                 UWORD expand, strip;
  293.                 UBYTE lf, cr, buffy[128];
  294.  
  295.                 expand = (xdata->ExpandBlanks)    ? 1 : 0;
  296.                 strip     = (xdata->StripHiBit)        ? 1 : 0;
  297.  
  298.                 switch(xdata->LF_Mode)
  299.                 {
  300.                     case STRIP_MODE:
  301.                         lf = 'S';
  302.                     break;
  303.  
  304.                     case ADD_MODE:
  305.                         lf = 'A';
  306.                     break;
  307.  
  308.                     case EXCHANGE_MODE:
  309.                         lf = 'X';
  310.                     break;
  311.  
  312.                     default:
  313.                         lf = 'N';
  314.                     break;
  315.  
  316.                 }
  317.  
  318.                 switch(xdata->CR_Mode)
  319.                 {
  320.                     case STRIP_MODE:
  321.                         cr = 'S';
  322.                     break;
  323.  
  324.                     case ADD_MODE:
  325.                         cr = 'A';
  326.                     break;
  327.  
  328.                     case EXCHANGE_MODE:
  329.                         cr = 'X';
  330.                     break;
  331.  
  332.                     default:
  333.                         cr = 'N';
  334.                     break;
  335.  
  336.                 }
  337.  
  338.                 sprintf(buffy, "C%ld,L%ld,F%lc,R%lc,E%ld,S%ld,P%lc", xdata->CharDelay, xdata->LineDelay, lf, cr, expand, strip, xdata->PromptChar);
  339.  
  340.                 if(io->xpr_gets("ASCII Options", buffy))
  341.                     ParseConfigString(io, buffy);
  342.             }
  343.         }
  344.     }
  345.     else
  346.         ParseConfigString(io, io->xpr_filename);
  347.  
  348.     return(XPRS_SUCCESS);
  349. }
  350.  
  351.  
  352. STATIC VOID WaitForPrompt(struct XPR_IO *io)
  353. {
  354.     struct XProtocolData *xdata = (struct XProtocolData *)io->xpr_data;
  355.     UWORD data;
  356.  
  357.     if(data = io->xpr_sread(xdata->SerBuf, 1, 0) > 0)
  358.     {
  359.         UWORD i;
  360.  
  361.         for(i=0; i<data; i++)
  362.         {
  363.             if(xdata->SerBuf[i] == xdata->PromptChar)
  364.                 return;
  365.         }
  366.     }
  367.  
  368.     for(;;)
  369.     {
  370.         if(io->xpr_sread(xdata->SerBuf, 1, 10000000) > 0)
  371.         {
  372.             if(xdata->SerBuf[0] == xdata->PromptChar)
  373.                 break;
  374.         }
  375.         else
  376.             break;
  377.     }
  378. }
  379.  
  380.  
  381. STATIC BOOL SendAsciiPacket(struct XPR_IO *io, UBYTE *filebuf, ULONG datalen)
  382. {
  383.     struct XProtocolData *xdata = (struct XProtocolData *)io->xpr_data;
  384.     UWORD i, out;
  385.     UBYTE *ptr;
  386.  
  387.     ptr = filebuf;
  388.  
  389.     for(i=0, out=0; i<datalen; i++, ptr++)
  390.     {
  391.         if(*ptr == '\n')
  392.         {
  393.             switch(xdata->LF_Mode)
  394.             {
  395.                 case STRIP_MODE:
  396.                     ;
  397.                 continue;
  398.  
  399.                 case ADD_MODE:
  400.                     xdata->SerBuf[out++] = '\r';
  401.                 break;
  402.  
  403.                 case EXCHANGE_MODE:
  404.                     *ptr = '\r';
  405.                 break;
  406.  
  407.             }
  408.         }
  409.  
  410.         if(*ptr == '\r')
  411.         {
  412.             switch(xdata->CR_Mode)
  413.             {
  414.                 case STRIP_MODE:
  415.                     ;
  416.                 continue;
  417.  
  418.                 case ADD_MODE:
  419.                     xdata->SerBuf[out++] = '\n';
  420.                     xdata->SerBuf[out++] = '\r';
  421.                 continue;
  422.  
  423.                 case EXCHANGE_MODE:
  424.                     *ptr = '\n';
  425.                 break;
  426.  
  427.             }
  428.         }
  429.  
  430.         xdata->SerBuf[out++] = *ptr;
  431.     }
  432.  
  433.  
  434.     if(xdata->ExpandBlanks  &&  (xdata->SerBuf[0] == '\n'  ||  xdata->SerBuf[0] == '\r'))
  435.         io->xpr_swrite(" ", 1);
  436.  
  437.  
  438.     if(xdata->CharDelay)    /* writin' in slo'-motion..(-: */
  439.     {
  440.         ptr = xdata->SerBuf;
  441.         for(i=0; i<out; i++, ptr++)
  442.         {
  443.             io->xpr_swrite(ptr, 1);
  444.            Delay(xdata->CharDelay);
  445.         }
  446.     }
  447.     else
  448.         io->xpr_swrite(xdata->SerBuf, out);    /* BLAST IT..!! */
  449.  
  450.  
  451.     if(xdata->LineDelay)
  452.           Delay(xdata->LineDelay);
  453.  
  454.     if(xdata->PromptChar  &&  xdata->PromptChar    != ' ')
  455.         WaitForPrompt(io);
  456.  
  457.     io->xpr_sflush();
  458.  
  459.     return(io->xpr_chkabort());
  460. }
  461.  
  462.  
  463. /*
  464. **STATIC BOOL uudecode(struct XPR_IO *io)
  465. **{
  466. **    struct XProtocolData *xdata = (struct XProtocolData *)io->xpr_data;
  467. **    BPTR fh;
  468. **    ULONG systemtags[] = { SYS_Output, 0, TAG_DONE };
  469. **    BOOL success;
  470. **
  471. **    if((fh = Open("T:uudecode.log", MODE_OLDFILE)) == NULL)
  472. **         fh = Open("T:uudecode.log", MODE_NEWFILE);
  473. **    else
  474. **        Seek(fh, 0, OFFSET_END);
  475. **
  476. **    sprintf(&xdata->FileBuf[511], "uudecode %s", xdata->FileBuf);
  477. **    if(fh)
  478. **    {
  479. **        fprintf(fh, "-------------------------------\n");
  480. **        myGetDate(fh);
  481. **        fprintf(fh, "System(\"%s\")\n", &xdata->FileBuf[511]);
  482. **    }
  483. **
  484. **    systemtags[1] = fh;
  485. **    success = (System(&xdata->FileBuf[511], (APTR)&systemtags[0]) != -1);
  486. **
  487. **    if(fh)
  488. **        Close(fh);
  489. **
  490. **    return(success);
  491. **}
  492. **
  493. **
  494. **STATIC VOID *uuencode(struct XPR_IO *io, VOID *fp)
  495. **{
  496. **    struct XProtocolData *xdata = (struct XProtocolData *)io->xpr_data;
  497. **    VOID *tmp_fp=NULL;
  498. **    BPTR fh;
  499. **    ULONG sys_time;
  500. **    ULONG systemtags[] = { SYS_Output, 0, TAG_DONE };
  501. **    UBYTE tmp_file[24];
  502. **
  503. **    if((fh = Open("T:uuencode.log", MODE_OLDFILE)) == NULL)
  504. **         fh = Open("T:uuencode.log", MODE_NEWFILE);
  505. **    else
  506. **        Seek(fh, 0, OFFSET_END);
  507. **
  508. **    myGetSysTime(&sys_time);
  509. **    sprintf(tmp_file, "T:%ld.uue", sys_time);
  510. **    sprintf(xdata->FileBuf, "uuencode %s %s", io->xpr_filename, tmp_file);
  511. **    if(fh)
  512. **    {
  513. **        fprintf(fh, "-------------------------------\n");
  514. **        myGetDate(fh);
  515. **        fprintf(fh, "System(\"%s\")\n", xdata->FileBuf);
  516. **    }
  517. **
  518. **    systemtags[1] = fh;
  519. **    if(System(xdata->FileBuf, (APTR)&systemtags[0]) != -1)
  520. **        tmp_fp = io->xpr_fopen(tmp_file, "r");
  521. **
  522. **    if(fh)
  523. **        Close(fh);
  524. **
  525. **    return(tmp_fp);
  526. **}
  527. */
  528.  
  529. LONG __saveds __asm XProtocolSend(register __a0 struct XPR_IO *io)
  530. {
  531.     struct XPR_UPDATE xpru;
  532.     struct XProtocolData *xdata;
  533.     VOID *fp;
  534.     LONG read;
  535.     BOOL brkflag;
  536.  
  537.     if(test(io) == FALSE)
  538.         return(XPRS_FAILURE);
  539.  
  540.     if(io->xpr_data == NULL)
  541.     {
  542.         if(setup(io) == FALSE)
  543.         {
  544.           xpru.xpru_updatemask = XPRU_ERRORMSG;
  545.           xpru.xpru_errormsg   = "Ran out of memory!";
  546.             io->xpr_update(&xpru);
  547.             return(XPRS_FAILURE);
  548.         }
  549.     }
  550.     xdata = (struct XProtocolData *)io->xpr_data;
  551.  
  552.  
  553.     xpru.xpru_updatemask    = XPRU_FILENAME;
  554.     xpru.xpru_filename    = io->xpr_filename;
  555.     io->xpr_update(&xpru);
  556.  
  557.     fp = io->xpr_fopen(io->xpr_filename, "r");
  558.    if(fp == NULL)
  559.     {
  560.         xpru.xpru_updatemask    = XPRU_ERRORMSG;
  561.         xpru.xpru_errormsg    = "Failed to open input file";
  562.         io->xpr_update(&xpru);
  563.         return(XPRS_FAILURE);
  564.     }
  565.  
  566. /*
  567. **    if(xdata->UU_Mode)
  568. **    {
  569. **        VOID *tmp_fp;
  570. **
  571. **        if(tmp_fp = uuencode(io, fp))
  572. **        {
  573. **            io->xpr_fclose(fp);
  574. **            fp = tmp_fp;
  575. **        }
  576. **        else
  577. **        {
  578. **            io->xpr_fclose(fp);
  579. **            xpru.xpru_updatemask    = XPRU_ERRORMSG;
  580. **            xpru.xpru_errormsg    = "Failed to create uuencoded file";
  581. **            io->xpr_update(&xpru);
  582. **            return(XPRS_FAILURE);
  583. **        }
  584. **    }
  585. */
  586.     xpru.xpru_updatemask    = XPRU_PACKETDELAY | XPRU_CHARDELAY | XPRU_MSG;
  587.  
  588.     xpru.xpru_packetdelay= xdata->LineDelay * 20;  /* msec! */
  589.     xpru.xpru_chardelay    = xdata->CharDelay * 20;  /* msec! */
  590. /*
  591. **    xpru.xpru_msg            = (xdata->UU_Mode) ? "Sending uuencoded File" :
  592. **                                                            "Starting ASCII Send";
  593. */
  594.     xpru.xpru_msg            = "Starting ASCII Send";
  595.     io->xpr_update(&xpru);
  596.  
  597.  
  598.     xpru.xpru_bytes        = 0;
  599.     xpru.xpru_blocks        = 0;
  600.     xpru.xpru_blocksize    = 0;
  601.  
  602.     while(read = io->xpr_fread(xdata->FileBuf, 1, FILEBUF, fp))
  603.     {
  604.         WORD send, sent;
  605.         UBYTE *buf;
  606.  
  607.         for(send=read, buf=xdata->FileBuf; send>0; buf+=sent, send-=sent)
  608.         {
  609.             sent  = strcspn(buf, "\r\n");
  610.             sent++;
  611.  
  612.             xpru.xpru_updatemask = XPRU_BYTES | XPRU_BLOCKS | XPRU_BLOCKSIZE;
  613.             xpru.xpru_blocks++;
  614.             xpru.xpru_bytes     += sent;
  615.             xpru.xpru_blocksize  = sent;
  616.             io->xpr_update(&xpru);
  617.  
  618.             if(brkflag = SendAsciiPacket(io, buf, sent))
  619.                 goto bibi;
  620.         }
  621.     }
  622.  
  623. bibi:
  624.     io->xpr_fclose(fp);
  625.  
  626.     xpru.xpru_updatemask = XPRU_MSG;
  627.     xpru.xpru_msg = (brkflag) ? "Aborted" : "Done";
  628.     io->xpr_update(&xpru);
  629.  
  630.     return((brkflag) ? XPRS_SUCCESS : XPRS_FAILURE);
  631. }
  632.  
  633.  
  634. LONG __saveds __asm XProtocolReceive(register __a0 struct XPR_IO *io)
  635. {
  636.     struct XPR_UPDATE xpru;
  637.     struct XProtocolData *xdata;
  638.     VOID *fp;
  639.     LONG read;
  640.     BOOL brkflag=FALSE;
  641.  
  642.     if(test(io) == FALSE)
  643.         return(XPRS_FAILURE);
  644.  
  645.     if(io->xpr_data == NULL)
  646.     {
  647.         if(setup(io) == FALSE)
  648.         {
  649.           xpru.xpru_updatemask = XPRU_ERRORMSG;
  650.           xpru.xpru_errormsg   = "Ran out of memory!";
  651.             io->xpr_update(&xpru);
  652.             return(XPRS_FAILURE);
  653.         }
  654.     }
  655.     xdata = (struct XProtocolData *)io->xpr_data;
  656.  
  657.     fp = io->xpr_fopen(io->xpr_filename, "w");
  658.    if(fp == NULL)
  659.     {
  660.         xpru.xpru_updatemask = XPRU_ERRORMSG | XPRU_FILENAME;
  661.         xpru.xpru_errormsg   = "Failed to open output file";
  662.         xpru.xpru_filename   = xdata->FileBuf;
  663.         io->xpr_update(&xpru);
  664.         return(XPRS_FAILURE);
  665.    }
  666.  
  667.     xpru.xpru_updatemask = XPRU_MSG | XPRU_FILENAME;
  668.     xpru.xpru_msg        = "Starting ASCII Receive";
  669.     xpru.xpru_filename   = xdata->FileBuf;
  670.     io->xpr_update(&xpru);
  671.  
  672.  
  673.     xpru.xpru_bytes        = 0;
  674.     xpru.xpru_blocks        = 0;
  675.     xpru.xpru_blocksize    = 0;
  676.     while((read = io->xpr_sread(xdata->SerBuf, 80, 5000000)) > 0)
  677.     {
  678.         if(xdata->StripHiBit)
  679.         {
  680.             UWORD i;
  681.  
  682.             for(i=0; i<read; i++)
  683.                 xdata->SerBuf[i] &= 0x7f;
  684.         }
  685.  
  686.       xpru.xpru_updatemask    = XPRU_BYTES | XPRU_BLOCKS | XPRU_BLOCKSIZE;
  687.       xpru.xpru_bytes      += read;
  688.       xpru.xpru_blocks++;
  689.       xpru.xpru_blocksize  = read;
  690.       io->xpr_update(&xpru);
  691.  
  692.       io->xpr_fwrite(xdata->SerBuf, 1, read, fp);
  693.  
  694.         if(brkflag = io->xpr_chkabort())
  695.             break;
  696.    }
  697.  
  698.     io->xpr_fclose(fp);
  699.     fp = NULL;
  700.  
  701. /*
  702. **    if(xdata->UU_Mode)
  703. **    {
  704. **        uudecode(io);
  705. **    }
  706. */
  707.  
  708.     xpru.xpru_updatemask = XPRU_MSG;
  709.     xpru.xpru_msg = (brkflag) ? "Aborted" : "Done";
  710.     io->xpr_update(&xpru);
  711.  
  712.     return((brkflag) ? XPRS_SUCCESS : XPRS_FAILURE);
  713. }
  714.  
  715.  
  716. LONG __saveds __asm XProtocolHostMon(register __a0 struct XPR_IO *io, register __a1 UBYTE *serbuff, register __d0 LONG actual, register __d1 LONG maxsize)
  717. {
  718.   return(actual);
  719. }
  720.  
  721.  
  722. LONG __saveds __asm XProtocolUserMon(register __a0 struct XPR_IO *io, register __a1 UBYTE *serbuff, register __d0 LONG actual, register __d1 LONG maxsize)
  723. {
  724.   return(actual);
  725. }
  726.  
  727.  
  728. STATIC BOOL test(struct XPR_IO *io)
  729. {
  730.     /* all we need..(-: */
  731.  
  732.     if(io->xpr_swrite == NULL)
  733.         return(FALSE);
  734.  
  735.     if(io->xpr_sread == NULL)
  736.         return(FALSE);
  737.  
  738.     if(io->xpr_sflush == NULL)
  739.         return(FALSE);
  740.  
  741.     if(io->xpr_fopen == NULL)
  742.         return(FALSE);
  743.  
  744.     if(io->xpr_fwrite == NULL)
  745.         return(FALSE);
  746.  
  747.     if(io->xpr_fread == NULL)
  748.         return(FALSE);
  749.  
  750.     if(io->xpr_fclose == NULL)
  751.         return(FALSE);
  752.  
  753.     if(io->xpr_update == NULL)
  754.         return(FALSE);
  755.  
  756.     if(io->xpr_chkabort == NULL)
  757.         return(FALSE);
  758.  
  759.     return(TRUE);
  760. }
  761.  
  762.  
  763. STATIC BOOL setup(struct XPR_IO *io)
  764. {
  765.     struct XProtocolData *xdata = (struct XProtocolData *)io->xpr_data;
  766.  
  767.     xdata = io->xpr_data = AllocMem(sizeof(struct XProtocolData), MEMF_PUBLIC | MEMF_CLEAR);
  768.  
  769.     if(io->xpr_data == NULL)
  770.         return(FALSE);
  771.  
  772. /* some good settings.. */
  773.     xdata->CharDelay    = 0;
  774.     xdata->LineDelay    = 0;
  775.     xdata->PromptChar    = ' ';
  776.  
  777.     xdata->ExpandBlanks    = TRUE;
  778.     xdata->StripHiBit        = FALSE;
  779. /*    xdata->UU_Mode            = FALSE;*/
  780.  
  781.     xdata->LF_Mode = NONE_MODE;
  782.     xdata->CR_Mode = NONE_MODE;
  783.  
  784.     return(TRUE);
  785. }
  786.  
  787. /* Search for specified option setting in string */
  788. STATIC UBYTE *FindOption(UBYTE *buf, UBYTE option)
  789. {
  790.     while(*buf)
  791.     {
  792.         buf += strspn(buf," ,\t\r\n");
  793.         if(*buf == option)
  794.             return(++buf);
  795.         buf += strcspn(buf," ,\t\r\n");
  796.   }
  797.  
  798.   return(NULL);
  799. }
  800.  
  801.  
  802. STATIC VOID ParseConfigString(struct XPR_IO *io, char *buf)
  803. {
  804.     struct XProtocolData *xdata = (struct XProtocolData *)io->xpr_data;
  805.     UBYTE *p;
  806.  
  807.     if(p = FindOption(buf, 'P'))
  808.         xdata->PromptChar = *p;
  809.     else
  810.     {
  811.         if(p = FindOption(buf, 'p'))
  812.             xdata->PromptChar = *p;
  813.     }
  814.  
  815.     strupr(buf);
  816.  
  817.     if(p = FindOption(buf, 'C'))
  818.     {
  819.         xdata->CharDelay = AtoL(p);
  820.         if(xdata->CharDelay > 500)
  821.             xdata->CharDelay = 500;
  822.     }
  823.  
  824.  
  825.     if(p = FindOption(buf, 'L'))
  826.     {
  827.         xdata->LineDelay = AtoL(p);
  828.         if(xdata->LineDelay > 500)
  829.             xdata->LineDelay = 500;
  830.     }
  831.  
  832.  
  833.     if(p = FindOption(buf, 'F'))
  834.     {
  835.         switch(*p)
  836.         {
  837.             case 'A':
  838.                 xdata->LF_Mode = ADD_MODE;
  839.             break;
  840.  
  841.             case 'S':
  842.                 xdata->LF_Mode = STRIP_MODE;
  843.             break;
  844.  
  845.             case 'X':
  846.                 xdata->LF_Mode = EXCHANGE_MODE;
  847.             break;
  848.  
  849.             default:
  850.                 xdata->LF_Mode = NONE_MODE;
  851.             break;
  852.  
  853.         }
  854.     }
  855.  
  856.  
  857.     if(p = FindOption(buf, 'R'))
  858.     {
  859.         switch(*p)
  860.         {
  861.             case 'A':
  862.                 xdata->CR_Mode = ADD_MODE;
  863.             break;
  864.  
  865.             case 'S':
  866.                 xdata->CR_Mode = STRIP_MODE;
  867.             break;
  868.  
  869.             case 'X':    /* LF -> CR */
  870.                 xdata->CR_Mode = EXCHANGE_MODE;
  871.             break;
  872.  
  873.             default:
  874.                 xdata->CR_Mode = NONE_MODE;
  875.             break;
  876.  
  877.         }
  878.     }
  879.  
  880.  
  881.     if(p = FindOption(buf, 'E'))
  882.         xdata->ExpandBlanks = (*p == '1');
  883.  
  884. /*
  885. **    if(p = FindOption(buf, 'U'))
  886. **        xdata->UU_Mode = (*p == '1');
  887. */
  888.  
  889.     if(p = FindOption(buf, 'S'))
  890.         xdata->StripHiBit = (*p == '1');
  891. }
  892.  
  893.  
  894. STATIC LONG AtoL(UBYTE *str)
  895. {
  896.     LONG cnt=0, help;
  897.  
  898.     while(*str <= ' ')        /* skip white spaces.. */
  899.     {
  900.         if(*str == '\0')
  901.             return(0);
  902.         str++;
  903.     }
  904.  
  905.     if(*str == '-')
  906.     {
  907.         help = -1;
  908.         str++;
  909.     }
  910.     else
  911.     {
  912.         if(*str == '+')
  913.             str++;
  914.         help = 1;
  915.     }
  916.     
  917.     for(;;)
  918.     {
  919.         if(*str >= '0' && *str <= '9')
  920.         {
  921.             cnt *= 10;
  922.             cnt += *str - '0';
  923.         }
  924.         else
  925.             break;
  926.  
  927.         if(!(*str))
  928.             break;
  929.  
  930.         str++;
  931.     }
  932.  
  933.     return(cnt * help);
  934. }
  935.  
  936.  
  937. /**********************************************************
  938.  *    ULONG getsystime(struct timeval *tv)
  939.  *
  940.  *      This function was rewritten using DateStamp() to
  941.  * eliminate the opening and closing of the timer.device
  942.  * that was occurring everytime this function was called.
  943.  * An attempt to save some processing time.   -WMP-
  944.  **********************************************************/
  945. VOID myGetSysTime(ULONG *secs)
  946. {
  947.     struct DateStamp ds;
  948.  
  949.     DateStamp(&ds);
  950.     *secs = (ds.ds_Days * 86400) + (ds.ds_Minute * 60 + (ds.ds_Tick / TICKS_PER_SECOND));
  951. }
  952.  
  953.  
  954. VOID myGetDate(BPTR fh)
  955. {
  956.     struct DateTime dt;
  957.     UBYTE time[12];
  958.     UBYTE date[12];
  959.     UBYTE day[12];
  960.  
  961.     DateStamp(&dt.dat_Stamp);
  962.  
  963.     dt.dat_Format    = FORMAT_DOS;
  964.     dt.dat_Flags    = 0;
  965.     dt.dat_StrDay    = day;
  966.     dt.dat_StrDate    = date;
  967.     dt.dat_StrTime    = time;
  968.  
  969.     DateToStr(&dt);
  970.  
  971.     fprintf(fh, "%s %s %s\n", day, date, time);
  972. }
  973.  
  974.  
  975. /* end of source-code */
  976.