fio.c revision 462be471126495414a94f9fa35e16c02dc462c04
/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License, Version 1.0 only
* (the "License"). You may not use this file except in compliance
* with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2005 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
/*
*
* flow control protocol.
*
* This protocol relies on flow control of the data stream.
* It is meant for working over links that can (almost) be
* A sumcheck is carried out over a whole file only. If a
* transport fails the receiver can request retransmission(s).
* This protocol uses a 7-bit datapath only, so it can be
* used on links that are not 8-bit transparent.
*
* When using this protocol with an X.25 PAD:
* Although this protocol uses no control chars except CR,
* control chars NULL and ^P are used before this protocol
* is started; since ^P is the default char for accessing
* PAD X.28 command mode, be sure to disable that access
* (PAD par 1). Also make sure both flow control pars
* (5 and 12) are set. The CR used in this proto is meant
* to trigger packet transmission, hence par 3 should be
* set to 2; a good value for the Idle Timer (par 4) is 10.
* All other pars should be set to 0.
*
* Normally a calling site will take care of setting the
* local PAD pars via an X.28 command and those of the remote
* PAD via an X.29 command, unless the remote site has a
* special channel assigned for this protocol with the proper
* par settings.
*
* Additional comments for hosts with direct X.25 access:
* - the global variable IsTcpIp, when set, excludes the ioctl's,
* so the same binary can run on X.25 and non-X.25 hosts;
* - reads are done in small chunks, which can be smaller than
* the packet size; your X.25 driver must support that.
*
*
* Author:
* Piet Beertema, CWI, Amsterdam, Sep 1984
* Modified for X.25 hosts:
* Robert Elz, Melbourne Univ, Mar 1985
*/
#include "uucp.h"
#ifdef F_PROTOCOL
extern unsigned msgtime;
/* privates */
* but see comment above
*/
* otherwise make as large as feasible to reduce
* number of write system calls
*/
#ifndef MAXMSGLEN
#endif /* MAXMSGLEN */
static int fchksum;
/* ARGSUSED */
static void
int sig;
{
}
static void (*fsig)();
static int ioctlok;
#ifdef ATTSVTTY
#else
#endif
int
fturnon(void)
{
int ret;
#ifdef ATTSVTTY
struct termio save_ttbuf;
#else
struct sgttyb save_ttbuf;
#endif
#ifdef ATTSVTTY
ioctlok = 1;
save_ttbuf = ttbuf;
ttbuf = save_ttbuf;
}
#else /* !ATTSVTTY */
ioctlok = 1;
save_ttbuf = ttbuf;
ttbuf = save_ttbuf;
}
#endif /* ATTSVTTY */
/* give the other side time to perform its ioctl;
* otherwise it may flush out the first data this
* side is about to send.
*/
sleep(2);
return SUCCESS;
}
int
fturnoff(void)
{
if (ioctlok) {
#ifdef ATTSVTTY
#else
#endif
}
sleep(2);
return SUCCESS;
}
int
char *str;
int fn;
char type;
{
char *s;
s = bufr;
*s++ = type;
while (*str)
*s++ = *str++;
if (*(s-1) == '\n')
s--;
*s++ = '\r';
*s = 0;
return SUCCESS;
}
int
char *str;
int fn;
{
char *smax;
return FAIL;
for (;;) {
goto msgerr;
*str &= 0177;
if (*str == '\r')
break;
if (*str < ' ') {
continue;
}
goto msgerr;
}
*str = '\0';
(void) alarm(0);
return SUCCESS;
(void) alarm(0);
return FAIL;
}
int
int fn;
{
long fbytes;
fchksum = 0xffff;
fbytes = 0L;
ack = '\0';
do {
if (alen <= 0) {
goto acct;
}
}
acct:
if (ack == 'R') {
retries++;
goto retry;
}
return ret;
}
/* max. attempts to retransmit a file: */
int
int fn;
{
int flen;
char eof;
fchksum = 0xffff;
fbytes = 0L;
do {
if (flen < 0)
goto acct;
goto acct;
} while (!eof);
acct:
if (retries++ < MAXRETRIES) {
goto retry;
}
}
else {
}
return ret;
}
static int
char *blk;
int len;
int fn;
{
return FAIL;
alarm(0);
}
#if !defined(ATTSVKILL)
/* call ultouch every TC calls to either frdblk or fwrblk */
#define TC 20
#endif /* !defined(ATTSVKILL) */
/* Byte conversion:
*
* from pre to
* 000-037 172 100-137
* 040-171 040-171
* 172-177 173 072-077
* 200-237 174 100-137
* 240-371 175 040-171
* 372-377 176 072-077
*/
static int
int fn;
int *lenp;
{
char *op;
int ret;
#if !defined(ATTSVKILL)
/* call ultouch occasionally */
if (--tc < 0) {
ultouch();
}
#endif /*!defined(ATTSVKILL)*/
nl = 0;
len = 0;
len++;
if (sum & 0x8000) {
sum <<= 1;
sum++;
} else
sum <<= 1;
sum += c;
sum &= 0xffff;
if (c & 0200) {
c &= 0177;
if (c < 040) {
*op++ = '\174';
*op++ = c + 0100;
} else
if (c <= 0171) {
*op++ = '\175';
*op++ = c;
}
else {
*op++ = '\176';
*op++ = c - 0100;
}
nl += 2;
} else {
if (c < 040) {
*op++ = '\172';
*op++ = c + 0100;
nl += 2;
} else
if (c <= 0171) {
*op++ = c;
nl++;
} else {
*op++ = '\173';
*op++ = c - 0100;
nl += 2;
}
}
/*
* peek at next char, see if it will fit
*/
if (c == EOF)
break;
goto writeit;
}
}
/*
* At EOF - append checksum, there is space for it...
*/
}
static int
char *ip;
int fn;
long *rlen;
{
char *op, c;
int i;
static char special = 0;
#if !defined(ATTSVKILL)
/* call ultouch occasionally */
if (--tc < 0) {
ultouch();
}
#endif /*!defined(ATTSVKILL)*/
*rlen = 0;
goto dcorr;
}
nl = 0;
do {
if (special) {
special = 0;
goto dcorr;
while (i--)
while (len < 5) {
if (i == FAIL) {
goto dcorr;
}
len += i;
*rlen += i;
while (i--)
*op++ &= 0177;
}
goto dcorr;
else {
return FAIL;
}
}
} else {
if (*ip < '\040') {
/* error: shouldn't get control chars */
goto dcorr;
}
switch (special) {
case 0:
c = *ip++;
break;
case '\172':
c = *ip++ - 0100;
break;
case '\173':
c = *ip++ + 0100;
break;
case '\174':
c = *ip++ + 0100;
break;
case '\175':
c = *ip++ + 0200;
break;
case '\176':
c = *ip++ + 0300;
break;
}
*op++ = c;
if (sum & 0x8000) {
sum <<= 1;
sum++;
} else
sum <<= 1;
sum += c & 0377;
sum &= 0xffff;
special = 0;
nl++;
}
} while (--len);
return nl;
}
return FAIL;
}
#endif /* F_PROTOCOL */