wht@tridom.uucp (Warren Tucker) (10/11/89)
---- Cut Here and unpack ---- #!/bin/sh # this is part 26 of a multipart archive # do not concatenate these parts, unpack them in order with /bin/sh # file z/ecurz.c continued # CurArch=26 if test ! -r s2_seq_.tmp then echo "Please unpack part 1 first!" exit 1; fi ( read Scheck if test "$Scheck" != $CurArch then echo "Please unpack part $Scheck next!" exit 1; else exit 0; fi ) < s2_seq_.tmp || exit 1 echo "x - Continuing file z/ecurz.c" sed 's/^X//' << 'SHAR_EOF' >> z/ecurz.c X printf("can only be run by ecu\n"); X exit(255); X } X X if(log_packets) X { X char log_packets_name[64]; X FILE *ftmp; X int iargv; X sprintf(log_packets_name,"/tmp/rz%05d.plog",getpid()); X unlink(log_packets_name); X ftmp = fopen(log_packets_name,"w"); X fclose(ftmp); X log_packets = open(log_packets_name,O_WRONLY,0644); X if(log_packets < 0) X log_packets = 0; X else X { X write(log_packets,"exec: ",6); X for(iargv = 0; iargv < gargc; iargv++) X { X write(log_packets,gargv[iargv],strlen(gargv[iargv])); X write(log_packets," ",1); X } X write(log_packets,"\n",1); X } X } X X X if(Batch && npats) X usage("Cannot specify batch receive and filename"); X if(npats > 1) X usage("only one filename allowed"); X sprintf(s128,"%s",numeric_revision); X report_init(s128); X mode(1); X signal(SIGINT,cancel_transaction); X signal(SIGTERM,cancel_transaction); X signal(SIGQUIT,cancel_transaction); X if(wcreceive(npats,patts)==ERROR) X { X exitcode=0200; X send_cancel(); X } X mode(0); X if(exitcode && !Zmodem) /* bellow again with all thy might. */ X send_cancel(); X report_uninit(0); X exit(exitcode); X} X X/* vi: set tabstop=4 shiftwidth=4: */ X/* end of ecurz.c */ SHAR_EOF echo "File z/ecurz.c is complete" chmod 0644 z/ecurz.c || echo "restore of z/ecurz.c fails" echo "x - extracting z/ecusz.c (Text)" sed 's/^X//' << 'SHAR_EOF' > z/ecusz.c && X/* CHK=0x7F75 */ X#define VERSION "ecusz 2.21" Xchar *numeric_revision = VERSION; X#define BUFFERED_WRITE X/*+------------------------------------------------------------------------- X ecusz.c - X/Y/ZMODEM send program X Derived from public domain source by Chuck Foresberg, Omen Technologies X Adaptation for ecu Copyright 1989, Warren H. Tucker, III X X Usage: ecusz [-X -Y -Z] [-12+abdefkLlNnquvwy] [-] file ... X (Y) = Option applies to YMODEM only X (Z) = Option applies to ZMODEM only X a (ASCII) change NL to CR/LF X b Binary file transfer override X f send Full pathname (Y/Z) X k Send 1024 byte packets (Y) X L N Limit subpacket length to N bytes (Z) X l N Limit frame length to N bytes (l>=L) (Z) X n send file if source newer (Z) X N send file if source newer or longer (Z) X o Use 16 bit CRC instead of 32 bit CRC (Z) X p Protect existing destination file (Z) X r Resume/Recover interrupted file transfer (Z) X q Quiet (no progress reports) X u Unlink file after transmission X w N Window is N bytes (Z) X y Yes,overwrite existing file (Z) X @file reads a list of filenames from 'file' X X Defined functions: X SIGALRM_handler() X cancel_transaction(n) X determine_transaction_time() X flushline() X get_file_list_name(namep) X getinsync(flag) X getnak() X getzrxinit() X log_packet_buffer(buf,len) X main(argc,argv) X onintr() X purgeline() X readline(n) X readock(timeout,count) X report_rcvr_cancelled(place_happened) X report_rcvr_skipped() X report_send_stats(filepos) X report_send_transaction() X rewind_file_list() X saybibi() X send_cancel() X sendline(ch) X sendzsinit() X set_file_list(pathc,pathv) X substr(s,t) X usage() X wcputsec(buf,sectnum,cseclen) X wcs(oname) X wcsend() X wctx(flen) X wctxpn(name) X xbuf_build(buf,count) X xsendline(ch) X zbuf_build(buf,count) X zsendfdata() X zsendfile(buf,blen) X X--------------------------------------------------------------------------*/ X/*+:EDITS:*/ X/*:07-03-1989-22:58-wht------------- ecu 2.00 ---------------- */ X/*:06-26-1989-23:24-wht-exclude "!! " from error messages on screen */ X/*:06-24-1989-16:51-wht-flush edits --- ecu 1.95 */ X X/* X Error return conditions X 255: usage X 254: protocol failed (bad line conditions,brain dead remote) X 253: could not open any files X 128-192: process terminated with signal==code-128 (64 signals allowed for) X signal 0 == program logic error (see cancel_transaction call in rbsb.c) X 127: 127 or more files not transmitted (see ~/.eculog) X 1-126: count of files not transmitted (see ~/.eculog) X 0: file transfer completely successful X*/ X Xchar *substr(),*getenv(); X X#include <stdio.h> X#include <signal.h> X#include <setjmp.h> X#include <ctype.h> X#include <fcntl.h> X#include "zmodem.h" X#include "zlint.h" X Xextern char *sys_errlist[]; Xextern unsigned short crctab[]; /* wht */ Xextern unsigned long total_data_chars_xfered; /* zcurses.c */ Xextern int errno; Xextern int Rxtimeout; /* Tenths of seconds to wait for something */ Xextern char Rxhdr[4]; /* Received header */ Xextern char Txhdr[4]; /* Transmitted header */ Xextern int Txfcs32; /* TURE means send binary frames with 32 bit FCS */ Xextern long Rxpos; /* Received file position */ Xextern long Txpos; /* Transmitted file position */ Xextern char *frametypes[]; Xextern char Attn[]; /* Attention string rx sends to tx on err */ Xextern char s256[]; X X#define RETRYMAX 10 /* non-zmodem retry count on block send */ X#define VMIN_COUNT 2 /* must not exceed 255 */ Xunsigned char vmin_count = VMIN_COUNT; Xint iofd = 0; /* line io fd */ X#ifdef BUFFERED_WRITE XFILE *iofp; X#endif X X X/* X * Attention string to be executed by receiver to interrupt streaming data X * when an error is detected. A pause (0336) may be needed before the X * ^C (03) or after it. X */ X#if defined(READCHECK) Xchar Myattn[] = { 0 }; X#else X#if defined(M_XENIX) Xchar Myattn[] = { 03,0336,0 }; X#else Xchar Myattn[] = { 0 }; X#endif X#endif X XFILE *in; X Xchar *Cmdstr; /* Pointer to the command string */ Xchar *bottom_label = (char *)0; Xchar Crcflg; Xchar Lastrx; Xchar Lzconv; /* Local ZMODEM file conversion request */ Xchar Lzmanag; /* Local ZMODEM file management request */ Xchar Lztrans; Xchar Pathname[PATHLEN]; Xchar curr_dir[256]; Xchar s128[128]; Xchar txbuf[1024]; Xchar zconv; /* ZMODEM file conversion request */ Xchar zmanag; /* ZMODEM file management request */ Xchar ztrans; /* ZMODEM file transport request */ Xint Ascii=0; /* Add CR's for brain damaged programs */ Xint Cmdack1; /* Rx ACKs command,then do it */ Xint Cmdtries = 11; Xint Command = 0; /* Send a command,then exit. */ Xint Dontread; /* Don't read the buffer,it's still there */ Xint Dottoslash=0; /* Change foo.bar.baz to foo/bar/baz */ Xint Exitcode = 0; Xint Filcnt=0; /* count of number of files opened */ Xint FileRejectCount=0; /* number of files not sent */ Xint FilesTotal; Xint Filesleft; Xint Fullname=0; /* transmit full pathname */ Xint Lastn; /* Count of last buffer read or -1 */ Xint Lfseen=0; Xint Noeofseen; Xint Nozmodem = 0; Xint Optiong; /* no wait for block ACK's */ Xint Quiet=0; /* overrides logic that would otherwise set verbose */ Xint Rxflags = 0; Xint SameZrposAgain=0; /* How many times we've been ZRPOS'd same place (wht) */ Xint Tframlen = 0; /* Override for tx frame length */ Xint Totsecs; /* total number of blocks this file */ Xint Twostop = 0; /* use two stop bits */ Xint Unlinkafter=0; /* Unlink file after it is sent */ Xint Wantfcs32 = TRUE; /* want to send 32 bit FCS */ Xint Xmodem=0; /* XMODEM Protocol - don't send pathnames */ Xint Zctlesc; /* Encode control characters */ Xint Zmodem=0; /* ZMODEM protocol requested by receiver */ Xint Zrwindow = 1400; /* RX window size (controls garbage count) */ Xint blklen=128; /* length of transmitted records */ Xint blklen_original; Xint blkopt=0; /* Override value for zmodem blklen */ Xint ecusz_flag = 1; Xint errors; Xint firstsec; Xint log_packets = 0; Xint no_files = 0; Xint npats = 0; Xlong Lastread; /* Beginning offset of last buffer read */ Xlong Lastsync; /* Last offset to which we got a ZRPOS */ Xlong Lrxpos; /* Receiver's last reported offset */ Xlong TotalLeft; Xlong TotalToSend; Xlong bytcnt; Xlong rx_char_count = 0L; Xlong this_file_length; Xlong tx_char_count = 0L; Xunsigned Baudrate; Xunsigned Rxbuflen = 16384; /* Receiver's max buffer length */ Xunsigned Txwcnt; /* Counter used to space ack requests */ Xunsigned Txwindow; /* Control the size of the transmitted window */ Xunsigned Txwspac; /* Spacing between zcrcq requests */ Xunsigned int bad_condx_blklen = 0; /* if <>0,blklen has been reduced (wht) */ Xunsigned int bad_condx_frame_count = 0; /* frame # last SameZrposAgain (wht) */ Xunsigned int this_file_frame_count; /* count of frames sent this file (wht) */ X X#define MAX_PATHS 512 Xchar *paths[MAX_PATHS]; X Xjmp_buf tohere; /* For the interrupt on RX timeout */ Xjmp_buf intrjmp; /* For the interrupt on RX CAN */ X Xint file_list_pathc; Xint file_list_path_current; Xchar **file_list_pathv; Xint required_type = 0; XFILE *fpflst = (FILE *)0; X X/*+------------------------------------------------------------------------- X log_packet_buffer(buf,len) X--------------------------------------------------------------------------*/ Xvoid Xlog_packet_buffer(buf,len) Xregister unsigned char *buf; Xregister int len; X{ Xchar xbuf[32]; X X while(len--) X { X sprintf(xbuf,"%02x ",*buf++); X write(log_packets,xbuf,strlen(xbuf)); X } X write(log_packets,"\n",1); X X} /* end of log_packet_buffer */ X X/*+------------------------------------------------------------------------- X rewind_file_list() X--------------------------------------------------------------------------*/ Xvoid Xrewind_file_list() X{ X file_list_path_current = 0; X if(fpflst) X { X fclose(fpflst); X fpflst = (FILE *)0; X } X} /* end of rewind_file_list */ X X/*+------------------------------------------------------------------------- X set_file_list(pathc,pathv) X--------------------------------------------------------------------------*/ Xvoid Xset_file_list(pathc,pathv) Xint pathc; Xchar **pathv; X{ X X file_list_pathc = pathc; X file_list_pathv = pathv; X rewind_file_list(); X} /* end of set_file_list */ X X/*+------------------------------------------------------------------------- X get_file_list_name(namep) X--------------------------------------------------------------------------*/ Xget_file_list_name(namep) Xchar **namep; X{ Xregister char *cptr; Xstatic char name[256]; X Xtry_fpflst: X if(fpflst) X { X if(fgets(name,sizeof(name),fpflst) != NULL) X { X name[strlen(name) - 1] = 0; X *namep = name; X return(1); X } X fclose(fpflst); X fpflst = (FILE *)0; X } X Xnext_arg: X if(file_list_path_current == file_list_pathc) X return(0); X cptr = file_list_pathv[file_list_path_current++]; X if(*cptr != '@') X { X *namep = cptr; X return(1); X } X cptr++; X if((fpflst = fopen(cptr,"r")) == NULL) X goto next_arg; X goto try_fpflst; X X} /* end of get_file_list_name */ X X/*+------------------------------------------------------------------------- X bye_bye(sig) X--------------------------------------------------------------------------*/ Xvoid Xbye_bye(sig) Xint sig; X{ X exit(sig+128); X} /* end of bye_bye */ X X/*+------------------------------------------------------------------------- X cancel_transaction(n) Xcalled by signal interrupt or terminate to clean things up X--------------------------------------------------------------------------*/ Xvoid Xcancel_transaction(n) X{ X if(Zmodem) X zmputs(Attn); X send_cancel(); X mode(0); X if(n >= 0) X { X sprintf(s128,"ecusz received signal %d: exiting",n); X report_str(s128,0); X } X report_tx_ind(0); X report_rx_ind(0); X report_uninit(0); X bye_bye(n); X} /* end of cancel_transaction */ X X/* Called when ZMODEM gets an interrupt (^X) */ Xonintr() X{ X signal(SIGINT,SIG_IGN); X#if defined(M_XENIX) X report_rx_ind(0); X report_tx_ind(0); X#endif X longjmp(intrjmp,-1); X} X X X/*+------------------------------------------------------------------------- X report_send_transaction() X--------------------------------------------------------------------------*/ Xvoid Xreport_send_transaction() X{ X if(Xmodem) X { X long blocks = (TotalToSend >> 7) + ((TotalToSend % 128) != 0); X long secs = 7 /* slightly worse than average first nak delay */ X + (blocks / 5L) /* assume .2 sec ack time */ X + ((blocks * (128L + 16L)) / (Baudrate / 10)); X if(!secs) X secs = 10L; X sprintf(s128,"Sending %ld blocks time ~= %ld:%02ld", X blocks,secs/60,secs % 60); X } X else X { X long min_100 = X (FilesTotal * 2L) + (((TotalToSend * 11L)) * 10L) / (Baudrate * 6L); X if(!min_100) X min_100 = 4L; X#if defined(M_I286) /* slower */ X else if(Baudrate > 4800) X { X min_100 *= 13; X min_100 /= 9; /* yech ... empirical */ X } X#endif X sprintf(s128,"Sending %ld bytes total time ~= %2lu:%02lu", X TotalToSend,min_100 / 100,((min_100 % 100) * 60L) / 100L); X } X report_transaction(s128); X X} /* end of report_send_transaction */ X X/*+------------------------------------------------------------------------- X report_send_stats(filepos) X--------------------------------------------------------------------------*/ Xvoid Xreport_send_stats(filepos) Xlong filepos; X{ X X if(Xmodem) X sprintf(s128,"File %d%% complete", X (this_file_length == 0) ? (int)100 : X (int)((filepos * 100L) / this_file_length)); X else X sprintf(s128,"This file %d%%, transaction %d%% complete", X (this_file_length == 0) ? (int)100 : X (int)((filepos * 100L)/this_file_length), X (TotalToSend == 0) ? (int)100 : X (int)(((total_data_chars_xfered + filepos) * 100L) X / TotalToSend)); X report_str(s128,0); X report_txpos(filepos); X X} /* end of report_send_stats */ X X/*+------------------------------------------------------------------------- X report_rcvr_cancelled(place_happened) X--------------------------------------------------------------------------*/ Xvoid Xreport_rcvr_cancelled(place_happened) Xchar *place_happened; X{ X strcpy(s128,"SEND CANCELLED"); X report_str(s128 + 5,1); X#ifdef LOG_XFER X strcat(s128," ("); X strcat(s128,place_happened); X strcat(s128,")"); X ecu_log_event(s128); X#endif X if(FileRejectCount < 127) X FileRejectCount++; X} /* end of report_rcvr_cancelled */ X X/*+------------------------------------------------------------------------- X report_rcvr_skipped() X--------------------------------------------------------------------------*/ Xvoid Xreport_rcvr_skipped() X{ X sprintf(s128,"SEND skipped: %s",Pathname); X report_str(s128 + 5,-1); X#ifdef LOG_XFER X ecu_log_event(s128); X#endif X if(FileRejectCount < 127) X FileRejectCount++; X TotalToSend -= this_file_length; X report_send_transaction(); X} /* end of report_rcvr_skipped */ X X X/*+------------------------------------------------------------------------- X xsendline(ch) X--------------------------------------------------------------------------*/ Xxsendline(ch) Xchar ch; X{ X#ifdef BUFFERED_WRITE X fputc(ch,iofp); X#else X write(iofd,&ch,1); X#endif X ++tx_char_count; X} /* end of xsendline */ X X/*+------------------------------------------------------------------------- X sendline(ch) X--------------------------------------------------------------------------*/ Xsendline(ch) Xchar ch; X{ X xsendline(ch); X} /* end of sendline */ X Xflushline() X{ X#ifdef BUFFERED_WRITE X fflush(iofp); X#endif X} X Xmain(argc,argv) Xchar *argv[]; X{ Xregister char *cp; Xlong min_100; Xchar **patts = paths; Xchar **gargv = argv; Xint gargc = argc; X X signal(SIGINT,bye_bye); X signal(SIGTERM,bye_bye); X X get_curr_dir(curr_dir,sizeof(curr_dir)); X X Rxtimeout = 600; X npats=0; X if(argc<2) X usage(); X while(--argc) X { X cp = *++argv; X if(*cp == '-') X { X cp++; X switch(*cp++) X { X case 'X': X required_type = 1; X Xmodem = TRUE; X break; X case 'Y': X required_type = 1; X Nozmodem = TRUE; X blklen=1024; X break; X case 'Z': X required_type = 1; X break; X X case '+': X Lzmanag = ZMAPND; X break; X case 'a': X Lzconv = ZCNL; X Ascii = TRUE; X break; X case 'b': X Lzconv = ZCBIN; X break; X case 'd': X ++Dottoslash; X /* **** FALL THROUGH TO **** */ X case 'f': X Fullname=TRUE; X break; X case ',': X log_packets = 1; X break; X case '/': X if(--argc < 1) X usage(); X strcpy(curr_dir,*++argv); X break; X case '.': X if(--argc < 1) X usage(); X iofd = atoi(*++argv); X break; X case 'C': X if(--argc < 1) X usage("no label after -C"); X bottom_label = *++argv; X break; X case 'e': X Zctlesc = 1; X break; X case 'k': X blklen=1024; X break; X case 'L': X if(--argc < 1) X { X usage(); X } X blkopt = atoi(*++argv); X if(blkopt<24 || blkopt>1024) X usage(); X break; X case 'l': X if(--argc < 1) X { X usage(); X } X Tframlen = atoi(*++argv); X if(Tframlen<32 || Tframlen>1024) X usage(); X break; X case 'N': X Lzmanag = ZMNEWL; X break; X case 'n': X Lzmanag = ZMNEW; X break; X case 'o': X Wantfcs32 = FALSE; X break; X case 'p': X Lzmanag = ZMPROT; X break; X case 'r': X Lzconv = ZCRESUM; X case 't': X if(--argc < 1) X { X usage(); X } X Rxtimeout = atoi(*++argv); X if(Rxtimeout<10 || Rxtimeout>1000) X usage(); X break; X case 'u': X ++Unlinkafter; X break; X case 'w': X if(--argc < 1) X { X usage(); X } X Txwindow = atoi(*++argv); X if(Txwindow < 256) X Txwindow = 256; X Txwindow = (Txwindow/64) * 64; X Txwspac = Txwindow/4; X if(blkopt > Txwspac || (!blkopt && Txwspac < 1024)) X blkopt = Txwspac; X break; X case 'y': X Lzmanag = ZMCLOB; X break; X default: X usage(); X } X } X else if(argc > 0) X { X if(npats < MAX_PATHS) X { X npats++; X *patts++ = cp; X } X else X { X printf("too many filenames to send\n"); X exit(255); X } X } X } X if(!required_type || !iofd) X { X printf("can only be run by ecu\n"); X exit(255); X } X X if(npats < 1 && !Command) X usage(); X X set_file_list(npats,paths); X sprintf(s128,"%s",numeric_revision); X report_init(s128); X mode(1); X X if(log_packets) X { X char log_packets_name[64]; X FILE *ftmp; X int iargv; X sprintf(log_packets_name,"/tmp/sz%05d.plog",getpid()); X unlink(log_packets_name); X ftmp = fopen(log_packets_name,"w"); X fclose(ftmp); X log_packets = open(log_packets_name,O_WRONLY,0644); X if(log_packets < 0) X log_packets = 0; X else X { X write(log_packets,"exec: ",6); X for(iargv = 0; iargv < gargc; iargv++) X { X write(log_packets,gargv[iargv],strlen(gargv[iargv])); X write(log_packets," ",1); X } X write(log_packets,"\n",1); X } X } X X if(signal(SIGINT,cancel_transaction) == SIG_IGN) X signal(SIGINT,SIG_IGN); X else X signal(SIGINT,cancel_transaction); X signal(SIGTERM,cancel_transaction); X X report_str("calculating transaction time",-1); X determine_transaction_time(); X#ifdef BUFFERED_WRITE X iofp = fdopen(iofd,"w"); X#endif X if(!Xmodem) X { X TotalToSend = TotalLeft; X report_send_transaction(); X report_str("starting remote receiver",-1); X if(!Nozmodem) X write(iofd,"rz\r",3); X else /* wht -- why not? */ X write(iofd,"rb\r",3); /* wht */ X nap(1500L); X report_str("beginning transfer",-1); X if(!Nozmodem) X { X stohdr(0L); X zshhdr(ZRQINIT,Txhdr); X } X } X else X report_str("beginning transfer",-1); X X if(wcsend()==ERROR) X { X Exitcode=254; /*wht was 0200 */ X send_cancel(); X } X mode(0); X report_uninit(0); X if(no_files) X Exitcode = 253; X exit(Exitcode ? Exitcode : FileRejectCount); X /*NOTREACHED*/ X} X X/*+------------------------------------------------------------------------- X wcsend(argc,argp) -- send group of files X--------------------------------------------------------------------------*/ Xwcsend() X{ X register n; X char *name; X X Crcflg=FALSE; X firstsec=TRUE; X bytcnt = -1; X rewind_file_list(); X while(get_file_list_name(&name)) X { X Totsecs = 0; X if(wcs(name)==ERROR) X return(ERROR); X } X Totsecs = 0; X if(Filcnt==0) X { /* bitch if we couldn't open ANY files */ X send_cancel(); X strcpy(s128,"SEND cannot open any requested files"); X report_str(s128 + 5,1); X#ifdef LOG_XFER X ecu_log_event(s128); X#endif X sleep(2); /* allow time for other rz to get ready */ X no_files = 1; X return(ERROR); /* ... then cancel */ X } X if(Zmodem) X saybibi(); X else if(!Xmodem) X wctxpn(""); X return(OK); X} X X/*+------------------------------------------------------------------------- X wcs(oname) -- send a file X--------------------------------------------------------------------------*/ Xwcs(oname) Xchar *oname; X{ Xregister c; Xregister char *p; Xstruct stat f; X X strcpy(Pathname,oname); /* global copy of name */ X X if((in=fopen(oname,"r"))==NULL) X { X sprintf(s128,"SEND %s: %s",sys_errlist[errno],oname); X#ifdef LOG_XFER X ecu_log_event(s128); X#endif X report_str(s128 + 5,1); X if(FileRejectCount < 127) X ++FileRejectCount; X return(OK); /* pass over it,there may be others */ X } X ++Noeofseen; X Lastread = 0; X Lastn = -1; X Dontread = FALSE; X /* Check for directory or block special files */ X fstat(fileno(in),&f); X c = f.st_mode & S_IFMT; X if(c == S_IFDIR || c == S_IFBLK) X { X sprintf(s128,"SEND %s: %s", X (c == S_IFDIR) ? "directory" : "block device",oname); X report_str(s128 + 5,1); X#ifdef LOG_XFER X ecu_log_event(s128); X#endif X if(FileRejectCount < 127) X ++FileRejectCount; X fclose(in); X return(OK); X } X f.st_mode &= ~(S_ISUID | S_ISGID); X Filcnt++; X report_file_send_open(oname,&f); X this_file_length = f.st_size; X report_send_stats(0L); X switch(wctxpn(Pathname)) X { X case ERROR: X sprintf(s128,"SEND protocol failure: %s",oname); X report_str(s128 + 5,1); X#ifdef LOG_XFER X ecu_log_event(s128); X#endif X if(FileRejectCount < 127) X ++FileRejectCount; X report_file_close(); X fclose(in); X return(ERROR); X case ZSKIP: X report_rcvr_skipped(); X return(OK); X } X if(!Zmodem && wctx(f.st_size)==ERROR) X return(ERROR); X if(Unlinkafter) X unlink(oname); X return(0); X} X X/* X * generate and transmit pathname block consisting of X * pathname (null terminated), X * file length,mode time and file mode in octal X * as provided by the Unix fstat call. X * N.B.: modifies the passed name,may extend it! X */ Xwctxpn(name) Xchar *name; X{ X register char *p,*q; X char name2[PATHLEN]; X struct stat f; X X if(Xmodem) X { X if((in!=stdin) && *name && fstat(fileno(in),&f)!= -1) X { X TotalToSend = f.st_size; X report_protocol_type("XMODEM"); X report_send_transaction(); X report_xfer_mode((Ascii) ? "ASCII" : "BINARY"); X report_last_txhdr("Waiting on NAK",0); X } X return(OK); X } X if(!Zmodem) X { X report_last_txhdr("START PENDING",0); X if(getnak()) X { X report_str("Timeout on pathname nak",1); X return(ERROR); X } X } X X q = (char *) 0; X if(Dottoslash) X { /* change . to . */ X for(p=name; *p; ++p) X { X if(*p == '/') X q = p; X else if(*p == '.') X *(q=p) = '/'; X } X if(q && strlen(++q) > 8) X { /* If name>8 chars */ X q += 8; /* make it .ext */ X strcpy(name2,q); /* save excess of name */ X *q = '.'; X strcpy(++q,name2); /* add it back */ X } X } X X for(p=name,q=txbuf ; *p; ) X if((*q++ = *p++) == '/' && !Fullname) X q = txbuf; X *q++ = 0; X p=q; X while(q < (txbuf + 1024)) X *q++ = 0; X if(!Ascii && (in != stdin) && *name && !fstat(fileno(in),&f)) X sprintf(p,"%lu %lo %o 0 %d %ld",f.st_size,f.st_mtime, X f.st_mode &= ~(S_ISUID | S_ISGID), X Filesleft,TotalLeft); X report_xfer_mode((Lzconv == ZCNL) ? "ASCII" : "BINARY"); X TotalLeft -= f.st_size; X if(--Filesleft <= 0) X TotalLeft = 0; X if(TotalLeft < 0) X TotalLeft = 0; X X /* force 1k blocks if name won't fit in 128 byte block */ X if(txbuf[125]) X blklen=1024; X else X { /* A little goodie for IMP/KMD */ X txbuf[127] = (f.st_size + 127) >>7; X txbuf[126] = (f.st_size + 127) >>15; X } X if(Zmodem) X return(zsendfile(txbuf,1+strlen(p)+(p-txbuf))); X report_protocol_type("YMODEM"); X if(wcputsec(txbuf,0,128)==ERROR) X return(ERROR); X return(OK); X} X Xgetnak() X{ X register firstch; X X Lastrx = 0; X for(;;) X { X switch(firstch = readock(50,1)) /* 50 was 800 (80 secs!!) wht */ X { X case ZPAD: X if(getzrxinit()) X return(ERROR); X Ascii = 0; /* Receiver does the conversion */ X return(FALSE); X case TIMEOUT: X report_str("Timeout",1); X return(TRUE); X case WANTG: X#if defined(MODE2OK) X mode(2); /* Set cbreak,XON/XOFF,etc. */ X#endif X Optiong = TRUE; X blklen=1024; X case WANTCRC: X Crcflg = TRUE; X case NAK: X return(FALSE); X case CAN: X if((firstch = readock(20,1)) == CAN && Lastrx == CAN) X return(TRUE); X default: X break; X } X Lastrx = firstch; X } X} X X/*+------------------------------------------------------------------------- X wctx(flen) X--------------------------------------------------------------------------*/ Xwctx(flen) Xlong flen; X{ Xregister int thisblklen; Xregister int firstch; Xregister int sectnum; Xregister int attempts; Xlong charssent; X X charssent = 0; X firstsec=TRUE; X thisblklen = blklen; X report_txblklen(blklen); X X attempts = 8; X while(((firstch = readock(Rxtimeout,2)) != NAK) && X (firstch != WANTCRC) && (firstch != WANTG) && X (firstch != TIMEOUT) && (firstch != CAN)) X { X if(!--attempts) X { X report_str("bad start stimulus",1); X send_cancel(); X return(ERROR); X } X } X X if(firstch==CAN) X { X report_str("receiver CAN",1); X return(ERROR); X } X X if((firstch==WANTCRC) || (firstch==WANTG)) X Crcflg=TRUE; X X report_protocol_crc_type((Crcflg) X ? ((firstch== WANTG) ? "/CRC-g" : "/CRC") X : "/CHK"); X X sectnum=0; X for(;;) X { X if(flen <= (charssent + 896L)) X { X thisblklen = 128; X report_txblklen(thisblklen); X } X if(!xbuf_build(txbuf,thisblklen)) X break; X if(wcputsec(txbuf,++sectnum,thisblklen)==ERROR) X return(ERROR); X charssent += thisblklen; X } X X /* file transfer completed */ X report_file_byte_io(this_file_length); X report_file_close(); X fclose(in); X X#if defined(LOG_XFER) X sprintf(s256,"SEND success: %s",Pathname); X ecu_log_event(s256); X#endif X X attempts=0; X do X { X purgeline(); X sendline(EOT); X flushline(); X report_last_txhdr("EOT",0); X ++attempts; X } while((firstch=(readock(Rxtimeout,1)) != ACK) && attempts < RETRYMAX); X if(attempts == RETRYMAX) X { X report_str("No ACK on EOT",1); X return(ERROR); X } X else X return(OK); X} X Xwcputsec(buf,sectnum,cseclen) Xchar *buf; Xint sectnum; Xint cseclen; /* data length of this block to send */ X{ X register int checksum; X register int wcj; X register unsigned char *cp; X unsigned short oldcrc; X int firstch; X int attempts; X X firstch=0; /* part of logic to detect CAN CAN */ X X sprintf(s128,"Sending block %d",sectnum); X report_last_txhdr(s128,0); X if(log_packets) X { X log_packet_buffer(buf,cseclen); X } X X for(attempts=0; attempts <= RETRYMAX; attempts++) X { X Lastrx= firstch; X sendline(cseclen == 1024 ? STX : SOH); X sendline(sectnum); X sendline(-sectnum - 1); X oldcrc=checksum=0; X X for(wcj = cseclen,cp = buf; --wcj >= 0; ) X { X sendline(*cp); X oldcrc=updcrc(*cp,oldcrc); X checksum += *cp++; X } X if(Crcflg) X { X oldcrc=updcrc(0,updcrc(0,oldcrc)); X sendline((int)(oldcrc >> 8)); X sendline((int)(oldcrc & 0xFF)); X } X else X sendline(checksum); X flushline(); X X if(Optiong) X { X firstsec = FALSE; X return(OK); X } X firstch = readock(Rxtimeout,(Noeofseen&§num) ? 2:1); Xgotnak: X switch(firstch) X { X case CAN: X if(Lastrx == CAN) X { Xcancan: X report_last_rxhdr("CAN",1); X return(ERROR); X } X break; X case TIMEOUT: X report_last_rxhdr("Timeout",1); X continue; X case WANTCRC: X if(firstsec) X Crcflg = TRUE; X case NAK: X report_last_rxhdr("NAK",1); X continue; X case ACK: X report_last_rxhdr("ACK",0); X firstsec=FALSE; X Totsecs += (cseclen>>7); X return(OK); X case ERROR: X report_last_rxhdr("Noise",0); X break; X default: X sprintf(s128,"0x%02x ???",firstch); X report_last_rxhdr(s128,1); X break; X } X for(;;) X { X Lastrx = firstch; X if((firstch = readock(Rxtimeout,2)) == TIMEOUT) X break; X if(firstch == NAK || firstch == WANTCRC) X goto gotnak; X if(firstch == CAN && Lastrx == CAN) X goto cancan; X } X } X report_str("retry count exceeded",1); X return(ERROR); SHAR_EOF echo "End of part 26" echo "File z/ecusz.c is continued in part 27" echo "27" > s2_seq_.tmp exit 0 -- ------------------------------------------------------------------- Warren Tucker, Tridom Corporation ...!gatech!emory!tridom!wht Ker-au'-lo-phon. An 8-foot partial flue-stop, having metal pipes surmounted by adjustable rings, and with a hole bored near the top of each pipe, producing a soft and "reedy" tone.