home *** CD-ROM | disk | FTP | other *** search
/ ftp.barnyard.co.uk / 2015.02.ftp.barnyard.co.uk.tar / ftp.barnyard.co.uk / cpm / walnut-creek-CDROM / ENTERPRS / CPM / UTILS / S / ZMP-SRC.LZH / ZMXFER5.C < prev    next >
Text File  |  2000-06-30  |  9KB  |  493 lines

  1. /********************** START OF XFER MODULE 5 ******************************/
  2.  
  3. #include "zmp.h"
  4. #include "zmodem.h"
  5.  
  6. #ifdef   AZTEC_C
  7. #include "libc.h"
  8. #else
  9. #include <stdio.h>
  10. #endif
  11.  
  12. extern int Tryzhdrtype;       /* Header type to send corresponding to Last rx close */
  13. extern char *Rxptr;        /* Pointer to main Rx buffer */
  14.  
  15. zperr(string,incrflag)
  16. char *string;
  17. int incrflag;
  18. {
  19.     clrline(MESSAGE);
  20.     report(MESSAGE,string);
  21.     if (incrflag)
  22.         dreport(ERRORS,++Errors);
  23. }
  24.  
  25. dreport(row,value)
  26. int row, value;
  27. {
  28.     static char buf[7];
  29.  
  30.     report(row,itoa(value,buf));
  31. }
  32.  
  33. lreport(row,value)
  34. int row;
  35. long value;
  36. {
  37.     static char buf[20];
  38.  
  39.     report(row,ltoa(value,buf));
  40. }
  41.  
  42. sreport(sct,bytes)
  43. int sct;
  44. long bytes;
  45. {  
  46.     dreport(BLOCKS,sct);
  47.     lreport(KBYTES,bytes);
  48. }
  49.  
  50. clrline(line)
  51. int line;
  52. {
  53.     report(line,"                ");
  54. }
  55.  
  56. /*
  57.  * Initialize for Zmodem receive attempt, try to activate Zmodem sender
  58.  *  Handles ZSINIT frame
  59.  *  Return ZFILE if Zmodem filename received, -1 on error,
  60.  *   ZCOMPL if transaction finished,  else 0
  61.  */
  62. tryz()
  63. {
  64.     static int c, n, *ip;
  65.     static int cmdzack1flg;
  66.  
  67.     if (Nozmodem)        /* ymodem has been forced */
  68.         return 0;
  69.  
  70.     for (n=Zmodem?15:5; --n>=0; ) {
  71.         if (opabort())
  72.             return NERROR;
  73.         /* Set buffer length (0) and capability flags */
  74.         stohdr(0L);
  75.         Txhdr[ZF0] = (Wantfcs32 ? CANFC32 : 0) | CANFDX;
  76.         if (Zctlesc)
  77.             Txhdr[ZF0] |= TESCCTL;
  78.         ip = (int *)&Txhdr[ZP0];
  79.         *ip = Cpbufsize;
  80.         zshhdr(Tryzhdrtype, Txhdr);
  81.         if (Tryzhdrtype == ZSKIP)    /* Don't skip too far */
  82.             Tryzhdrtype = ZRINIT;    /* CAF 8-21-87 */
  83. again:
  84.         switch (zgethdr(Rxhdr, 0)) {
  85.         case ZRQINIT:
  86.             continue;
  87.         case ZEOF:
  88.             continue;
  89.         case TIMEOUT:
  90.             continue;
  91.         case ZFILE:
  92.             Zconv = Rxhdr[ZF0];
  93.             Zmanag = Rxhdr[ZF1];
  94.             Ztrans = Rxhdr[ZF2];
  95.             Tryzhdrtype = ZRINIT;
  96.             c = zrdata(Secbuf, KSIZE);
  97.             if (c == GOTCRCW)
  98.                 return ZFILE;
  99.             zshhdr(ZNAK, Txhdr);
  100.             goto again;
  101.         case ZSINIT:
  102.             Zctlesc = TESCCTL & Rxhdr[ZF0];
  103.             if (zrdata(Attn, ZATTNLEN) == GOTCRCW) {
  104.                 zshhdr(ZACK, Txhdr);
  105.                 goto again;
  106.             }
  107.             zshhdr(ZNAK, Txhdr);
  108.             goto again;
  109.         case ZFREECNT:
  110.             stohdr(0L);
  111.             zshhdr(ZACK, Txhdr);
  112.             goto again;
  113.         case ZCOMMAND:
  114.             cmdzack1flg = Rxhdr[ZF0];
  115.             if (zrdata(Secbuf, KSIZE) == GOTCRCW) {
  116.                stohdr(0L);
  117.                 purgeline();    /* dump impatient questions */
  118.                 do {
  119.                     zshhdr(ZCOMPL, Txhdr);
  120.                     zperr("Waiting for ZFIN",FALSE);
  121.                     if (opabort())
  122.                         return NERROR;
  123.                 }
  124.                 while (++Errors<20 && zgethdr(Rxhdr,1) != ZFIN);
  125.                 ackbibi();
  126.                 return ZCOMPL;
  127.             }
  128.             zshhdr(ZNAK, Txhdr); 
  129.             goto again;
  130.         case ZCOMPL:
  131.             goto again;
  132.         default:
  133.             continue;
  134.         case ZFIN:
  135.             ackbibi(); 
  136.             return ZCOMPL;
  137.         case ZCAN:
  138.             return NERROR;
  139.         }
  140.     }
  141.     return 0;
  142. }
  143.  
  144. /*
  145.  * Receive 1 or more files with ZMODEM protocol
  146.  */
  147.  
  148. rzmfile()
  149. {
  150.     static int c;
  151.  
  152.     for (;;) {
  153.         if (opabort())
  154.             return NERROR;
  155.         switch (c = rzfile()) {
  156.         case ZEOF:
  157.         case ZSKIP:
  158.             switch (tryz()) {
  159.             case ZCOMPL:
  160.                 return OK;
  161.             default:
  162.                 return NERROR;
  163.             case ZFILE:
  164.                 break;
  165.             }
  166.             continue;
  167.         default:
  168.             return c;
  169.         case NERROR:
  170.             return NERROR;
  171.         }
  172.     }
  173. }
  174.  
  175. /*
  176.  * Receive a file with ZMODEM protocol
  177.  *  Assumes file name frame is in Secbuf
  178.  */
  179. rzfile()
  180. {
  181.     static int c, n;
  182.     static unsigned bufleft;
  183.     static long rxbytes;
  184.  
  185.     Eofseen=FALSE;
  186.     if (procheader(Secbuf) == NERROR) {
  187.         return (Tryzhdrtype = ZSKIP);
  188.     }
  189.  
  190.     n = 20; 
  191.     rxbytes = 0L;
  192.     Firstsec = TRUE;
  193.  
  194.     for (;;) {
  195.         if (opabort())
  196.             return NERROR;
  197.         stohdr(rxbytes);
  198.         zshhdr(ZRPOS, Txhdr);
  199. nxthdr:
  200.         if (opabort())
  201.             return NERROR;
  202.         switch (c = zgethdr(Rxhdr, 0)) {
  203.  
  204.             default:
  205.                 return NERROR;
  206.  
  207.             case ZNAK:
  208.             case TIMEOUT:
  209.                 if ( --n < 0) {
  210.                     return NERROR;
  211.                 }
  212.  
  213.             case ZFILE:
  214.                 zrdata(Secbuf, KSIZE);
  215.                 continue;
  216.  
  217.             case ZEOF:
  218.                 if (rclhdr(Rxhdr) != rxbytes) {
  219.                 /*
  220.                  * Ignore eof if it's at wrong place - force
  221.                  *  a timeout because the eof might have gone
  222.                  *  out before we sent our zrpos.
  223.                  */
  224.                     Errors = 0;  
  225.                     goto nxthdr;
  226.                 }
  227.                 if (closeit()) {
  228.                     Tryzhdrtype = ZFERR;
  229.                     return NERROR;
  230.                 }
  231.                      lreport(KBYTES,rxbytes);
  232.                 crcrept(Crc32);
  233.                 return c;
  234.  
  235.             case NERROR:    /* Too much garbage in header search error */
  236.                 if ( --n < 0) {
  237.                     return NERROR;
  238.                 }
  239.                 zmputs(Attn);
  240.                 continue;
  241.  
  242.             case ZDATA:
  243.                 if (rclhdr(Rxhdr) != rxbytes) {
  244.                     if ( --n < 0) {
  245.                         return NERROR;
  246.                     }
  247.                     zmputs(Attn);  
  248.                     continue;
  249.                 }
  250. moredata:
  251.                 if (opabort())
  252.                     return NERROR;
  253.                 bufleft = Cpbufsize - Cpindex;
  254.                 c = zrdata(Rxptr,
  255.                      (bufleft > KSIZE) ? KSIZE : bufleft);
  256.             switch (c) {
  257.  
  258.             case ZCAN:
  259.                 return NERROR;
  260.  
  261.             case NERROR:    /* CRC error */
  262.                 statrep(rxbytes);
  263.                 if ( --n < 0) {
  264.                     return NERROR;
  265.                 }
  266.                 zmputs(Attn);
  267.                 continue;
  268.  
  269.             case TIMEOUT:
  270.                 statrep(rxbytes);
  271.                 if ( --n < 0) {
  272.                     return NERROR;
  273.                 }
  274.                 continue;
  275.  
  276.             case GOTCRCW:
  277.                 n = 20;
  278.                 if (putsec(Rxcount,TRUE) == NERROR)
  279.                     return NERROR; /* Write to disk! */
  280.                 rxbytes += Rxcount;
  281.                 stohdr(rxbytes);
  282.                 statrep(rxbytes);
  283.                 zshhdr(ZACK, Txhdr);
  284.                 mcharout(XON);
  285.                 goto nxthdr;
  286.  
  287.             case GOTCRCQ:
  288.                 n = 20;
  289.                 if (putsec(Rxcount,TRUE) == NERROR)
  290.                     return NERROR; /* Write to disk! */
  291.                 rxbytes += Rxcount;
  292.                 stohdr(rxbytes);
  293.                 zshhdr(ZACK, Txhdr);
  294.                 goto moredata;
  295.  
  296.             case GOTCRCG:
  297.                 n = 20;
  298.                 if (putsec(Rxcount,FALSE) == NERROR)
  299.                     return NERROR; /* Don't write to disk */
  300.                 rxbytes += Rxcount;
  301.                 goto moredata;
  302.  
  303.             case GOTCRCE:
  304.                 n = 20;
  305.                 if (putsec(Rxcount,FALSE) == NERROR)
  306.                     return NERROR; /* Don't write to disk */
  307.                 rxbytes += Rxcount;
  308.                 goto nxthdr;
  309.             }
  310.         }
  311.     }
  312. }
  313.  
  314. /* Status report: don't do unless after error or ZCRCW since characters */
  315. /*    will be lost unless rx has interrupt-driven I/O            */
  316. statrep(rxbytes)
  317. long rxbytes;
  318. {
  319.     lreport(KBYTES,rxbytes);
  320.     crcrept(Crc32);
  321. }
  322.  
  323. /* Report CRC mode in use, but only if first sector */
  324. crcrept(flag)
  325. int flag;
  326. {
  327.     if (Firstsec)
  328.         report(BLKCHECK, flag ? "CRC-32" : "CRC-16");
  329.     Firstsec = FALSE;    /* clear the flag */
  330. }
  331.  
  332. /* Add a block to the main buffer pointer and write to disk if full */
  333.         /* or if flag set */
  334. putsec(count,flag)
  335. int count, flag;
  336. {
  337.     short status;
  338.     unsigned size;
  339.  
  340.     status = 0;
  341.     Rxptr += count;
  342.     Cpindex += count;
  343.     if ((Cpindex >= Cpbufsize) || flag)
  344.     {
  345.         size = (Cpindex > Cpbufsize) ? Cpbufsize : Cpindex;
  346.  
  347. #ifdef AZTEC_C
  348.         status = fwrite(Cpmbuf,1,size,Fd);
  349.         if (status <= 0)
  350. #else
  351.         status = write(Fd,Cpmbuf,size);
  352.         if (status != size)
  353. #endif
  354.  
  355.         {
  356.             zperr("Disk write error",TRUE);
  357.             status = NERROR;
  358.         }
  359.         Cpindex = 0;
  360.         Rxptr = Cpmbuf;
  361.     }
  362.     return status;
  363. }
  364.  
  365. /*
  366.  * Send a string to the modem, processing for \336 (sleep 1 sec)
  367.  *   and \335 (break signal)
  368.  */
  369. zmputs(s)
  370. char *s;
  371. {
  372.     static int c;
  373.  
  374.     while (*s) {
  375.         if (opabort())
  376.             return NERROR;
  377.         switch (c = *s++) {
  378.         case '\336':
  379.             wait(1); 
  380.             continue;
  381.         case '\335':
  382.             sendbrk(); 
  383.             continue;
  384.         default:
  385.             mcharout(c);
  386.         }
  387.     }
  388. }
  389.  
  390. /* Test if file exists, rename to .BAK if so */
  391. testexist(filename)
  392. char *filename;
  393. {
  394.     int fd;
  395.     char *p, newfile[20], *index();
  396.  
  397.     if ((fd = open(filename,0)) != UBIOT) {
  398.         close(fd);
  399.         strcpy(newfile,filename);
  400.         if (p = index(newfile,'.'))
  401.             *p = '\0';    /* stop at dot */
  402.         strcat(newfile,".bak");
  403.         unlink(newfile);    /* remove any .bak already there */
  404.         rename(filename,newfile);
  405.     }
  406. }
  407.  
  408. /*
  409.  * Close the receive dataset, return OK or NERROR
  410.  */
  411. closeit()
  412. {  
  413.     static int status;
  414.     int length;
  415.  
  416.     status = OK;
  417.     if (Cpindex) {
  418.         length = 128*roundup(Cpindex,128);
  419.  
  420. #ifdef AZTEC_C
  421.         status = fwrite(Cpmbuf,length,1,Fd) ? OK : NERROR;
  422. #else
  423.         status = ((write(Fd,Cpmbuf,length) == length) ? OK : NERROR);
  424. #endif
  425.  
  426.         Cpindex = 0;
  427.         Rxptr = Cpmbuf;
  428.     }
  429.     if (status == NERROR)
  430.         zperr("Disk write error",TRUE);
  431.  
  432. #ifdef AZTEC_C
  433.     if (fclose(Fd)==NERROR) {
  434.         Fd = 0;
  435. #else
  436.     if (close(Fd)==NERROR) {
  437.         Fd = -1;
  438. #endif
  439.  
  440.         zperr("File close error",TRUE);
  441.         return NERROR;
  442.     }
  443.     return status;
  444. }
  445.  
  446. /*
  447.  * Ack a ZFIN packet, let byegones be byegones
  448.  */
  449.  
  450. ackbibi()
  451. {
  452.     static int n;
  453.  
  454.     stohdr(0L);
  455.     for (n=3; --n>=0; ) {
  456.         purgeline();
  457.         zshhdr(ZFIN, Txhdr);
  458.         switch (readline(100)) {
  459.         case 'O':
  460.             readline(INTRATIME);    /* Discard 2nd 'O' */
  461.             return;
  462.         case RCDO:
  463.             return;
  464.         case TIMEOUT:
  465.         default:
  466.             break;
  467.         }
  468.     }
  469. }
  470.    
  471. long
  472. atol(string)
  473. char *string;
  474. {
  475.     static long value, lv;
  476.     static char *p;
  477.    
  478.     value = 0L;
  479.     p = string + strlen(string);     /* end of string */
  480.     while (!isdigit(*p))
  481.         p--;
  482.     for (lv = 1L; isdigit(*p) && p >= string; lv *= 10)
  483.         value += ((*p--) - '0') * lv;
  484.     return value;
  485. }
  486.  
  487. rlabel() /*print receive mode labels on the 25th line*/
  488. {
  489.     putlabel("RECEIVE FILE Mode:  Press ESC to Abort...");
  490. }
  491.  
  492. /************************** END OF MODULE 5 *********************************/
  493.