#! /bin/sh # This is a shell archive. Remove anything before this line, then unpack # it by saving it into a file and typing "sh file". To overwrite existing # files, type "sh file -c". You can also feed this as standard input via # unshar, or by typing "sh 'sz.c' <<'END_OF_FILE' X#define VERSION "sz 3.03 5-09-89" X#define PUBDIR "/usr/spool/uucppublic" X X/*% cc -compat -M2 -Ox -K -i -DTXBSIZE=16384 -DNFGVMIN -DREADCHECK sz.c -lx -o sz; size sz X X/*% cc -Zi -DXX -DNFGVMIN -DREADCHECK sz.c -lx -o xsz; size xsz X<-xtx-*> cc -Osal -DTXBSIZE=32768 -DSV sz.c -lx -o $B/sz; size $B/sz X X **************************************************************************** X * X * sz.c By Chuck Forsberg, Omen Technology INC X * X **************************************************************************** X * X * Typical Unix/Xenix/Clone compiles: X * X * cc -O sz.c -o sz USG (SYS III/V) Unix X * cc -O -DSV sz.c -o sz Sys V Release 2 with non-blocking input X * Define to allow reverse channel checking X * cc -O -DV7 sz.c -o sz Unix Version 7, 2.8 - 4.3 BSD X * X * cc -O -K -i -DNFGVMIN -DREADCHECK sz.c -lx -o sz Classic Xenix X * X * ln sz sb **** All versions **** X * ln sz sx **** All versions **** X * X **************************************************************************** X * X * Typical VMS compile and install sequence: X * X * define LNK$LIBRARY SYS$LIBRARY:VAXCRTL.OLB X * cc sz.c X * cc vvmodem.c X * link sz,vvmodem X * sz :== $disk$user2:[username.subdir]sz.exe X * X * If you feel adventureous, remove the #define BADSEEK line X * immediately following the #ifdef vax11c line! Some VMS X * systems know how to fseek, some don't. X * X **************************************************************************** X * X * X * A program for Unix to send files and commands to computers running X * Professional-YAM, PowerCom, YAM, IMP, or programs supporting Y/XMODEM. X * X * Sz uses buffered I/O to greatly reduce CPU time compared to UMODEM. X * X * USG UNIX (3.0) ioctl conventions courtesy Jeff Martin X * X * This version implements ZMODEM Run Length Encoding, Comparision, X * and variable length headers. These features were not funded X * by the original Telenet development contract. This software, X * including these features, may be freely used for non X * commercial and educational purposes. This software may also X * be freely used to support file transfer operations to or from X * licensed Omen Technology products. Contact Omen Technology X * for licensing for other uses. Any programs which use part or X * all of this software must be provided in source form with this X * notice intact except by written permission from Omen X * Technology Incorporated. X * X * Omen Technology Inc FAX: 503-621-3745 X * Post Office Box 4681 X * Portland OR 97208 X * X * Previous versions of this program (not containing the extensions X * listed above) remain in the public domain. X * X * This code is made available in the hope it will be useful, X * BUT WITHOUT ANY WARRANTY OF ANY KIND OR LIABILITY FOR ANY X * DAMAGES OF ANY KIND. X * X * 2.1x hacks to avoid VMS fseek() bogosity, allow input from pipe X * -DBADSEEK -DTXBSIZE=32768 X * 2.x has mods for VMS flavor X * X * 1.34 implements tx backchannel garbage count and ZCRCW after ZRPOS X * in accordance with the 7-31-87 ZMODEM Protocol Description X */ X X#ifdef XX X#define XARGSFILE "args" Xlong Thisflen; X#endif X Xchar *substr(), *getenv(); X X#ifdef vax11c X#define STATIC X#define BADSEEK X#define TXBSIZE 32768 /* Must be power of two, < MAXINT */ X#include X#include X#define STAT X#define LOGFILE "szlog.tmp" X#include X#include X#include X#include X#include X#define OS "VMS" X#define ROPMODE "r" X#define READCHECK X#define BUFWRITE Xextern int errno; X#define SS_NORMAL SS$_NORMAL X#define xsendline(c) sendline(c) X X#ifndef PROGNAME X#define PROGNAME "sz" X#endif X X X#else /* vax11c */ X X#ifdef GENIE X#define STATIC static X#define LOGFILE "szlog" X#define BADSEEK X#define TXBSIZE 32768 /* Must be power of two, < MAXINT */ X#define OS "GEnie" X#define SS_NORMAL 0 X#include X#include X#include X#include X#include X#include X#include XFILDES fdes; Xextern int errno; Xint Binfile; Xlong Thisflen; X X#define sendline(c) putchar(c & 0377) X#define xsendline(c) putchar(c) X X#else /* GENIE */ X X#define LOGFILE "/tmp/szlog" X#define SS_NORMAL 0 X#include X#include X#include X#include X#include Xextern int errno; X#define STATIC X X#define sendline(c) putchar(c & 0377) X#define xsendline(c) putchar(c) X X#endif X#endif X X#define PATHLEN 256 X#define OK 0 X#define FALSE 0 X#ifdef TRUE X#undef TRUE X#endif X#define TRUE 1 X#define ERROR (-1) X/* Ward Christensen / CP/M parameters - Don't change these! */ X#define ENQ 005 X#define CAN ('X'&037) X#define XOFF ('s'&037) X#define XON ('q'&037) X#define SOH 1 X#define STX 2 X#define EOT 4 X#define ACK 6 X#define NAK 025 X#define CPMEOF 032 X#define WANTCRC 0103 /* send C not NAK to get crc not checksum */ X#define WANTG 0107 /* Send G not NAK to get nonstop batch xmsn */ X#define TIMEOUT (-2) X#define RCDO (-3) X#define GCOUNT (-4) X#define RETRYMAX 10 X X X#define HOWMANY 2 XSTATIC int Zmodem=0; /* ZMODEM protocol requested by receiver */ Xunsigned Baudrate=4800; /* Default, set by first mode() call */ XSTATIC unsigned Effbaud = 4800; XSTATIC unsigned Txwindow; /* Control the size of the transmitted window */ XSTATIC unsigned Txwspac; /* Spacing between zcrcq requests */ XSTATIC unsigned Txwcnt; /* Counter used to space ack requests */ XSTATIC long Lrxpos; /* Receiver's last reported offset */ XSTATIC int errors; X X#ifdef vax11c X#include "vrzsz.c" /* most of the system dependent stuff here */ X#else X#ifdef GENIE X#include "genie.c" /* most of the system dependent stuff here */ X#else X#include "rbsb.c" /* most of the system dependent stuff here */ X#ifdef XX X#undef STAT X#endif X#endif X#endif X X#include "crctab.c" X XSTATIC int Filesleft; XSTATIC long Totalleft; 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#ifdef READCHECK XSTATIC char Myattn[] = { 0 }; X#else X#ifdef USG XSTATIC char Myattn[] = { 03, 0336, 0 }; X#else X#ifndef GENIE XSTATIC char Myattn[] = { 0 }; X#endif X#endif X#endif X XFILE *in; X X#ifdef BADSEEK XSTATIC int Canseek = 0; /* 1: Can seek 0: only rewind -1: neither (pipe) */ X#ifndef TXBSIZE X#define TXBSIZE 16384 /* Must be power of two, < MAXINT */ X#endif X#else XSTATIC int Canseek = 1; /* 1: Can seek 0: only rewind -1: neither (pipe) */ X#endif X X#ifdef TXBSIZE X#define TXBMASK (TXBSIZE-1) XSTATIC char Txb[TXBSIZE]; /* Circular buffer for file reads */ XSTATIC char *txbuf = Txb; /* Pointer to current file segment */ X#else XSTATIC char txbuf[1024]; X#endif XSTATIC long vpos = 0; /* Number of bytes read from file */ X XSTATIC char Lastrx; XSTATIC char Crcflg; XSTATIC int Verbose=0; XSTATIC int Modem2=0; /* XMODEM Protocol - don't send pathnames */ XSTATIC int Restricted=0; /* restricted; no /.. or ../ in filenames */ XSTATIC int Quiet=0; /* overrides logic that would otherwise set verbose */ XSTATIC int Ascii=0; /* Add CR's for brain damaged programs */ XSTATIC int Fullname=0; /* transmit full pathname */ XSTATIC int Unlinkafter=0; /* Unlink file after it is sent */ XSTATIC int Dottoslash=0; /* Change foo.bar.baz to foo/bar/baz */ XSTATIC int firstsec; XSTATIC int errcnt=0; /* number of files unreadable */ XSTATIC int blklen=128; /* length of transmitted records */ XSTATIC int Optiong; /* Let it rip no wait for sector ACK's */ XSTATIC int Eofseen; /* EOF seen on input set by zfilbuf */ XSTATIC int BEofseen; /* EOF seen on input set by fooseek */ XSTATIC int Totsecs; /* total number of sectors this file */ XSTATIC int Filcnt=0; /* count of number of files opened */ XSTATIC int Lfseen=0; XSTATIC unsigned Rxbuflen = 16384; /* Receiver's max buffer length */ XSTATIC int Tframlen = 0; /* Override for tx frame length */ XSTATIC int blkopt=0; /* Override value for zmodem blklen */ XSTATIC int Rxflags = 0; XSTATIC long bytcnt; XSTATIC int Wantfcs32 = TRUE; /* want to send 32 bit FCS */ XSTATIC char Lzconv; /* Local ZMODEM file conversion request */ XSTATIC char Lzmanag; /* Local ZMODEM file management request */ XSTATIC int Lskipnocor; XSTATIC char Lztrans; XSTATIC int Command; /* Send a command, then exit. */ XSTATIC char *Cmdstr; /* Pointer to the command string */ XSTATIC int Cmdtries = 11; XSTATIC int Cmdack1; /* Rx ACKs command, then do it */ XSTATIC int Exitcode; XSTATIC int Test; /* 1= Force receiver to send Attn, etc with qbf. */ X /* 2= Character transparency test */ XSTATIC char *qbf= X "The quick brown fox jumped over the lazy dog's back 1234567890\r\n"; XSTATIC long Lastsync; /* Last offset to which we got a ZRPOS */ XSTATIC int Beenhereb4; /* How many times we've been ZRPOS'd same place */ X XSTATIC jmp_buf tohere; /* For the interrupt on RX timeout */ XSTATIC jmp_buf intrjmp; /* For the interrupt on RX CAN */ X X#ifdef XARGSFILE Xchar * Xmystrsave(s) Xchar *s; X{ X register char *p; X char *malloc(); X X if (p = malloc(strlen(s)+1) ) { X strcpy(p, s); return p; X } X fprintf(stderr, "No memory for mystrsave!\n"); X exit(1); X} X X/* Remove (presumably) terminating CR and/or LF from string */ Xuncrlf(s) Xregister char *s; X{ X for ( ; *s; ++s) X switch (*s) { X case '\r': X case '\n': X *s = 0; return; X } X} X#endif X X X/* called by signal interrupt or terminate to clean things up */ Xbibi(n) X{ X canit(); fflush(stdout); mode(0); X fprintf(stderr, "sz: caught signal %d; exiting\n", n); X#ifndef GENIE X if (n == SIGQUIT) X abort(); X#endif X if (n == 99) X fprintf(stderr, "mode(2) in rbsb.c not implemented!!\n"); X cucheck(); X exit(128+n); X} X/* Called when ZMODEM gets an interrupt (^X) */ Xonintr() X{ X signal(SIGINT, SIG_IGN); X longjmp(intrjmp, -1); X} X XSTATIC int Zctlesc; /* Encode control characters */ XSTATIC int Nozmodem = 0; /* If invoked as "sb" */ XSTATIC char *Progname = "sz"; XSTATIC int Zrwindow = 1400; /* RX window size (controls garbage count) */ X#include "zm.c" X X#include "zmr.c" X X#ifdef XARGSFILE X#define XARGSMAX 256 Xchar *xargv[XARGSMAX+1]; X#endif X Xmain(argc, argv) Xchar *argv[]; X{ X register char *cp; X register npats; X int dm; X char **patts; X static char xXbuf[BUFSIZ]; X X if ((cp = getenv("ZNULLS")) && *cp) X Znulls = atoi(cp); X if ((cp=getenv("SHELL")) && (substr(cp, "rsh") || substr(cp, "rksh"))) X Restricted=TRUE; X from_cu(); X#ifdef vax11c X chkinvok(PROGNAME); X#else X chkinvok(argv[0]); X#endif X X Rxtimeout = 600; X npats=0; X if (argc<2) X usage(); X setbuf(stdout, xXbuf); X while (--argc) { X cp = *++argv; X if (*cp++ == '-' && *cp) { X while ( *cp) { X switch(*cp++) { X case '\\': X *cp = toupper(*cp); continue; X case '+': X Lzmanag = ZMAPND; break; X#ifdef CSTOPB X case '2': X Twostop = TRUE; break; X#endif X case 'a': X Lzconv = ZCNL; X Ascii = TRUE; break; X case 'b': X Lzconv = ZCBIN; break; X case 'C': X if (--argc < 1) { X usage(); X } X Cmdtries = atoi(*++argv); X break; X case 'i': X Cmdack1 = ZCACK1; X /* **** FALL THROUGH TO **** */ X case 'c': X if (--argc != 1) { X usage(); X } X Command = TRUE; X Cmdstr = *++argv; X break; X case 'd': X ++Dottoslash; X /* **** FALL THROUGH TO **** */ X case 'f': X Fullname=TRUE; break; X case 'e': X Zctlesc = 1; break; X case 'k': X blklen=1024; break; X case 'L': X if (--argc < 1) { 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 usage(); X } X Tframlen = atoi(*++argv); X if (Tframlen<32 || Tframlen>1024) X usage(); X break; X case 'N': X Lzmanag = ZMNEWL; break; X case 'n': X Lzmanag = ZMNEW; break; X case 'o': X Wantfcs32 = FALSE; break; X case 'p': X Lzmanag = ZMPROT; break; X case 'r': X if (Lzconv == ZCRESUM) X Lzmanag = (Lzmanag & ZMMASK) | ZMCRC; X Lzconv = ZCRESUM; break; X case 'q': X Quiet=TRUE; Verbose=0; break; X case 't': X if (--argc < 1) { X usage(); X } X Rxtimeout = atoi(*++argv); X if (Rxtimeout<10 || Rxtimeout>1000) X usage(); X break; X case 'T': X if (++Test > 1) { X chartest(1); chartest(2); X mode(0); exit(0); X } X break; X#ifndef vax11c X case 'u': X ++Unlinkafter; break; X#endif X case 'v': X ++Verbose; break; X case 'w': X if (--argc < 1) { 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 X || (!blkopt && Txwspac < 1024)) X blkopt = Txwspac; X break; X case 'X': X ++Modem2; break; X case 'Y': X Lskipnocor = TRUE; X /* **** FALLL THROUGH TO **** */ X case 'y': X Lzmanag = ZMCLOB; break; X case 'Z': X case 'z': X Lztrans = ZTRLE; break; X default: X usage(); X } X } X } X else if ( !npats && argc>0) { X if (argv[0][0]) { X npats=argc; X patts=argv; X } X } X } X if (npats < 1 && !Command && !Test) X usage(); X if (Verbose) { X if (freopen(LOGFILE, "a", stderr)==NULL) { X printf("Can't open log file %s\n",LOGFILE); X exit(0200); X } X setbuf(stderr, NULL); X } X if (Fromcu && !Quiet) { X if (Verbose == 0) X Verbose = 2; X } X vfile("%s %s for %s\n", Progname, VERSION, OS); X X#ifdef XARGSFILE X vfile("npats=%d *patts=%s", npats, *patts); X if (npats == 1 && !strcmp(XARGSFILE, *patts)) { X in = fopen(XARGSFILE, "r"); X if (!in) { X printf(stderr, "Can't open / control file!\n"); X exit(2); X } X for (npats=0,argv=patts=xargv; npats>7); X } X#endif X fprintf(stderr, "Give your local XMODEM receive command now.\r\n"); X fflush(stderr); X return OK; X } X zperr("Awaiting pathname nak for %s", *name?name:""); X if ( !Zmodem) X if (getnak()) X return ERROR; X X q = (char *) 0; X if (Dottoslash) { /* change . to . */ X for (p=name; *p; ++p) { X if (*p == '/') X q = p; X else if (*p == '.') X *(q=p) = '/'; X } X if (q && strlen(++q) > 8) { /* 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 (*name) { X#ifdef XX X if (Thisflen >= 0) { X sprintf(p, "%u 0 0 0 %d %ld", X Thisflen, Filesleft, Totalleft); X Totalleft -= Thisflen; X } X#endif X#ifdef GENIE X else X sprintf(p, "%d", fdes.current_file_size * 1260); X vfile("%s open Binfile=%d size=%ld", name, Binfile, X fdes.current_file_size * 1260); X#endif X X#ifdef STAT X#ifndef XX X if (fstat(fileno(in), &f)!= -1) X sprintf(p, "%lu %lo %o 0 %d %ld", f.st_size, f.st_mtime, X f.st_mode, Filesleft, Totalleft); X Totalleft -= f.st_size; X#endif X#endif X X } X if (--Filesleft <= 0) X Totalleft = 0; X if (Totalleft < 0) X Totalleft = 0; X X#ifdef STAT X /* force 1k blocks if name won't fit in 128 byte block */ X if (txbuf[125]) X blklen=1024; X else { /* A little goodie for IMP/KMD */ X txbuf[127] = (f.st_size + 127) >>7; X txbuf[126] = (f.st_size + 127) >>15; X } X#endif X if (Zmodem) X return zsendfile(txbuf, 1+strlen(p)+(p-txbuf)); 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 switch (firstch = readline(800)) { X case ZPAD: X if (getzrxinit()) X return ERROR; X Ascii = 0; /* Receiver does the conversion */ X return FALSE; X case TIMEOUT: X zperr("Timeout on pathname"); X return TRUE; X case WANTG: X#ifdef 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 = readline(20)) == CAN && Lastrx == CAN) X return TRUE; X default: X break; X } X Lastrx = firstch; X } X} X X Xwctx(flen) Xlong flen; X{ X register int thisblklen; X register int sectnum, attempts, firstch; X long charssent; X X charssent = 0; firstsec=TRUE; thisblklen = blklen; X vfile("wctx:file length=%ld", flen); X X while ((firstch=readline(Rxtimeout))!=NAK && firstch != WANTCRC X && firstch != WANTG && firstch!=TIMEOUT && firstch!=CAN) X ; X if (firstch==CAN) { X zperr("Receiver CANcelled"); X return ERROR; X } X if (firstch==WANTCRC) X Crcflg=TRUE; X if (firstch==WANTG) X Crcflg=TRUE; X sectnum=0; X for (;;) { X if (flen <= (charssent + 896L)) X thisblklen = 128; X if ( !filbuf(txbuf, thisblklen)) X break; X if (wcputsec(txbuf, ++sectnum, thisblklen)==ERROR) X return ERROR; X charssent += thisblklen; X } X fclose(in); X attempts=0; X do { X purgeline(); X sendline(EOT); X flushmo(); X ++attempts; X } X while ((firstch=(readline(Rxtimeout)) != ACK) && attempts < RETRYMAX); X if (attempts == RETRYMAX) { X zperr("No ACK on EOT"); 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 sector to send */ X{ X register checksum, wcj; X register char *cp; X unsigned oldcrc; X int firstch; X int attempts; X X firstch=0; /* part of logic to detect CAN CAN */ X X if (Verbose>2) X fprintf(stderr, "Sector %3d %2dk\n", Totsecs, Totsecs/8 ); X else if (Verbose>1) X fprintf(stderr, "\rSector %3d %2dk ", Totsecs, Totsecs/8 ); X for (attempts=0; attempts <= RETRYMAX; attempts++) { X Lastrx= firstch; X sendline(cseclen==1024?STX:SOH); X sendline(sectnum); X sendline(-sectnum -1); X oldcrc=checksum=0; X for (wcj=cseclen,cp=buf; --wcj>=0; ) { X sendline(*cp); X oldcrc=updcrc((0377& *cp), oldcrc); X checksum += *cp++; X } X if (Crcflg) { X oldcrc=updcrc(0,updcrc(0,oldcrc)); X sendline((int)oldcrc>>8); X sendline((int)oldcrc); X } X else X sendline(checksum); X flushmo(); X X if (Optiong) { X firstsec = FALSE; return OK; X } X firstch = readline(Rxtimeout); Xgotnak: X switch (firstch) { X case CAN: X if(Lastrx == CAN) { Xcancan: X zperr("Cancelled"); return ERROR; X } X break; X case TIMEOUT: X zperr("Timeout on sector ACK"); continue; X case WANTCRC: X if (firstsec) X Crcflg = TRUE; X case NAK: X zperr("NAK on sector"); continue; X case ACK: X firstsec=FALSE; X Totsecs += (cseclen>>7); X return OK; X case ERROR: X zperr("Got burst for sector ACK"); break; X default: X zperr("Got %02x for sector ACK", firstch); break; X } X for (;;) { X Lastrx = firstch; X if ((firstch = readline(Rxtimeout)) == TIMEOUT) X break; X if (firstch == NAK || firstch == WANTCRC) X goto gotnak; X if (firstch == CAN && Lastrx == CAN) X goto cancan; X } X } X zperr("Retry Count Exceeded"); X return ERROR; X} X X/* fill buf with count chars padding with ^Z for CPM */ Xfilbuf(buf, count) Xregister char *buf; X{ X register c, m; X X if ( !Ascii) { X m = read(fileno(in), buf, count); X if (m <= 0) X return 0; X while (m < count) X buf[m++] = 032; X return count; X } X m=count; X if (Lfseen) { X *buf++ = 012; --m; Lfseen = 0; X } X while ((c=getc(in))!=EOF) { X if (c == 012) { X *buf++ = 015; X if (--m == 0) { X Lfseen = TRUE; break; X } X } X *buf++ =c; X if (--m == 0) X break; X } X if (m==count) X return 0; X else X while (--m>=0) X *buf++ = CPMEOF; X return count; X} X X/* Fill buffer with blklen chars */ Xzfilbuf() X{ X int n; X X#ifdef TXBSIZE X vfile("zfilbuf: bytcnt =%lu vpos=%lu blklen=%d", bytcnt, vpos, blklen); X /* We assume request is within buffer, or just beyond */ X txbuf = Txb + (bytcnt & TXBMASK); X if (vpos <= bytcnt) { X#ifdef GENIE X if (Binfile) { X long l, m; char *p; X X for (p=txbuf, n=0, l=blklen; l; l -= 128, p+= 128) { X n += m = fgetb(p, 128, in); X if (m == 0) X break; X } X } else X#endif X n = fread(txbuf, 1, blklen, in); X X vpos += n; X if (n < blklen) X Eofseen = 1; X vfile("zfilbuf: n=%d vpos=%lu Eofseen=%d", n, vpos, Eofseen); X return n; X } X if (vpos >= (bytcnt+blklen)) X return blklen; X /* May be a short block if crash recovery etc. */ X Eofseen = BEofseen; X return (vpos - bytcnt); X#else X n = fread(txbuf, 1, blklen, in); X if (n < blklen) X Eofseen = 1; X return n; X#endif X} X X#ifdef TXBSIZE X/* Replacement for brain damaged fseek function. Returns 0==success */ Xfooseek(fptr, pos, whence) XFILE *fptr; Xlong pos; X{ X long m, n; X#ifdef GENIE X long l, k; char *p; X#endif X X vfile("fooseek: pos =%lu vpos=%lu Canseek=%d", pos, vpos, Canseek); X /* Seek offset < current buffer */ X if (pos < (vpos -TXBSIZE +1024)) { X BEofseen = 0; X if (Canseek > 0) { X vpos = pos & ~TXBMASK; X if (vpos >= pos) X vpos -= TXBSIZE; X if (fseek(fptr, vpos, 0)) X return 1; X } X else if (Canseek == 0) { X#ifdef GENIE X if (Binfile) { X if (fseekb(fptr, vpos = 0L, 0)) X return 1; X } else X#endif X if (fseek(fptr, vpos = 0L, 0)) X return 1; X } else X return 1; X while (vpos < pos) { X#ifdef GENIE X if (Binfile) { X for (p=Txb,n=0,l=TXBSIZE; l; l -= 128,p+= 128) { X n += (k = fgetb(p, 128, fptr)); X vfile("bsk1: l=%d k=%d", l, k); X if (k == 0) X break; X } X } else X#endif X n = fread(Txb, 1, TXBSIZE, fptr); X vpos += n; X vfile("n=%d vpos=%ld", n, vpos); X if (n < TXBSIZE) { X BEofseen = 1; X break; X } X } X vfile("vpos=%ld", vpos); X return 0; X } X /* Seek offset > current buffer (Crash Recovery, etc.) */ X if (pos > vpos) { X if (Canseek) X if (fseek(fptr, vpos = (pos & ~TXBMASK), 0)) X return 1; X while (vpos <= pos) { X txbuf = Txb + (vpos & TXBMASK); X m = TXBSIZE - (vpos & TXBMASK); X vfile("m=%ld vpos=%ld", m,vpos); X#ifdef GENIE X if (Binfile) { X for (p=txbuf,n=0,l=m; l; l -= 128,p+= 128) { X n += (k = fgetb(p, 128, fptr)); X vfile("bsk2: l=%d k=%d n=%d", l, k, n); X if (k == 0) X break; X } X } else X#endif X n = fread(txbuf, 1, m, fptr); X vfile("n=%ld vpos=%ld", n,vpos); X vpos += n; X vfile("bo=%d m=%ld vpos=%ld", txbuf-Txb,m,vpos); X if (n < m) { X BEofseen = 1; X break; X } X } X return 0; X } X /* Seek offset is within current buffer */ X vfile("within buffer: vpos=%ld", vpos); X return 0; X} X#define fseek fooseek X#endif X X X/* VARARGS1 */ Xvfile(f, a, b, c, d) Xregister char *f; X{ X if (Verbose > 2) { X fprintf(stderr, f, a, b, c, d); X fprintf(stderr, "\n"); X } X} X X Xalrm() X{ X longjmp(tohere, -1); X} X X X#ifndef GENIE X#ifndef vax11c X/* X * readline(timeout) reads character(s) from file descriptor 0 X * timeout is in tenths of seconds X */ Xreadline(timeout) X{ X register int c; X static char byt[1]; X X fflush(stdout); X if (setjmp(tohere)) { X zperr("TIMEOUT"); X return TIMEOUT; X } X c = timeout/10; X if (c<2) X c=2; X if (Verbose>5) { X fprintf(stderr, "Timeout=%d Calling alarm(%d) ", timeout, c); X } X signal(SIGALRM, alrm); alarm(c); X c=read(0, byt, 1); X alarm(0); X if (Verbose>5) X fprintf(stderr, "ret %x\n", byt[0]); X if (c<1) X return TIMEOUT; X return (byt[0]&0377); X} X Xflushmo() X{ X fflush(stdout); X} X X Xpurgeline() X{ X#ifdef USG X ioctl(0, TCFLSH, 0); X#else X lseek(0, 0L, 2); X#endif X} X#endif X#endif X X/* send cancel string to get the other end to shut up */ Xcanit() X{ X static char canistr[] = { X 24,24,24,24,24,24,24,24,24,24,8,8,8,8,8,8,8,8,8,8,0 X }; X X#ifdef vax11c X raw_wbuf(strlen(canistr), canistr); X purgeline(); X#else X printf(canistr); X fflush(stdout); X#endif X} X X X/* X * Log an error X */ X/*VARARGS1*/ Xzperr(s,p,u) Xchar *s, *p, *u; X{ X if (Verbose <= 0) X return; X fprintf(stderr, "Retry %d: ", errors); X fprintf(stderr, s, p, u); X fprintf(stderr, "\n"); X} X X/* X * substr(string, token) searches for token in string s X * returns pointer to token within string if found, NULL otherwise X */ Xchar * Xsubstr(s, t) Xregister char *s,*t; X{ X register char *ss,*tt; X /* search for first char of token */ X for (ss=s; *s; s++) X if (*s == *t) X /* compare token with substring */ X for (ss=s,tt=t; ;) { X if (*tt == 0) X return s; X if (*ss++ != *tt++) X break; X } X return NULL; X} X Xchar *babble[] = { X#ifdef vax11c X "Send file(s) with ZMODEM/YMODEM/XMODEM Protocol", X " (Y) = Option applies to YMODEM only", X " (Z) = Option applies to ZMODEM only", X "Usage: sz [-2+abdefkLlNnquvwYy] [-] file ...", X " sz [-2Ceqv] -c COMMAND", X " \\ Force next option letter to upper case", X " sb [-2adfkquv] [-] file ...", X " sx [-2akquv] [-] file", X#endif X#ifndef vax11c X "Send file(s) with ZMODEM/YMODEM/XMODEM Protocol", X " (Y) = Option applies to YMODEM only", X " (Z) = Option applies to ZMODEM only", X "Usage: sz [-2+abdefkLlNnquvwYy] [-] file ...", X " sz [-2Ceqv] -c COMMAND", X " sb [-2adfkquv] [-] file ...", X " sx [-2akquv] [-] file", X#endif X#ifdef CSTOPB X " 2 Use 2 stop bits", X#endif X " + Append to existing destination file (Z)", X " a (ASCII) change NL to CR/LF", X " b Binary file transfer override", X " c send COMMAND (Z)", X#ifndef vax11c X " d Change '.' to '/' in pathnames (Y/Z)", X#endif X " e Escape all control characters (Z)", X " f send Full pathname (Y/Z)", X " i send COMMAND, ack Immediately (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 only if source newer (Z)", X " N send file only 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#ifndef vax11c X " u Unlink (remove) file after transmission", X#endif X " v Verbose - provide debugging information", X " w N restrict Window to N bytes (Z)", X " Y Yes, overwrite existing file, skip if not present at rx (Z)", X " y Yes, overwrite existing file (Z)", X " Z Activate ZMODEM compression(Z)", X "" X}; X Xusage() X{ X char **pp; X X for (pp=babble; **pp; ++pp) X fprintf(stderr, "%s\n", *pp); X fprintf(stderr, "%s for %s by Chuck Forsberg, Omen Technology INC\n", X VERSION, OS); X fprintf(stderr, "\t\t\042The High Reliability Software\042\n"); X cucheck(); X exit(SS_NORMAL); X} X X/* X * Get the receiver's init parameters X */ Xgetzrxinit() X{ X register n; X#ifdef STAT X struct stat f; X#endif X X for (n=10; --n>=0; ) { X X switch (zgethdr(Rxhdr, 1)) { X case ZCHALLENGE: /* Echo receiver's challenge numbr */ X stohdr(Rxpos); X zshhdr(4, ZACK, Txhdr); X continue; X case ZCOMMAND: /* They didn't see out ZRQINIT */ X stohdr(0L); X zshhdr(4, ZRQINIT, Txhdr); X continue; X case ZRINIT: X Rxflags = 0377 & Rxhdr[ZF0]; X Usevhdrs = Rxhdr[ZF1] & CANVHDR; X Txfcs32 = (Wantfcs32 && (Rxflags & CANFC32)); X Zctlesc |= Rxflags & TESCCTL; X Rxbuflen = (0377 & Rxhdr[ZP0])+((0377 & Rxhdr[ZP1])<<8); X if ( !(Rxflags & CANFDX)) X Txwindow = 0; X vfile("Rxbuflen=%d Tframlen=%d", Rxbuflen, Tframlen); X if ( !Fromcu) X signal(SIGINT, SIG_IGN); X#ifdef MODE2OK X mode(2); /* Set cbreak, XON/XOFF, etc. */ X#endif X X#ifndef READCHECK X#ifndef USG X#ifndef GENIE X /* Use 1024 byte frames if no sample/interrupt */ X if (Rxbuflen < 32 || Rxbuflen > 1024) { X Rxbuflen = 1024; X vfile("Rxbuflen=%d", Rxbuflen); X } X#endif X#endif X#endif X X /* Override to force shorter frame length */ X if (Rxbuflen && (Rxbuflen>Tframlen) && (Tframlen>=32)) X Rxbuflen = Tframlen; X if ( !Rxbuflen && (Tframlen>=32) && (Tframlen<=1024)) X Rxbuflen = Tframlen; X vfile("Rxbuflen=%d", Rxbuflen); X X#ifndef GENIE X#ifndef vax11c X#ifdef STAT X /* If using a pipe for testing set lower buf len */ X fstat(0, &f); X if ((f.st_mode & S_IFMT) != S_IFCHR) { X Rxbuflen = 1024; X } X#endif X#endif X#endif X X#ifdef BADSEEK X#ifdef GENIE X if (Txwindow == 0) { X Txwspac = (Txwindow = 4096)/4; X } X#else X if (Txwindow == 0) X Txwindow = TXBSIZE - 1024; X Txwspac = TXBSIZE/4; X#endif X Canseek = 0; X#endif X X /* X * If input is not a regular file, force ACK's to X * prevent running beyond the buffer limits X */ X#ifdef STAT X if ( !Command) { X fstat(fileno(in), &f); X if ((f.st_mode & S_IFMT) != S_IFREG) { X Canseek = -1; X#ifdef TXBSIZE X Txwindow = TXBSIZE - 1024; X Txwspac = TXBSIZE/4; X#else X return ERROR; X#endif X } X } X#endif X X /* Set initial subpacket length */ X if (blklen < 1024) { /* Command line override? */ X if (Effbaud > 300) X blklen = 256; X if (Effbaud > 1200) X blklen = 512; X if (Effbaud > 2400) X blklen = 1024; X } X if (Rxbuflen && blklen>Rxbuflen) X blklen = Rxbuflen; X if (blkopt && blklen > blkopt) X blklen = blkopt; X#ifdef GENIE X blklen /= 128; blklen *= 128; X if (blklen < 128) X blklen = 128; X#endif X vfile("Rxbuflen=%d blklen=%d", Rxbuflen, blklen); X vfile("Txwindow = %u Txwspac = %d", Txwindow, Txwspac); X X X if (Lztrans == ZTRLE && (Rxflags & CANRLE)) X Txfcs32 = 2; X else X Lztrans = 0; X X return (sendzsinit()); X case ZCAN: X case TIMEOUT: X return ERROR; X case ZRQINIT: X if (Rxhdr[ZF0] == ZCOMMAND) X continue; X default: X zshhdr(4, ZNAK, Txhdr); X continue; X } X } X return ERROR; X} X X/* Send send-init information */ Xsendzsinit() X{ X register c; X X if (Myattn[0] == '\0' && (!Zctlesc || (Rxflags & TESCCTL))) X return OK; X errors = 0; X for (;;) { X stohdr(0L); X#ifdef ALTCANOFF X Txhdr[ALTCOFF] = ALTCANOFF; X#endif X if (Zctlesc) { X Txhdr[ZF0] |= TESCCTL; zshhdr(4, ZSINIT, Txhdr); X } X else X zsbhdr(4, ZSINIT, Txhdr); X zsdata(Myattn, ZATTNLEN, ZCRCW); X c = zgethdr(Rxhdr, 1); X switch (c) { X case ZCAN: X return ERROR; X case ZACK: X return OK; X default: X if (++errors > 19) X return ERROR; X continue; X } X } X} X X/* Send file name and related info */ Xzsendfile(buf, blen) Xchar *buf; X{ X register c; X register UNSL long crc; X long lastcrcrq = -1; X char *p; X X for (;;) { X Txhdr[ZF0] = Lzconv; /* file conversion request */ X Txhdr[ZF1] = Lzmanag; /* file management request */ X if (Lskipnocor) X Txhdr[ZF1] |= ZMSKNOLOC; X Txhdr[ZF2] = Lztrans; /* file transport request */ X Txhdr[ZF3] = 0; X zsbhdr(4, ZFILE, Txhdr); X zsdata(buf, blen, ZCRCW); Xagain: X c = zgethdr(Rxhdr, 1); X switch (c) { X case ZRINIT: X while ((c = readline(50)) > 0) X if (c == ZPAD) { X goto again; X } X /* **** FALL THRU TO **** */ X default: X continue; X case ZCAN: X case TIMEOUT: X case ZABORT: X case ZFIN: X return ERROR; X case ZCRC: X if (Rxpos != lastcrcrq) { X lastcrcrq = Rxpos; X crc = 0xFFFFFFFFL; X if (Canseek >= 0) { X fseek(in, 0L, 0); X while (((c = getc(in)) != EOF) && --lastcrcrq) X crc = UPDC32(c, crc); X crc = ~crc; X clearerr(in); /* Clear possible EOF */ X lastcrcrq = Rxpos; X } X } X stohdr(crc); X zsbhdr(4, ZCRC, Txhdr); X goto again; X case ZSKIP: X fclose(in); return c; X case ZRPOS: X /* X * Suppress zcrcw request otherwise triggered by X * lastyunc==bytcnt X */ X#ifdef GENIE X /* X * Special case - turn on RLE if not archive, etc. X * otherwise turn off RLE unless cmd line specified X */ X if (Rxflags & CANRLE) { /* RX can do it */ X bytcnt = 0; X zfilbuf(); X vfile("txbuf012: %x %x %x", txbuf[0], txbuf[1], X txbuf[2]); X if ((txbuf[0] != 032) /* .ARC file */ X && (txbuf[0] != 0x1f) /* .Z file */ X && (txbuf[0] != 0x1c) /* .LHZ file */ X && strncmp(txbuf, "ZOO", 3) X && strncmp(txbuf, "GIF", 3) X && (txbuf[2] != 3)) /* .ZIP file */ X Txfcs32 = 2; X else if ( !(Lztrans & ZTRLE)) X Txfcs32 = 1; X } X /* GEnie binary can't seek to byte */ X if (Binfile) { X Rxpos &= ~127L; X } X#endif X if (fseek(in, Rxpos, 0)) X return ERROR; X Lastsync = (bytcnt = Txpos = Lrxpos = Rxpos) -1; X return zsendfdata(); X } X } X} X X/* Send the data in the file */ Xzsendfdata() X{ X register c, e, n; X register newcnt; X register long tcount = 0; X int junkcount; /* Counts garbage chars received by TX */ X static int tleft = 6; /* Counter for test mode */ X X junkcount = 0; X Beenhereb4 = FALSE; Xsomemore: X if (setjmp(intrjmp)) { Xwaitack: X junkcount = 0; X c = getinsync(0); Xgotack: X switch (c) { X default: X case ZCAN: X fclose(in); X return ERROR; X case ZSKIP: X fclose(in); X return c; X case ZACK: X case ZRPOS: X break; X case ZRINIT: X return OK; X } X#ifdef READCHECK X /* X * If the reverse channel can be tested for data, X * this logic may be used to detect error packets X * sent by the receiver, in place of setjmp/longjmp X * rdchk(fd) returns non 0 if a character is available X */ X while (rdchk(0)) { X#ifdef EATSIT X switch (checked) X#else X switch (readline(1)) X#endif X { X case CAN: X case ZPAD: X c = getinsync(1); X goto gotack; X case XOFF: /* Wait a while for an XON */ X case XOFF|0200: X readline(100); X } X } X#endif X } X X if ( !Fromcu) X signal(SIGINT, onintr); X newcnt = Rxbuflen; X Txwcnt = 0; X stohdr(Txpos); X zsbhdr(4, ZDATA, Txhdr); X X /* X * Special testing mode. This should force receiver to Attn,ZRPOS X * many times. Each time the signal should be caught, causing the X * file to be started over from the beginning. X */ X if (Test) { X if ( --tleft) X while (tcount < 20000) { X printf(qbf); fflush(stdout); X tcount += strlen(qbf); X#ifdef READCHECK X while (rdchk(0)) { X#ifdef EATSIT X switch (checked) X#else X switch (readline(1)) X#endif X { X case CAN: X case ZPAD: X#ifdef TCFLSH X ioctl(0, TCFLSH, 1); X#endif X goto waitack; X case XOFF: /* Wait for XON */ X case XOFF|0200: X readline(100); X } X } X#endif X } X signal(SIGINT, SIG_IGN); canit(); X sleep(3); purgeline(); mode(0); X printf("\nsz: Tcount = %ld\n", tcount); X if (tleft) { X printf("ERROR: Interrupts Not Caught\n"); X exit(1); X } X exit(SS_NORMAL); X } X X do { X n = zfilbuf(); X if (Eofseen) X e = ZCRCE; X else if (junkcount > 3) X e = ZCRCW; X else if (bytcnt == Lastsync) X e = ZCRCW; X else if (Rxbuflen && (newcnt -= n) <= 0) X e = ZCRCW; X else if (Txwindow && (Txwcnt += n) >= Txwspac) { X Txwcnt = 0; e = ZCRCQ; X } else X e = ZCRCG; X if (Verbose>1) X fprintf(stderr, "\r%7ld ZMODEM%s ", X Txpos, Crc32t?" CRC-32":""); X zsdata(txbuf, n, e); X bytcnt = Txpos += n; X if (e == ZCRCW) X goto waitack; X#ifdef READCHECK X /* X * If the reverse channel can be tested for data, X * this logic may be used to detect error packets X * sent by the receiver, in place of setjmp/longjmp X * rdchk(fd) returns non 0 if a character is available X */ X fflush(stdout); X while (rdchk(0)) { X#ifdef EATSIT X switch (checked) X#else X switch (readline(1)) X#endif X { X case CAN: X case ZPAD: X c = getinsync(1); X if (c == ZACK) X break; X#ifdef TCFLSH X ioctl(0, TCFLSH, 1); X#endif X /* zcrce - dinna wanna starta ping-pong game */ X zsdata(txbuf, 0, ZCRCE); X goto gotack; X case XOFF: /* Wait a while for an XON */ X case XOFF|0200: X readline(100); X default: X ++junkcount; X } X } X#endif /* READCHECK */ X if (Txwindow) { X while ((tcount = Txpos - Lrxpos) >= Txwindow) { X vfile("%ld window >= %u", tcount, Txwindow); X if (e != ZCRCQ) X zsdata(txbuf, 0, e = ZCRCQ); X c = getinsync(1); X if (c != ZACK) { X#ifdef TCFLSH X ioctl(0, TCFLSH, 1); X#endif X zsdata(txbuf, 0, ZCRCE); X goto gotack; X } X } X vfile("window = %ld", tcount); X } X } while (!Eofseen); X if ( !Fromcu) X signal(SIGINT, SIG_IGN); X X for (;;) { X stohdr(Txpos); X zsbhdr(4, ZEOF, Txhdr); X switch (getinsync(0)) { X case ZACK: X continue; X case ZRPOS: X goto somemore; X case ZRINIT: X return OK; X case ZSKIP: X fclose(in); X return c; X default: X fclose(in); X return ERROR; X } X } X} X X/* X * Respond to receiver's complaint, get back in sync with receiver X */ Xgetinsync(flag) X{ X register c; X X for (;;) { X if (Test) { X printf("\r\n\n\n***** Signal Caught *****\r\n"); X Rxpos = 0; c = ZRPOS; X } else X c = zgethdr(Rxhdr, 0); X switch (c) { X case ZCAN: X case ZABORT: X case ZFIN: X case TIMEOUT: X return ERROR; X case ZRPOS: X /* ************************************* */ X /* If sending to a buffered modem, you */ X /* might send a break at this point to */ X /* dump the modem's buffer. */ X clearerr(in); /* In case file EOF seen */ X if (fseek(in, Rxpos, 0)) X return ERROR; X Eofseen = 0; X bytcnt = Lrxpos = Txpos = Rxpos; X#ifndef GENIE X if (Lastsync == Rxpos) { X if (++Beenhereb4 > 4) X if (blklen > 32) X blklen /= 2; X } X#endif X Lastsync = Rxpos; X return c; X case ZACK: X Lrxpos = Rxpos; X if (flag || Txpos == Rxpos) X return ZACK; X continue; X case ZRINIT: X case ZSKIP: X fclose(in); X return c; X case ERROR: X default: X zsbhdr(4, ZNAK, Txhdr); X continue; X } X } X} X X X/* Say "bibi" to the receiver, try to do it cleanly */ Xsaybibi() X{ X for (;;) { X stohdr(0L); /* CAF Was zsbhdr - minor change */ X zshhdr(4, ZFIN, Txhdr); /* to make debugging easier */ X switch (zgethdr(Rxhdr, 0)) { X case ZFIN: X sendline('O'); sendline('O'); flushmo(); X case ZCAN: X case TIMEOUT: X return; X } X } X} X X/* Local screen character display function */ Xbttyout(c) X{ X if (Verbose) X putc(c, stderr); X} X X/* Send command and related info */ Xzsendcmd(buf, blen) Xchar *buf; X{ X register c; X long cmdnum; X X#ifdef GENIE X cmdnum = 69; X#else X cmdnum = getpid(); X#endif X errors = 0; X for (;;) { X stohdr(cmdnum); X Txhdr[ZF0] = Cmdack1; X zsbhdr(4, ZCOMMAND, Txhdr); X zsdata(buf, blen, ZCRCW); Xlisten: X Rxtimeout = 100; /* Ten second wait for resp. */ X Usevhdrs = 0; /* Allow rx to send fixed len headers */ X c = zgethdr(Rxhdr, 1); X X switch (c) { X case ZRINIT: X goto listen; /* CAF 8-21-87 */ X case ERROR: X case GCOUNT: X case TIMEOUT: X if (++errors > Cmdtries) X return ERROR; X continue; X case ZCAN: X case ZABORT: X case ZFIN: X case ZSKIP: X case ZRPOS: X return ERROR; X default: X if (++errors > 20) X return ERROR; X continue; X case ZCOMPL: X Exitcode = Rxpos; X saybibi(); X return OK; X case ZRQINIT: X#ifdef vax11c /* YAMP :== Yet Another Missing Primitive */ X return ERROR; X#else X vfile("******** RZ *******"); X system("rz"); X vfile("******** SZ *******"); X goto listen; X#endif X } X } X} X X/* X * If called as sb use YMODEM protocol X */ Xchkinvok(s) Xchar *s; X{ X register char *p; X X p = s; X while (*p == '-') X s = ++p; X while (*p) X if (*p++ == '/') X s = p; X if (*s == 'v') { X Verbose=1; ++s; X } X Progname = s; X if (s[0]=='s' && s[1]=='b') { X Nozmodem = TRUE; blklen=1024; X } X if (s[0]=='s' && s[1]=='x') { X Modem2 = TRUE; X } X} X X#ifdef STAT Xcountem(argc, argv) Xregister char **argv; X{ X register c; X struct stat f; X X for (Totalleft = 0, Filesleft = 0; --argc >=0; ++argv) { X f.st_size = -1; X if (Verbose>2) { X fprintf(stderr, "\nCountem: %03d %s ", argc, *argv); X fflush(stderr); X } X if (access(*argv, 04) >= 0 && stat(*argv, &f) >= 0) { X c = f.st_mode & S_IFMT; X if (c != S_IFDIR && c != S_IFBLK) { X ++Filesleft; Totalleft += f.st_size; X } X } X if (Verbose>2) X fprintf(stderr, " %ld", f.st_size); X } X if (Verbose>2) X fprintf(stderr, "\ncountem: Total %d %ld\n", X Filesleft, Totalleft); X} X#else Xcountem(argc, argv) Xregister char **argv; X{ X register c; X register char *p; X long size; X X for (Totalleft = 0, Filesleft = 0; --argc >=0; ++argv) { X size = -1; X if (Verbose>2) { X fprintf(stderr, "\nCountem: %03d %s ", argc, *argv); X fflush(stderr); X } X ++Filesleft; X#ifdef XARGSFILE X /* Look for file length in third colon sep field */ X for (p = *argv; *p; ++p) { X if (*p == ':') { X for (++p; *p; ++p) { X if (*p == ':') { X ++p; X size = atol(p); X Totalleft += size; X break; X } X } X break; X } X } X#endif X X if (Verbose>2) X fprintf(stderr, " %ld", size); X } X if (Verbose>2) X fprintf(stderr, "\ncountem: Total %d %ld\n", X Filesleft, Totalleft); X} X#endif X Xchartest(m) X{ X register n; X X mode(m); X printf("\r\n\nCharacter Transparency Test Mode %d\r\n", m); X printf("If Pro-YAM/ZCOMM is not displaying ^M hit ALT-V NOW.\r\n"); X printf("Hit Enter.\021"); fflush(stdout); X readline(500); X X for (n = 0; n < 256; ++n) { X if (!(n%8)) X printf("\r\n"); X printf("%02x ", n); fflush(stdout); X sendline(n); flushmo(); X printf(" "); fflush(stdout); X if (n == 127) { X printf("Hit Enter.\021"); fflush(stdout); X readline(500); X printf("\r\n"); fflush(stdout); X } X } X printf("\021\r\nEnter Characters, echo is in hex.\r\n"); X printf("Hit SPACE or pause 40 seconds for exit.\r\n"); X X while (n != TIMEOUT && n != ' ') { X n = readline(400); X printf("%02x\r\n", n); X fflush(stdout); X } X printf("\r\nMode %d character transparency test ends.\r\n", m); X fflush(stdout); X} X X/* End of sz.c */ END_OF_FILE if test 44054 -ne `wc -c <'sz.c'`; then echo shar: \"'sz.c'\" unpacked with wrong size! fi # end of 'sz.c' fi echo shar: End of archive 4 \(of 4\). cp /dev/null ark4isdone MISSING="" for I in 1 2 3 4 ; do if test ! -f ark${I}isdone ; then MISSING="${MISSING} ${I}" fi done if test "${MISSING}" = "" ; then echo You have unpacked all 4 archives. rm -f ark[1-9]isdone else echo You still need to unpack the following archives: echo " " ${MISSING} fi ## End of shell archive. exit 0 .