Zmodem protocol changes
This commit is contained in:
parent
de58423731
commit
9d82aca2c3
@ -52,7 +52,7 @@ struct tchars oldtch, tch;
|
||||
#endif
|
||||
|
||||
int hanged_up = 0;
|
||||
unsigned Baudrate = 2400;
|
||||
unsigned Baudrate = 9600; /* Default, set by first io_mode() call */
|
||||
int current_mode = -1;
|
||||
|
||||
|
||||
@ -188,26 +188,29 @@ int io_mode(int fd, int n)
|
||||
#ifdef USE_TERMIOS
|
||||
case 2:
|
||||
if (!did0) {
|
||||
did0 = TRUE;
|
||||
tcgetattr(fd,&oldtty);
|
||||
}
|
||||
tty = oldtty;
|
||||
|
||||
tty.c_iflag = 0; /* Transparant input */
|
||||
tty.c_iflag = BRKINT | IXON;
|
||||
tty.c_oflag = 0; /* Transparent output */
|
||||
tty.c_cflag &= ~( CSIZE | CSTOPB | PARENB | PARODD); /* Disable parity and all character sizes */
|
||||
tty.c_cflag |= CS8 | CREAD | HUPCL | CLOCAL;
|
||||
tty.c_lflag = 0;
|
||||
tty.c_cc[VMIN] = 1;
|
||||
tty.c_cc[VTIME] = 0;
|
||||
tty.c_cflag &= ~( CSIZE | PARENB ); /* Disable parity and all character sizes */
|
||||
tty.c_cflag |= CS8 | CREAD;
|
||||
tty.c_lflag = (protocol == ZM_ZMODEM) ? 0 : ISIG;
|
||||
tty.c_cc[VINTR] = (protocol == ZM_ZMODEM) ? -1:030; /* Interrupt char */
|
||||
tty.c_cc[VQUIT] = -1; /* Quit char */
|
||||
tty.c_cc[VMIN] = 3; /* This many chars satisfies reads */
|
||||
tty.c_cc[VTIME] = 1;
|
||||
|
||||
tcsetattr(fd,TCSADRAIN,&tty);
|
||||
did0 = TRUE;
|
||||
Baudrate = getspeed(cfgetospeed(&tty));
|
||||
Syslog('t', "Baudrate = %d", Baudrate);
|
||||
|
||||
return 0;
|
||||
case 1:
|
||||
case 3:
|
||||
if (!did0) {
|
||||
did0 = TRUE;
|
||||
tcgetattr(fd,&oldtty);
|
||||
#ifdef __linux__
|
||||
Syslog('t', "iflag%s%s%s%s%s%s%s%s%s%s%s%s%s",
|
||||
@ -313,36 +316,36 @@ int io_mode(int fd, int n)
|
||||
(oldtty.c_lflag & NOFLSH) ? " NOFLSH":"");
|
||||
#endif
|
||||
}
|
||||
|
||||
tty = oldtty;
|
||||
|
||||
tty.c_iflag = IGNBRK;
|
||||
if (n == 3) { /* with flow control */
|
||||
tty.c_iflag |= IXOFF; /* Enable XON/XOFF flow control on input */
|
||||
tty.c_cflag |= CRTSCTS; /* hardware flowcontrol */
|
||||
}
|
||||
|
||||
tty.c_iflag = n==3 ? (IXON|IXOFF) : IXOFF;
|
||||
|
||||
/*
|
||||
* Setup raw mode: no echo, noncanonical (no edit chars),
|
||||
* no signal generating chars, and no extended chars (^V,
|
||||
* ^O, ^R, ^W).
|
||||
*/
|
||||
tty.c_lflag = 0; /* Transparant input */
|
||||
tty.c_lflag &= ~(ECHO | ICANON | ISIG | IEXTEN);
|
||||
// tty.c_lflag = 0; /* Transparant input */
|
||||
tty.c_oflag = 0; /* Transparent output */
|
||||
tty.c_cflag &= ~( CSIZE | CSTOPB | PARENB | PARODD); /* Same baud rate, disable parity */
|
||||
tty.c_cflag |= CS8 | CREAD | HUPCL | CLOCAL;
|
||||
tty.c_cc[VMIN] = 1; /* This many chars satisfies reads */
|
||||
tty.c_cc[VTIME] = 0;
|
||||
|
||||
tty.c_cflag &= ~( CSIZE | PARENB ); /* Same baud rate, disable parity */
|
||||
tty.c_cflag |= CS8;
|
||||
tty.c_cc[VMIN] = 2; /* This many chars satisfies reads */
|
||||
tty.c_cc[VTIME] = 1;
|
||||
tcsetattr(fd,TCSADRAIN,&tty);
|
||||
Baudrate = getspeed(cfgetospeed(&tty));
|
||||
Syslog('t', "Baudrate = %d", Baudrate);
|
||||
did0 = TRUE;
|
||||
|
||||
return 0;
|
||||
case 0:
|
||||
if (!did0)
|
||||
return -1;
|
||||
tcdrain (fd); /* wait until everything is sent */
|
||||
tcflush (fd,TCIOFLUSH); /* flush input queue */
|
||||
tcsetattr (fd,TCSADRAIN,&oldtty);
|
||||
tcsetattr (fd,TCSADRAIN,&oldtty); /* Restore */
|
||||
tcflow (fd,TCOON); /* restart output */
|
||||
|
||||
return 0;
|
||||
@ -383,7 +386,7 @@ void sendbrk(void)
|
||||
|
||||
if (isatty(0)) {
|
||||
#ifdef USE_TERMIOS
|
||||
tcsendbreak(0, 0);
|
||||
tcsendbreak(0, 200);
|
||||
#endif
|
||||
#ifdef USE_TERMIO
|
||||
ioctl(0, TCSBRK, 0);
|
||||
|
@ -77,7 +77,6 @@ int Rxtimeout = 10; /* Seconds to wait for something, receiver */
|
||||
char *txbuf=NULL;
|
||||
static int lastsent; /* Last char we sent */
|
||||
static int Not8bit; /* Seven bits seen on header */
|
||||
static char zsendline_tab[256];
|
||||
|
||||
extern unsigned Baudrate;
|
||||
extern int zmodem_requested;
|
||||
@ -200,6 +199,9 @@ void zsbhdr(int type, char *shdr)
|
||||
}
|
||||
|
||||
BUFFER_FLUSH();
|
||||
|
||||
if (type != ZDATA)
|
||||
fflush(stdout);
|
||||
}
|
||||
|
||||
|
||||
@ -272,6 +274,7 @@ void zshhdr(int type, char *shdr)
|
||||
BUFFER_BYTE(021);
|
||||
|
||||
BUFFER_FLUSH();
|
||||
fflush(stdout);
|
||||
}
|
||||
|
||||
|
||||
@ -308,6 +311,9 @@ void zsdata(register char *buf, int length, int frameend)
|
||||
BUFFER_BYTE(XON);
|
||||
|
||||
BUFFER_FLUSH();
|
||||
|
||||
if (frameend != ZCRCG)
|
||||
fflush(stdout);
|
||||
}
|
||||
|
||||
|
||||
@ -322,9 +328,6 @@ void zsda32(register char *buf, int length, int frameend)
|
||||
crc = 0xFFFFFFFFL;
|
||||
for (;--length >= 0; ++buf) {
|
||||
c = *buf & 0377;
|
||||
if (c & 0140)
|
||||
BUFFER_BYTE(lastsent = c);
|
||||
else
|
||||
zsendline(c);
|
||||
crc = updcrc32(c, crc);
|
||||
}
|
||||
@ -476,7 +479,7 @@ void garbitch(void)
|
||||
int zgethdr(char *shdr)
|
||||
{
|
||||
register int c, n, cancount, tmcount;
|
||||
int Zrwindow = 1024;
|
||||
int Zrwindow = 1400;
|
||||
|
||||
n = Zrwindow + Baudrate;
|
||||
Rxframeind = Rxtype = 0;
|
||||
@ -488,10 +491,11 @@ again:
|
||||
/*
|
||||
* Return immediate ERROR if ZCRCW sequence seen
|
||||
*/
|
||||
if (((c = GETCHAR(Rxtimeout)) < 0) && (c != TIMEOUT))
|
||||
goto fifi;
|
||||
else {
|
||||
switch(c) {
|
||||
// if (((c = GETCHAR(Rxtimeout)) < 0) && (c != TIMEOUT))
|
||||
// goto fifi;
|
||||
// else {
|
||||
// switch(c) {
|
||||
switch (c = GETCHAR(Rxtimeout)) {
|
||||
case 021:
|
||||
case 0221: goto again;
|
||||
case HANGUP: goto fifi;
|
||||
@ -539,7 +543,7 @@ agn2:
|
||||
case ZPAD: /* This is what we want. */
|
||||
break;
|
||||
}
|
||||
}
|
||||
// }
|
||||
cancount = 5;
|
||||
|
||||
splat:
|
||||
@ -566,7 +570,8 @@ splat:
|
||||
c = zrhhdr(shdr);
|
||||
break;
|
||||
case CAN: goto gotcan;
|
||||
default: goto agn2;
|
||||
default: Syslog('z', "Zmodem: zgethdr got %d char", c);
|
||||
goto agn2;
|
||||
}
|
||||
|
||||
for (n = 4; ++n < ZMAXHLEN; ) /* Clear unused hdr bytes */
|
||||
@ -739,64 +744,32 @@ void zputhex(int c)
|
||||
*/
|
||||
void zsendline(int c)
|
||||
{
|
||||
switch(zsendline_tab[(unsigned) (c&=0377)]) {
|
||||
case 0: BUFFER_BYTE(lastsent = c);
|
||||
switch (c &= 0377) {
|
||||
case 0377:
|
||||
lastsent = c;
|
||||
if (Zctlesc || Zsendmask[32]) {
|
||||
BUFFER_BYTE(ZDLE); c = ZRUB1;
|
||||
}
|
||||
BUFFER_BYTE(c);
|
||||
break;
|
||||
case 1: BUFFER_BYTE(ZDLE);
|
||||
c ^= 0100;
|
||||
BUFFER_BYTE(lastsent = c);
|
||||
case ZDLE:
|
||||
BUFFER_BYTE(ZDLE);
|
||||
BUFFER_BYTE(lastsent = (c ^= 0100));
|
||||
break;
|
||||
case 2: if ((lastsent & 0177) != '@') {
|
||||
BUFFER_BYTE(lastsent = c);
|
||||
} else {
|
||||
case 021:
|
||||
case 023:
|
||||
case 0221:
|
||||
case 0223:
|
||||
BUFFER_BYTE(ZDLE);
|
||||
c ^= 0100;
|
||||
BUFFER_BYTE(lastsent = c);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void zsendline_init(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
Syslog('z', "zsendline_init() Zctlesc=%d", Zctlesc);
|
||||
|
||||
for (i = 0; i < 256; i++) {
|
||||
if (i & 0140)
|
||||
zsendline_tab[i] = 0;
|
||||
else {
|
||||
switch(i) {
|
||||
case ZDLE:
|
||||
case XOFF: /* ^Q */
|
||||
case XON: /* ^S */
|
||||
case (XOFF | 0200):
|
||||
case (XON | 0200):
|
||||
zsendline_tab[i]=1;
|
||||
break;
|
||||
case 020: /* ^P */
|
||||
case 0220:
|
||||
zsendline_tab[i]=1;
|
||||
break;
|
||||
case 015:
|
||||
case 0215:
|
||||
if (Zctlesc)
|
||||
zsendline_tab[i]=1;
|
||||
else
|
||||
zsendline_tab[i]=2;
|
||||
break;
|
||||
default:
|
||||
if (Zctlesc)
|
||||
zsendline_tab[i]=1;
|
||||
else
|
||||
zsendline_tab[i]=0;
|
||||
if (((c & 0140) == 0) && (Zctlesc || Zsendmask[c & 037])) {
|
||||
BUFFER_BYTE(ZDLE); c ^= 0100;
|
||||
}
|
||||
BUFFER_BYTE(lastsent = c);
|
||||
}
|
||||
}
|
||||
// zsendline_tab[255] = 1; /* IAC */
|
||||
}
|
||||
|
||||
|
||||
|
@ -22,7 +22,14 @@
|
||||
#define ZBIN 'A' /* Binary frame indicator (CRC-16) */
|
||||
#define ZHEX 'B' /* HEX frame indicator */
|
||||
#define ZBIN32 'C' /* Binary frame with 32 bit FCS */
|
||||
#define ZBINR32 'D' /* RLE packed Binary frame with 32 bit FCS */
|
||||
#define ZVBIN 'a' /* Binary frame indicator (CRC-16) */
|
||||
#define ZVHEX 'b' /* HEX frame indicator */
|
||||
#define ZVBIN32 'c' /* Binary frame with 32 bit FCS */
|
||||
#define ZVBINR32 'd' /* RLE packed Binary frame with 32 bit FCS */
|
||||
#define ZRESC 0176 /* RLE flag/escape character */
|
||||
#define ZMAXHLEN 16 /* Max header information length NEVER CHANGE */
|
||||
#define ZMAXSPLEN 1024 /* Max subpacket length NEVER CHANGE */
|
||||
|
||||
|
||||
/* Frame types (see array "frametypes" in zm.c) */
|
||||
@ -75,19 +82,28 @@
|
||||
#define ZP3 3 /* High order 8 bits of file position */
|
||||
|
||||
/* Parameters for ZRINIT header */
|
||||
#define ZRPXWN 8 /* 9th byte in header contains window size/256 */
|
||||
#define ZRPXQQ 9 /* 10th to 14th bytes contain quote mask */
|
||||
|
||||
/* Bit Masks for ZRINIT flags byte ZF0 */
|
||||
#define CANFDX 01 /* Rx can send and receive true FDX */
|
||||
#define CANOVIO 02 /* Rx can receive data during disk I/O */
|
||||
#define CANBRK 04 /* Rx can send a break signal */
|
||||
#define CANRLE 010 /* Receiver can decode RLE */
|
||||
#define CANLZW 020 /* Receiver can uncompress */
|
||||
#define CANFC32 040 /* Receiver can use 32 bit Frame Check */
|
||||
#define ESCCTL 0100 /* Receiver expects ctl chars to be escaped */
|
||||
#define ESC8 0200 /* Receiver expects 8th bit to be escaped */
|
||||
|
||||
/* Bit Masks for ZRINIT flags byte ZF1 */
|
||||
#define CANVHDR 01 /* Variable headers OK */
|
||||
#define ZRRQWN 8 /* Receiver specified window size in ZRPXWN */
|
||||
#define ZRRQQQ 16 /* Additional control chars to quote in ZRPXQQ */
|
||||
#define ZRQNVH (ZRRQWN|ZRRQQQ) /* Variable len hdr reqd to access info */
|
||||
|
||||
/* Parameters for ZSINIT frame */
|
||||
#define ZATTNLEN 32 /* Max length of attention string */
|
||||
#define ALTCOFF ZF1 /* Offset to alternate canit string, 0 if not used */
|
||||
/* Bit Masks for ZSINIT flags byte ZF0 */
|
||||
#define TESCCTL 0100 /* Transmitter expects ctl chars to be escaped */
|
||||
#define TESC8 0200 /* Transmitter expects 8th bit to be escaped */
|
||||
@ -115,7 +131,9 @@
|
||||
#define ZTRLE 3 /* Run Length encoding */
|
||||
/* Extended options for ZF3, bit encoded */
|
||||
#define ZXSPARS 64 /* Encoding for sparse file operations */
|
||||
#define ZCANVHDR 01 /* Variable headers OK */
|
||||
/* Receiver window size override */
|
||||
#define ZRWOVR 4 /* byte position for receive window override/256 */
|
||||
|
||||
/* Parameters for ZCOMMAND frame ZF0 (otherwise 0) */
|
||||
#define ZCACK1 1 /* Acknowledge, then do command */
|
||||
@ -134,7 +152,7 @@ char Rxhdr[ZMAXHLEN]; /* Received header */
|
||||
char Txhdr[ZMAXHLEN]; /* Transmitted header */
|
||||
char Attn[ZATTNLEN+1]; /* Attention string rx sends to tx on err */
|
||||
char *Altcan; /* Alternate canit string */
|
||||
//char Zsendmask[33]; /* Additional control characters to mask */
|
||||
char Zsendmask[33]; /* Additional control characters to mask */
|
||||
int Zctlesc;
|
||||
|
||||
enum zm_type_enum {
|
||||
@ -159,7 +177,6 @@ int zdlread(void);
|
||||
void stohdr(int);
|
||||
int rclhdr(register char *);
|
||||
char *protname(void);
|
||||
void zsendline_init(void);
|
||||
void purgeline(int);
|
||||
void canit(int);
|
||||
|
||||
|
@ -88,7 +88,6 @@ int zmrcvfiles(int want1k, int wantg)
|
||||
Syslog('+', "%s: start receive", protname());
|
||||
|
||||
get_frame_buffer();
|
||||
zsendline_init();
|
||||
|
||||
Rxtimeout = 10;
|
||||
if (secbuf == NULL)
|
||||
|
158
mbsebbs/zmsend.c
158
mbsebbs/zmsend.c
@ -47,6 +47,7 @@ static int zfilbuf(void);
|
||||
static int zsendfile(char*,int);
|
||||
static int zsendfdata(void);
|
||||
static int getinsync(int);
|
||||
void initzsendmsk(char *p);
|
||||
|
||||
static FILE *in;
|
||||
static int Eofseen; /* EOF seen on input set by zfilbuf */
|
||||
@ -61,14 +62,23 @@ static int blkopt; /* Override value for zmodem blklen */
|
||||
static int errors;
|
||||
static int Lastsync;
|
||||
static int bytcnt;
|
||||
static int maxbytcnt;
|
||||
static int Lrxpos=0;
|
||||
static int Lztrans=0;
|
||||
static int Lzmanag=0;
|
||||
static int Lskipnocor=0;
|
||||
static int Lzconv=0;
|
||||
static int Beenhereb4;
|
||||
static char Myattn[]={0};
|
||||
static int Canseek = 1; /* 1: Can seek 0: only rewind -1: neither (pipe) */
|
||||
/*
|
||||
* Attention string to be executed by receiver to interrupt streaming data
|
||||
* when an error is detected. A pause (0336) may be needed before the
|
||||
* ^C (03) or after it.
|
||||
*/
|
||||
static char Myattn[]={ 0 };
|
||||
static int skipsize;
|
||||
static jmp_buf intrjmp; /* For the interrupt on RX CAN */
|
||||
|
||||
struct timeval starttime, endtime;
|
||||
struct timezone tz;
|
||||
static int use8k = FALSE;
|
||||
@ -81,6 +91,16 @@ extern char *frametypes[];
|
||||
extern unsigned Baudrate;
|
||||
|
||||
|
||||
/* Called when ZMODEM gets an interrupt (^X) */
|
||||
void onintr(int );
|
||||
void onintr(int c)
|
||||
{
|
||||
signal(SIGINT, SIG_IGN);
|
||||
Syslog('z', "Zmodem: got signal interrupt");
|
||||
longjmp(intrjmp, -1);
|
||||
}
|
||||
|
||||
|
||||
int zmsndfiles(down_list *lst, int try8)
|
||||
{
|
||||
int rc, maxrc = 0;
|
||||
@ -89,11 +109,11 @@ int zmsndfiles(down_list *lst, int try8)
|
||||
Syslog('+', "Zmodem: start Zmodem%s send", try8 ? "-8K":"");
|
||||
|
||||
get_frame_buffer();
|
||||
zsendline_init();
|
||||
|
||||
use8k = try8;
|
||||
protocol = ZM_ZMODEM;
|
||||
Rxtimeout = 60;
|
||||
bytcnt = maxbytcnt = -1;
|
||||
|
||||
if ((rc = initsend())) {
|
||||
if (txbuf)
|
||||
@ -132,7 +152,7 @@ int zmsndfiles(down_list *lst, int try8)
|
||||
free(txbuf);
|
||||
txbuf = NULL;
|
||||
del_frame_buffer();
|
||||
// io_mode(0, 1);
|
||||
io_mode(0, 1);
|
||||
|
||||
Syslog('z', "Zmodem: send rc=%d", maxrc);
|
||||
return (maxrc < 2)?0:maxrc;
|
||||
@ -144,7 +164,7 @@ static int initsend(void)
|
||||
{
|
||||
Syslog('z', "Zmodem: initsend");
|
||||
|
||||
// io_mode(0, 1);
|
||||
io_mode(0, 1);
|
||||
PUTSTR((char *)"rz\r");
|
||||
stohdr(0L);
|
||||
zshhdr(ZRQINIT, Txhdr);
|
||||
@ -266,19 +286,19 @@ int getzrxinit(void)
|
||||
case ZRINIT:
|
||||
Rxflags = 0377 & Rxhdr[ZF0];
|
||||
Txfcs32 = (Wantfcs32 && (Rxflags & CANFC32));
|
||||
{
|
||||
int old = Zctlesc;
|
||||
Zctlesc |= Rxflags & TESCCTL;
|
||||
/* update table - was initialised to not escape */
|
||||
if (Zctlesc && !old)
|
||||
zsendline_init();
|
||||
if (Rxhdr[ZF1] & ZRRQQQ) { /* Escape ctrls */
|
||||
initzsendmsk(Rxhdr + ZRPXQQ);
|
||||
Syslog('z', "Zmodem: requested ZRPXQQ");
|
||||
}
|
||||
|
||||
Rxbuflen = (0377 & Rxhdr[ZP0])+((0377 & Rxhdr[ZP1])<<8);
|
||||
if ( !(Rxflags & CANFDX))
|
||||
Txwindow = 0;
|
||||
Syslog('z', "Zmodem: Remote allowed Rxbuflen=%d", Rxbuflen);
|
||||
// io_mode(0, 2); /* Set cbreak, XON/XOFF, etc. */
|
||||
Syslog('z', "Zmodem: Rxbuflen=%d", Rxbuflen);
|
||||
|
||||
signal(SIGINT, SIG_IGN);
|
||||
io_mode(0, 2); /* Set cbreak, XON/XOFF, etc. */
|
||||
|
||||
/* Set initial subpacket length */
|
||||
if (blklen < 1024) { /* Command line override? */
|
||||
@ -288,6 +308,8 @@ int getzrxinit(void)
|
||||
blklen = 512;
|
||||
if (Baudrate > 2400)
|
||||
blklen = 1024;
|
||||
if (Baudrate < 300)
|
||||
blklen = 1024;
|
||||
}
|
||||
if (Rxbuflen && blklen>Rxbuflen)
|
||||
blklen = Rxbuflen;
|
||||
@ -337,7 +359,8 @@ int sendzsinit(void)
|
||||
} else
|
||||
zsbhdr(ZSINIT, Txhdr);
|
||||
Syslog('z', "sendzsinit Myattn \"%s\"", printable(Myattn, 0));
|
||||
zsdata(Myattn, 1 + strlen(Myattn), ZCRCW);
|
||||
// zsdata(Myattn, 1 + strlen(Myattn), ZCRCW);
|
||||
zsdata(Myattn, ZATTNLEN, ZCRCW);
|
||||
c = zgethdr(Rxhdr);
|
||||
switch (c) {
|
||||
case ZCAN: return TERROR;
|
||||
@ -375,9 +398,12 @@ int zfilbuf(void)
|
||||
*/
|
||||
int zsendfile(char *buf, int blen)
|
||||
{
|
||||
int c;
|
||||
int c, i, m, n;
|
||||
register unsigned int crc = -1;
|
||||
int lastcrcrq = -1;
|
||||
int lastcrcof = -1;
|
||||
int l;
|
||||
char *p;
|
||||
|
||||
Syslog('z', "zsendfile %s (%d)", buf, blen);
|
||||
for (errors=0; ++errors<11;) {
|
||||
@ -414,15 +440,42 @@ again:
|
||||
case ZNAK:
|
||||
continue;
|
||||
case ZCRC:
|
||||
if (Rxpos != lastcrcrq) {
|
||||
l = Rxhdr[9] & 0377;
|
||||
l = (l<<8) + (Rxhdr[8] & 0377);
|
||||
l = (l<<8) + (Rxhdr[7] & 0377);
|
||||
l = (l<<8) + (Rxhdr[6] & 0377);
|
||||
if (Rxpos != lastcrcrq || l != lastcrcof) {
|
||||
lastcrcrq = Rxpos;
|
||||
crc = 0xFFFFFFFFL;
|
||||
fseek(in, 0L, 0);
|
||||
while (((c = getc(in)) != EOF) && --lastcrcrq)
|
||||
// fseek(in, 0L, 0);
|
||||
// while (((c = getc(in)) != EOF) && --lastcrcrq)
|
||||
// crc = updcrc32(c, crc);
|
||||
// crc = ~crc;
|
||||
// clearerr(in); /* Clear possible EOF */
|
||||
// lastcrcrq = Rxpos;
|
||||
|
||||
if (Canseek >= 0) {
|
||||
fseek(in, bytcnt = l, 0); i = 0;
|
||||
Syslog('z', "Zmodem: CRC32 on %ld bytes", Rxpos);
|
||||
do {
|
||||
/* No rx timeouts! */
|
||||
if (--i < 0) {
|
||||
i = 32768L/blklen;
|
||||
PUTCHAR(SYN);
|
||||
fflush(stdout);
|
||||
}
|
||||
bytcnt += m = n = zfilbuf();
|
||||
if (bytcnt > maxbytcnt)
|
||||
maxbytcnt = bytcnt;
|
||||
for (p = txbuf; --m >= 0; ++p) {
|
||||
c = *p & 0377;
|
||||
crc = updcrc32(c, crc);
|
||||
}
|
||||
Syslog('z', "bytcnt=%d crc=%08X", bytcnt, crc);
|
||||
} while (n && bytcnt < lastcrcrq);
|
||||
crc = ~crc;
|
||||
clearerr(in); /* Clear possible EOF */
|
||||
lastcrcrq = Rxpos;
|
||||
}
|
||||
}
|
||||
stohdr(crc);
|
||||
zsbhdr(ZCRC, Txhdr);
|
||||
@ -441,7 +494,7 @@ again:
|
||||
skipsize = Rxpos;
|
||||
if (fseek(in, Rxpos, 0))
|
||||
return TERROR;
|
||||
Lastsync = (bytcnt = Txpos = Lrxpos = Rxpos) -1;
|
||||
Lastsync = (maxbytcnt = bytcnt = Txpos = Lrxpos = Rxpos) -1;
|
||||
return zsendfdata();
|
||||
}
|
||||
}
|
||||
@ -471,7 +524,8 @@ int zsendfdata(void)
|
||||
junkcount = 0;
|
||||
Beenhereb4 = 0;
|
||||
somemore:
|
||||
if (0) {
|
||||
// if (0) {
|
||||
if (setjmp(intrjmp)) {
|
||||
waitack:
|
||||
junkcount = 0;
|
||||
c = getinsync(0);
|
||||
@ -486,18 +540,18 @@ gotack:
|
||||
return c;
|
||||
case ZACK: Syslog('z', "zmsend: got ZACK");
|
||||
break; // Possible bug, added 23-08-99
|
||||
case ZRPOS: blklen = ((blklen >> 2) > 64) ? (blklen >> 2) : 64;
|
||||
case ZRPOS: /* blklen = ((blklen >> 2) > 64) ? (blklen >> 2) : 64;
|
||||
goodblks = 0;
|
||||
goodneeded = ((goodneeded << 1) > 16) ? 16 : goodneeded << 1;
|
||||
Syslog('z', "zmsend: blocklen now %d", blklen);
|
||||
Syslog('z', "zmsend: blocklen now %d", blklen); */
|
||||
break;
|
||||
case TIMEOUT: /* Put back here 08-09-1999 mb */
|
||||
Syslog('z', "zmsend: zsendfdata TIMEOUT");
|
||||
goto to;
|
||||
case HANGUP: /* New, added 08-09-1999 mb */
|
||||
Syslog('z', "zmsend: zsendfdata HANGUP");
|
||||
fclose(in);
|
||||
return c;
|
||||
// case TIMEOUT: /* Put back here 08-09-1999 mb */
|
||||
// Syslog('z', "zmsend: zsendfdata TIMEOUT");
|
||||
// goto to;
|
||||
// case HANGUP: /* New, added 08-09-1999 mb */
|
||||
// Syslog('z', "zmsend: zsendfdata HANGUP");
|
||||
// fclose(in);
|
||||
// return c;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -520,7 +574,9 @@ gotack:
|
||||
}
|
||||
}
|
||||
}
|
||||
to:
|
||||
//to:
|
||||
|
||||
signal(SIGINT, onintr);
|
||||
newcnt = Rxbuflen;
|
||||
Txwcnt = 0;
|
||||
stohdr(Txpos);
|
||||
@ -544,12 +600,14 @@ to:
|
||||
alarm_on();
|
||||
zsdata(txbuf, n, e);
|
||||
bytcnt = Txpos += n;
|
||||
if (bytcnt > maxbytcnt)
|
||||
maxbytcnt = bytcnt;
|
||||
|
||||
if ((blklen < maxblklen) && (++goodblks > goodneeded)) {
|
||||
blklen = ((blklen << 1) < maxblklen) ? blklen << 1 : maxblklen;
|
||||
goodblks = 0;
|
||||
Syslog('z', "zmsend: blocklen now %d", blklen);
|
||||
}
|
||||
// if ((blklen < maxblklen) && (++goodblks > goodneeded)) {
|
||||
// blklen = ((blklen << 1) < maxblklen) ? blklen << 1 : maxblklen;
|
||||
// goodblks = 0;
|
||||
// Syslog('z', "zmsend: blocklen now %d", blklen);
|
||||
// }
|
||||
|
||||
if (e == ZCRCW)
|
||||
goto waitack;
|
||||
@ -591,6 +649,7 @@ to:
|
||||
Syslog('z', "window = %ld", tcount);
|
||||
}
|
||||
} while (!Eofseen);
|
||||
signal(SIGINT, SIG_IGN);
|
||||
|
||||
for (;;) {
|
||||
stohdr(Txpos);
|
||||
@ -599,6 +658,7 @@ egotack:
|
||||
switch (getinsync(0)) {
|
||||
case ZACK: Syslog('z', "zsendfdata() ZACK");
|
||||
goto egotack; // continue in old source
|
||||
case ZNAK: continue;
|
||||
case ZRPOS: goto somemore;
|
||||
case ZRINIT: fclose(in);
|
||||
return OK;
|
||||
@ -630,10 +690,17 @@ int getinsync(int flag)
|
||||
case ZCAN:
|
||||
case ZABORT:
|
||||
case ZFIN:
|
||||
case TERROR:
|
||||
/* case TERROR: */
|
||||
case TIMEOUT: Syslog('+', "Zmodem: Got %s sending data", frametypes[c+FTOFFSET]);
|
||||
return TERROR;
|
||||
case ZRPOS: /* ************************************* */
|
||||
case ZRPOS: if (Rxpos > bytcnt) {
|
||||
Syslog('z', "Zmodem: getinsync: Rxpos=%lx bytcnt=%lx Maxbytcnt=%lx",
|
||||
Rxpos, bytcnt, maxbytcnt);
|
||||
if (Rxpos > maxbytcnt)
|
||||
Syslog('+', "Nonstandard Protocol at %lX", Rxpos);
|
||||
return ZRPOS;
|
||||
}
|
||||
/* ************************************* */
|
||||
/* If sending to a buffered modem, you */
|
||||
/* might send a break at this point to */
|
||||
/* dump the modem's buffer. */
|
||||
@ -667,6 +734,7 @@ int getinsync(int flag)
|
||||
case ZRINIT: return c;
|
||||
case ZSKIP: Syslog('+', "Zmodem: File skipped by receiver request");
|
||||
return c;
|
||||
case TERROR:
|
||||
default: zsbhdr(ZNAK, Txhdr);
|
||||
continue;
|
||||
}
|
||||
@ -674,3 +742,21 @@ int getinsync(int flag)
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* Set additional control chars to mask in Zsendmask
|
||||
* according to bit array stored in char array at p
|
||||
*/
|
||||
void initzsendmsk(char *p)
|
||||
{
|
||||
int c;
|
||||
|
||||
for (c = 0; c < 33; ++c) {
|
||||
if (p [c >> 3] & (1 << (c & 7))) {
|
||||
Zsendmask[c] = 1;
|
||||
Syslog('z', "Zmodem: escaping %02o", c);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
Reference in New Issue
Block a user