Update to 4.4-Lite networking code, with a few local changes.
This commit is contained in:
parent
13e5e05cdb
commit
c427e65091
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)argo_debug.h 7.4 (Berkeley) 5/6/91
|
||||
* $Id: argo_debug.h,v 1.3 1993/05/20 05:26:42 cgd Exp $
|
||||
* from: @(#)argo_debug.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: argo_debug.h,v 1.4 1994/05/13 06:08:03 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ARGO_DEBUG_H_
|
||||
#define _NETISO_ARGO_DEBUG_H_
|
||||
|
||||
/*****************************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,6 +61,9 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ARGO_DEBUG_H_
|
||||
#define _NETISO_ARGO_DEBUG_H_
|
||||
|
||||
#define dump_buf(a, b) Dump_buf((caddr_t)(a), (int)(b))
|
||||
|
||||
/***********************************************
|
||||
@ -74,14 +74,14 @@ SOFTWARE.
|
||||
* lint can't handle the flaky vacuous definitions
|
||||
* of IFDEBUG, ENDDEBUG, etc.
|
||||
*/
|
||||
#endif defined(lint)
|
||||
#endif /* defined(lint) */
|
||||
|
||||
/***********************************************
|
||||
* DEBUG ON:
|
||||
**********************************************/
|
||||
#ifndef ARGO_DEBUG
|
||||
#define ARGO_DEBUG
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
|
||||
#ifdef ARGO_DEBUG
|
||||
@ -101,7 +101,7 @@ unsigned char argo_debug[128];
|
||||
if(argo_debug[ascii]) {
|
||||
#define ENDDEBUG ; }
|
||||
|
||||
#else ARGO_DEBUG
|
||||
#else /* ARGO_DEBUG */
|
||||
|
||||
/***********************************************
|
||||
* DEBUG OFF:
|
||||
@ -109,11 +109,11 @@ unsigned char argo_debug[128];
|
||||
|
||||
#ifndef STAR
|
||||
#define STAR *
|
||||
#endif STAR
|
||||
#endif /* STAR */
|
||||
#define IFDEBUG(ascii) //*beginning of comment*/STAR
|
||||
#define ENDDEBUG STAR/*end of comment*//
|
||||
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
/***********************************************
|
||||
* ASSERT
|
||||
@ -123,15 +123,15 @@ unsigned char argo_debug[128];
|
||||
#ifndef lint
|
||||
#define ASSERT(phrase) \
|
||||
if( !(phrase) ) printf("ASSERTION NOT VALID at line %d file %s\n",__LINE__,__FILE__)
|
||||
#else lint
|
||||
#else /* lint */
|
||||
#define ASSERT(phrase) /* phrase */
|
||||
#endif lint
|
||||
#endif /* lint */
|
||||
|
||||
#else ARGO_DEBUG
|
||||
#else /* ARGO_DEBUG */
|
||||
|
||||
#define ASSERT(phrase) /* phrase */
|
||||
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
|
||||
/***********************************************
|
||||
@ -275,7 +275,7 @@ void dump_mbuf();
|
||||
#define TPMT_PCB 0x23
|
||||
#define TPMT_PERF 0x45
|
||||
|
||||
#else ARGO_DEBUG
|
||||
#else /* ARGO_DEBUG */
|
||||
|
||||
#define TPMT_DATA MT_DATA
|
||||
#define TPMT_RCVRTC MT_DATA
|
||||
@ -288,6 +288,6 @@ void dump_mbuf();
|
||||
#define TPMT_PCB MT_PCB
|
||||
#define TPMT_PERF MT_PCB
|
||||
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
#endif /* !_NETISO_ARGO_DEBUG_H_ */
|
||||
#endif /* _NETISO_ARGO_DEBUG_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnl.h 7.3 (Berkeley) 5/6/91
|
||||
* $Id: clnl.h,v 1.3 1993/05/20 05:26:44 cgd Exp $
|
||||
* from: @(#)clnl.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnl.h,v 1.4 1994/05/13 06:08:05 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_CLNL_H_
|
||||
#define _NETISO_CLNL_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,7 +61,5 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
struct clnl_protosw {
|
||||
int (*clnl_input)(); /* input routine */
|
||||
void (*clnl_input)(); /* input routine */
|
||||
};
|
||||
|
||||
#endif /* !_NETISO_CLNL_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993, 1994
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp.h 7.8 (Berkeley) 5/6/91
|
||||
* $Id: clnp.h,v 1.4 1994/04/12 08:15:38 cgd Exp $
|
||||
* from: @(#)clnp.h 8.2 (Berkeley) 4/16/94
|
||||
* $Id: clnp.h,v 1.5 1994/05/13 06:08:07 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_CLNP_H_
|
||||
#define _NETISO_CLNP_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -279,12 +276,13 @@ struct clnp_optidx {
|
||||
#define CLNP_NO_ER 0x020 /* do not generate ERs */
|
||||
#define CLNP_SEND_RAW 0x080 /* send pkt as RAW DT rather than TP DT */
|
||||
#define CLNP_NO_CKSUM 0x100 /* don't use clnp checksum */
|
||||
#define CLNP_ECHO 0x200 /* fake echo function */
|
||||
#define CLNP_ECHO 0x200 /* send echo request */
|
||||
#define CLNP_NOCACHE 0x400 /* don't store cache information */
|
||||
#define CLNP_ECHOR 0x800 /* send echo reply */
|
||||
|
||||
/* valid clnp flags */
|
||||
#define CLNP_VFLAGS (CLNP_SEND_RAW|CLNP_NO_SEG|CLNP_NO_ER|CLNP_NO_CKSUM\
|
||||
|CLNP_ECHO|CLNP_NOCACHE)
|
||||
|CLNP_ECHO|CLNP_NOCACHE|CLNP_ECHOR)
|
||||
|
||||
/*
|
||||
* Constants used by clnp
|
||||
@ -401,7 +399,7 @@ extern float troll_random;
|
||||
#define SN_MTU(ifp, rt) (((rt && rt->rt_rmx.rmx_mtu) ?\
|
||||
rt->rt_rmx.rmx_mtu : clnp_badmtu(ifp, rt, __LINE__, __FILE__)))
|
||||
|
||||
#endif TROLL
|
||||
#endif /* TROLL */
|
||||
|
||||
/*
|
||||
* Macro to remove an address from a clnp header
|
||||
@ -460,7 +458,5 @@ struct iso_addr *clnp_srcaddr();
|
||||
struct mbuf *clnp_reass();
|
||||
#ifdef TROLL
|
||||
struct troll trollctl;
|
||||
#endif TROLL
|
||||
#endif KERNEL
|
||||
|
||||
#endif /* !_NETISO_CLNP_H_ */
|
||||
#endif /* TROLL */
|
||||
#endif /* KERNEL */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_debug.c 7.8 (Berkeley) 5/27/91
|
||||
* $Id: clnp_debug.c,v 1.3 1993/12/18 00:42:25 mycroft Exp $
|
||||
* from: @(#)clnp_debug.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_debug.c,v 1.4 1994/05/13 06:08:10 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,7 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/domain.h>
|
||||
@ -90,7 +89,7 @@ struct addr_osinet u_osinet = {
|
||||
{0x00, 0x04},
|
||||
{0x00, 0x02, 0x00, 0x01, 0x23, 0x42, 0x78, 0x20, 0x01, 0x05, 0x00}
|
||||
};
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
struct addr_rfc986 u_rfc986 = {
|
||||
{0x00, 0x06},
|
||||
{0x01, 0xc0, 0x0c, 0x0c, 0xab, 0x11}
|
||||
@ -129,7 +128,7 @@ main()
|
||||
a.isoa_len = 9;
|
||||
printf("type bad idi: %s\n", clnp_iso_addrp(&a));
|
||||
}
|
||||
#endif TESTDEBUG
|
||||
#endif /* TESTDEBUG */
|
||||
|
||||
unsigned int clnp_debug;
|
||||
static char letters[] = "0123456789abcdef";
|
||||
@ -141,14 +140,15 @@ static char letters[] = "0123456789abcdef";
|
||||
char *
|
||||
clnp_hexp(src, len, where)
|
||||
char *src; /* src of data to print */
|
||||
int len; /* lengthof src */
|
||||
int len; /* lengthof src */
|
||||
char *where; /* where to put data */
|
||||
{
|
||||
int i;
|
||||
|
||||
for (i=0; i<len; i++) {
|
||||
*where++ = letters[src[i] >> 4];
|
||||
*where++ = letters[src[i] & 0x0f];
|
||||
register int j = ((u_char *)src)[i];
|
||||
*where++ = letters[j >> 4];
|
||||
*where++ = letters[j & 0x0f];
|
||||
}
|
||||
return where;
|
||||
}
|
||||
@ -227,7 +227,7 @@ struct iso_addr *isoa;
|
||||
cp = clnp_hexp(&o986->o986_inetaddr[3], 1, cp);
|
||||
*cp++ = DELIM;
|
||||
cp = clnp_hexp(&o986->o986_upid, 1, cp);
|
||||
#endif vax
|
||||
#endif /* vax */
|
||||
}
|
||||
|
||||
} break;
|
||||
@ -236,7 +236,7 @@ struct iso_addr *isoa;
|
||||
*cp++ = '?';
|
||||
break;
|
||||
}
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
*cp = (char)0;
|
||||
|
||||
return(iso_addr_b);
|
||||
@ -256,4 +256,4 @@ register struct sockaddr_iso *s;
|
||||
return (iso_addr_b);
|
||||
}
|
||||
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_er.c 7.7 (Berkeley) 5/6/91
|
||||
* $Id: clnp_er.c,v 1.3 1993/12/18 00:42:29 mycroft Exp $
|
||||
* from: @(#)clnp_er.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_er.c,v 1.4 1994/05/13 06:08:12 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_frag.c 7.12 (Berkeley) 5/6/91
|
||||
* $Id: clnp_frag.c,v 1.3 1993/12/18 00:42:32 mycroft Exp $
|
||||
* from: @(#)clnp_frag.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_frag.c,v 1.4 1994/05/13 06:08:13 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -62,6 +62,7 @@ SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/domain.h>
|
||||
#include <sys/protosw.h>
|
||||
@ -242,7 +243,7 @@ struct rtentry *rt; /* route if direct ether */
|
||||
error = troll_output(ifp, frag_hdr, first_hop, rt);
|
||||
#else
|
||||
error = (*ifp->if_output)(ifp, frag_hdr, first_hop, rt);
|
||||
#endif TROLL
|
||||
#endif /* TROLL */
|
||||
|
||||
/*
|
||||
* Tough situation: if the error occured on the last
|
||||
@ -281,7 +282,7 @@ struct rtentry *rt; /* route if direct ether */
|
||||
num_bytes *= troll_random();
|
||||
frag_size -= num_bytes;
|
||||
}
|
||||
#endif TROLL
|
||||
#endif /* TROLL */
|
||||
total_len -= frag_size;
|
||||
if (!last_frag) {
|
||||
frag_base += frag_size;
|
||||
@ -854,4 +855,4 @@ struct rtentry *rt;
|
||||
}
|
||||
}
|
||||
|
||||
#endif TROLL
|
||||
#endif /* TROLL */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_input.c 7.13 (Berkeley) 5/6/91
|
||||
* $Id: clnp_input.c,v 1.5 1994/01/04 08:13:28 cgd Exp $
|
||||
* from: @(#)clnp_input.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_input.c,v 1.6 1994/05/13 06:08:15 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,7 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/domain.h>
|
||||
@ -94,13 +93,10 @@ struct clnl_protosw clnl_protox[256];
|
||||
int clnpqmaxlen = IFQ_MAXLEN; /* RAH? why is this a variable */
|
||||
struct mbuf *clnp_data_ck();
|
||||
|
||||
int clnp_input();
|
||||
|
||||
int esis_input();
|
||||
|
||||
void clnp_input(), esis_input();
|
||||
#ifdef ISO_X25ESIS
|
||||
int x25esis_input();
|
||||
#endif ISO_X25ESIS
|
||||
void x25esis_input();
|
||||
#endif /* ISO_X25ESIS */
|
||||
|
||||
/*
|
||||
* FUNCTION: clnp_init
|
||||
@ -114,6 +110,7 @@ int x25esis_input();
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
void
|
||||
clnp_init()
|
||||
{
|
||||
register struct protosw *pr;
|
||||
@ -279,6 +276,7 @@ next:
|
||||
* TODO: I would like to make seg_part a pointer into the mbuf, but
|
||||
* will it be correctly aligned?
|
||||
*/
|
||||
void
|
||||
clnp_input(m, shp)
|
||||
struct mbuf *m; /* ptr to first mbuf of pkt */
|
||||
struct snpa_hdr *shp; /* subnetwork header */
|
||||
@ -436,7 +434,7 @@ struct snpa_hdr *shp; /* subnetwork header */
|
||||
if (need_afrin)
|
||||
INCSTAT(cns_congest_rcvd);
|
||||
}
|
||||
#endif DECBIT
|
||||
#endif /* DECBIT */
|
||||
|
||||
if (errcode != 0) {
|
||||
clnp_discard(m, (char)errcode);
|
||||
@ -534,60 +532,9 @@ struct snpa_hdr *shp; /* subnetwork header */
|
||||
IFDEBUG(D_INPUT)
|
||||
printf("clnp_input: echoing packet\n");
|
||||
ENDDEBUG
|
||||
{
|
||||
/*
|
||||
* Echo whole datagram in a new datagram, as per RFC 1139
|
||||
* and ISO/IEC 8473-1, 2nd edition.
|
||||
*/
|
||||
static struct clnp_fixed ecr_template = {
|
||||
ISO8473_CLNP, /* network identifier */
|
||||
0, /* length */
|
||||
ISO8473_V1, /* version */
|
||||
CLNP_TTL, /* ttl */
|
||||
CLNP_ECR|CNF_SEG_OK,/* type & flags */
|
||||
0, /* segment length */
|
||||
0 /* checksum */
|
||||
};
|
||||
struct clnp_segment *seg;
|
||||
register struct mbuf *mnew;
|
||||
|
||||
/* Get header */
|
||||
MGETHDR(mnew, M_DONTWAIT, MT_HEADER);
|
||||
if (mnew == 0) {
|
||||
m_freem(m);
|
||||
INCSTAT(cns_odropped);
|
||||
return;
|
||||
}
|
||||
mnew->m_next = m; /* chain in old datagram */
|
||||
|
||||
/* construct new CLNP PDU header */
|
||||
clnp = mtod(mnew, struct clnp_fixed *);
|
||||
*clnp = ecr_template;
|
||||
hoff = (caddr_t)clnp + sizeof(struct clnp_fixed);
|
||||
|
||||
/* Insert addresses in reverse order from original PDU */
|
||||
CLNP_INSERT_ADDR(hoff, src);
|
||||
CLNP_INSERT_ADDR(hoff, dst);
|
||||
/* Insert empty segmentation part */
|
||||
seg = (struct clnp_segment*) hoff;
|
||||
bzero((caddr_t)seg, sizeof(struct clnp_segment));
|
||||
/* increment offset accordingly */
|
||||
hoff += sizeof(struct clnp_segment);
|
||||
|
||||
/* Calculate length */
|
||||
clnp->cnf_hdr_len = mnew->m_len = (u_char)(hoff - (caddr_t)clnp);
|
||||
seg_len += clnp->cnf_hdr_len;
|
||||
/* Stuff in packet at various places... */
|
||||
seg->cng_tot_len = seg_len;
|
||||
clnp->cnf_seglen_msb = (seg_len & 0xff00) >> 8;
|
||||
clnp->cnf_seglen_lsb = (seg_len & 0x00ff);
|
||||
|
||||
/*
|
||||
* Forward (umm... really send new PDU) back to sender
|
||||
*/
|
||||
clnp_forward(mnew, (int)seg_len, &src, (struct clnp_optidx *)0,
|
||||
/*seg_off*/0, (struct snpa_hdr *)0);
|
||||
}
|
||||
(void)clnp_echoreply(m,
|
||||
(clnp->cnf_type & CNF_SEG_OK ? (int)seg_part.cng_tot_len : seg_len),
|
||||
&source, &target, oidxp);
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -599,4 +546,4 @@ struct snpa_hdr *shp; /* subnetwork header */
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_options.c 7.8 (Berkeley) 5/6/91
|
||||
* $Id: clnp_options.c,v 1.3 1993/12/18 00:42:36 mycroft Exp $
|
||||
* from: @(#)clnp_options.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_options.c,v 1.4 1994/05/13 06:08:17 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -63,7 +63,6 @@ SOFTWARE.
|
||||
|
||||
#ifdef ISO
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/domain.h>
|
||||
@ -529,4 +528,4 @@ struct clnp_optidx *oidx; /* RETURN: filled in with option idx info */
|
||||
ENDDEBUG
|
||||
return(0);
|
||||
}
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_output.c 7.10 (Berkeley) 5/6/91
|
||||
* $Id: clnp_output.c,v 1.3 1993/12/18 00:42:38 mycroft Exp $
|
||||
* from: @(#)clnp_output.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_output.c,v 1.4 1994/05/13 06:08:20 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -110,10 +110,20 @@ static struct clnp_fixed echo_template = {
|
||||
0 /* checksum */
|
||||
};
|
||||
|
||||
static struct clnp_fixed echor_template = {
|
||||
ISO8473_CLNP, /* network identifier */
|
||||
0, /* length */
|
||||
ISO8473_V1, /* version */
|
||||
CLNP_TTL, /* ttl */
|
||||
CLNP_ECR|CNF_SEG_OK|CNF_ERR_OK, /* type */
|
||||
0, /* segment length */
|
||||
0 /* checksum */
|
||||
};
|
||||
|
||||
#ifdef DECBIT
|
||||
u_char qos_option[] = {CLNPOVAL_QOS, 1,
|
||||
CLNPOVAL_GLOBAL|CLNPOVAL_SEQUENCING|CLNPOVAL_LOWDELAY};
|
||||
#endif DECBIT
|
||||
#endif /* DECBIT */
|
||||
|
||||
int clnp_id = 0; /* id for segmented dgrams */
|
||||
|
||||
@ -370,6 +380,8 @@ int flags; /* flags */
|
||||
*clnp = raw_template;
|
||||
} else if (flags & CLNP_ECHO) {
|
||||
*clnp = echo_template;
|
||||
} else if (flags & CLNP_ECHOR) {
|
||||
*clnp = echor_template;
|
||||
} else {
|
||||
*clnp = dt_template;
|
||||
}
|
||||
@ -453,7 +465,7 @@ int flags; /* flags */
|
||||
hdrlen += sizeof(qos_option);
|
||||
m->m_len += sizeof(qos_option);
|
||||
}
|
||||
#endif DECBIT
|
||||
#endif /* DECBIT */
|
||||
|
||||
/*
|
||||
* If an options mbuf is present, concatenate a copy to the hdr mbuf.
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_raw.c 7.8 (Berkeley) 5/6/91
|
||||
* $Id: clnp_raw.c,v 1.3 1993/12/18 00:42:46 mycroft Exp $
|
||||
* from: @(#)clnp_raw.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_raw.c,v 1.4 1994/05/13 06:08:22 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -80,7 +80,7 @@ SOFTWARE.
|
||||
#include <netiso/clnp_stat.h>
|
||||
#include <netiso/argo_debug.h>
|
||||
|
||||
#include <netiso/tp_user.h>/* XXX -- defines SOL_NETWORK */
|
||||
#include <netiso/tp_user.h> /* XXX -- defines SOL_NETWORK */
|
||||
|
||||
struct sockproto rclnp_proto = { PF_ISO, 0 };
|
||||
/*
|
||||
@ -97,6 +97,7 @@ struct sockproto rclnp_proto = { PF_ISO, 0 };
|
||||
* NOTES: The protocol field of rclnp_proto is set to zero indicating
|
||||
* no protocol.
|
||||
*/
|
||||
void
|
||||
rclnp_input(m, src, dst, hdrlen)
|
||||
struct mbuf *m; /* ptr to packet */
|
||||
struct sockaddr_iso *src; /* ptr to src address */
|
||||
@ -108,13 +109,9 @@ int hdrlen; /* length (in bytes) of clnp header */
|
||||
m_freem(m);
|
||||
return;
|
||||
}
|
||||
#endif TROLL
|
||||
#endif /* TROLL */
|
||||
|
||||
if (raw_input(m, &rclnp_proto, (struct sockaddr *)src,
|
||||
(struct sockaddr *)dst) == 0) {
|
||||
clnp_stat.cns_delivered--;
|
||||
clnp_stat.cns_noproto++;
|
||||
}
|
||||
raw_input(m, &rclnp_proto, (struct sockaddr *)src, (struct sockaddr *)dst);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -141,7 +138,7 @@ struct socket *so; /* socket to send from */
|
||||
int error; /* return value of function */
|
||||
int flags; /* flags for clnp_output */
|
||||
|
||||
if (0 == m0->m_flags & M_PKTHDR)
|
||||
if (0 == (m0->m_flags & M_PKTHDR))
|
||||
return (EINVAL);
|
||||
/*
|
||||
* Set up src address. If user has bound socket to an address, use it.
|
||||
@ -209,7 +206,7 @@ struct mbuf **m; /* ptr to ptr to option data */
|
||||
else switch (op) {
|
||||
#else
|
||||
switch (op) {
|
||||
#endif SOL_NETWORK
|
||||
#endif /* SOL_NETWORK */
|
||||
case PRCO_SETOPT:
|
||||
switch (optname) {
|
||||
case CLNPOPT_FLAGS: {
|
||||
@ -255,7 +252,7 @@ struct mbuf **m; /* ptr to ptr to option data */
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
break;
|
||||
default:
|
||||
error = EINVAL;
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_stat.h 7.4 (Berkeley) 5/6/91
|
||||
* $Id: clnp_stat.h,v 1.3 1993/05/20 05:26:56 cgd Exp $
|
||||
* from: @(#)clnp_stat.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_stat.h,v 1.4 1994/05/13 06:08:24 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_CLNP_STAT_H_
|
||||
#define _NETISO_CLNP_STAT_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,6 +61,9 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_CLNP_STAT_H_
|
||||
#define _NETISO_CLNP_STAT_H_
|
||||
|
||||
struct clnp_stat {
|
||||
int cns_total; /* total pkts received */
|
||||
int cns_toosmall; /* fixed part of header too small */
|
||||
@ -95,7 +95,7 @@ struct clnp_stat {
|
||||
|
||||
#ifdef INCSTAT
|
||||
#undef INCSTAT
|
||||
#endif INCSTAT
|
||||
#endif /* INCSTAT */
|
||||
#define INCSTAT(x) clnp_stat./**/x/**/++
|
||||
|
||||
#endif /* !_NETISO_CLNP_STAT_H_ */
|
||||
#endif /* _NETISO_CLNP_STAT_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_subr.c 7.13 (Berkeley) 5/6/91
|
||||
* $Id: clnp_subr.c,v 1.3 1993/12/18 00:42:51 mycroft Exp $
|
||||
* from: @(#)clnp_subr.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_subr.c,v 1.4 1994/05/13 06:08:26 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -63,7 +63,6 @@ SOFTWARE.
|
||||
|
||||
#ifdef ISO
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/domain.h>
|
||||
@ -184,7 +183,7 @@ register struct iso_addr *destp; /* ptr to destination address buffer */
|
||||
else
|
||||
return (caddr_t) 0;
|
||||
}
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
|
||||
/*
|
||||
* FUNCTION: clnp_ours
|
||||
@ -363,7 +362,7 @@ struct snpa_hdr *inbound_shp; /* subnetwork header of inbound packet */
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif DECBIT
|
||||
#endif /* DECBIT */
|
||||
|
||||
/*
|
||||
* Dispatch the datagram if it is small enough, otherwise fragment
|
||||
@ -413,7 +412,7 @@ register struct iso_addr *dstp; /* ptr to dst addr */
|
||||
return bufp;
|
||||
}
|
||||
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
|
||||
/*
|
||||
* FUNCTION: clnp_route
|
||||
@ -576,6 +575,42 @@ struct iso_addr *final_dst; /* final destination */
|
||||
return error;
|
||||
}
|
||||
|
||||
/*
|
||||
* FUNCTION: clnp_echoreply
|
||||
*
|
||||
* PURPOSE: generate an echo reply packet and transmit
|
||||
*
|
||||
* RETURNS: result of clnp_output
|
||||
*
|
||||
* SIDE EFFECTS:
|
||||
*/
|
||||
clnp_echoreply(ec_m, ec_len, ec_src, ec_dst, ec_oidxp)
|
||||
struct mbuf *ec_m; /* echo request */
|
||||
int ec_len; /* length of ec */
|
||||
struct sockaddr_iso *ec_src; /* src of ec */
|
||||
struct sockaddr_iso *ec_dst; /* destination of ec (i.e., us) */
|
||||
struct clnp_optidx *ec_oidxp; /* options index to ec packet */
|
||||
{
|
||||
struct isopcb isopcb;
|
||||
int flags = CLNP_NOCACHE|CLNP_ECHOR;
|
||||
int ret;
|
||||
|
||||
/* fill in fake isopcb to pass to output function */
|
||||
bzero(&isopcb, sizeof(isopcb));
|
||||
isopcb.isop_laddr = ec_dst;
|
||||
isopcb.isop_faddr = ec_src;
|
||||
|
||||
/* forget copying the options for now. If implemented, need only
|
||||
* copy record route option, but it must be reset to zero length */
|
||||
|
||||
ret = clnp_output(ec_m, &isopcb, ec_len, flags);
|
||||
|
||||
IFDEBUG(D_OUTPUT)
|
||||
printf("clnp_echoreply: output returns %d\n", ret);
|
||||
ENDDEBUG
|
||||
return ret;
|
||||
}
|
||||
|
||||
/*
|
||||
* FUNCTION: clnp_badmtu
|
||||
*
|
||||
@ -591,10 +626,10 @@ struct rtentry *rt; /* dst route */
|
||||
int line; /* where the dirty deed occured */
|
||||
char *file; /* where the dirty deed occured */
|
||||
{
|
||||
printf("sending on route %x with no mtu, line %s of file %s\n",
|
||||
printf("sending on route 0x%x with no mtu, line %d of file %s\n",
|
||||
rt, line, file);
|
||||
#ifdef ARGO_DEBUG
|
||||
printf("route dst is");
|
||||
printf("route dst is ");
|
||||
dump_isoaddr(rt_key(rt));
|
||||
#endif
|
||||
return ifp->if_mtu;
|
||||
@ -619,4 +654,4 @@ u_int len; /* number of bytes */
|
||||
while (len--)
|
||||
*(to + len) = *(from + len);
|
||||
}
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)clnp_timer.c 7.5 (Berkeley) 5/6/91
|
||||
* $Id: clnp_timer.c,v 1.3 1993/12/18 00:42:54 mycroft Exp $
|
||||
* from: @(#)clnp_timer.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: clnp_timer.c,v 1.4 1994/05/13 06:08:28 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -142,6 +142,7 @@ register struct clnp_fragl *cfh; /* fragment header to delete */
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
void
|
||||
clnp_slowtimo()
|
||||
{
|
||||
register struct clnp_fragl *cfh = clnp_frags;
|
||||
@ -170,6 +171,7 @@ clnp_slowtimo()
|
||||
* NOTES:
|
||||
* TODO: should send back ER
|
||||
*/
|
||||
void
|
||||
clnp_drain()
|
||||
{
|
||||
register struct clnp_fragl *cfh = clnp_frags;
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 1989 Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1989, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)cltp_usrreq.c 7.6 (Berkeley) 6/27/91
|
||||
* $Id: cltp_usrreq.c,v 1.3 1993/12/18 00:42:56 mycroft Exp $
|
||||
* from: @(#)cltp_usrreq.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: cltp_usrreq.c,v 1.4 1994/05/13 06:08:30 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef CLTPOVAL_SRC /* XXX -- till files gets changed */
|
||||
@ -59,6 +59,7 @@
|
||||
* CLTP protocol implementation.
|
||||
* Per ISO 8602, December, 1987.
|
||||
*/
|
||||
void
|
||||
cltp_init()
|
||||
{
|
||||
|
||||
@ -69,6 +70,7 @@ int cltp_cksum = 1;
|
||||
|
||||
|
||||
/* ARGUSED */
|
||||
void
|
||||
cltp_input(m0, srcsa, dstsa, cons_channel, output)
|
||||
struct mbuf *m0;
|
||||
struct sockaddr *srcsa, *dstsa;
|
||||
@ -148,7 +150,6 @@ bad:
|
||||
m_freem(dtom(src));
|
||||
if (m0)
|
||||
m_freem(m0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -163,6 +164,7 @@ cltp_notify(isop)
|
||||
sowwakeup(isop->isop_socket);
|
||||
}
|
||||
|
||||
void
|
||||
cltp_ctlinput(cmd, sa)
|
||||
int cmd;
|
||||
struct sockaddr *sa;
|
||||
@ -250,12 +252,6 @@ bad:
|
||||
return (error);
|
||||
}
|
||||
|
||||
#ifndef TP_LOCAL
|
||||
/* XXXX should go in iso.h maybe? from tp_param.h, in any case */
|
||||
#define TP_LOCAL 22
|
||||
#define TP_FOREIGN 33
|
||||
#endif
|
||||
|
||||
u_long cltp_sendspace = 9216; /* really max datagram size */
|
||||
u_long cltp_recvspace = 40 * (1024 + sizeof(struct sockaddr_iso));
|
||||
/* 40 1K datagrams */
|
||||
@ -267,7 +263,7 @@ cltp_usrreq(so, req, m, nam, control)
|
||||
int req;
|
||||
struct mbuf *m, *nam, *control;
|
||||
{
|
||||
struct isopcb *isop = sotoisopcb(so);
|
||||
register struct isopcb *isop = sotoisopcb(so);
|
||||
int s, error = 0;
|
||||
|
||||
if (req == PRU_CONTROL)
|
||||
@ -371,11 +367,15 @@ cltp_usrreq(so, req, m, nam, control)
|
||||
break;
|
||||
|
||||
case PRU_SOCKADDR:
|
||||
iso_getnetaddr(isop, nam, TP_LOCAL);
|
||||
if (isop->isop_laddr)
|
||||
bcopy((caddr_t)isop->isop_laddr, mtod(m, caddr_t),
|
||||
nam->m_len = isop->isop_laddr->siso_len);
|
||||
break;
|
||||
|
||||
case PRU_PEERADDR:
|
||||
iso_getnetaddr(isop, nam, TP_FOREIGN);
|
||||
if (isop->isop_faddr)
|
||||
bcopy((caddr_t)isop->isop_faddr, mtod(m, caddr_t),
|
||||
nam->m_len = isop->isop_faddr->siso_len);
|
||||
break;
|
||||
|
||||
case PRU_SENSE:
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*
|
||||
* Copyright (c) 1989 Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1989, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)cltp_var.h 7.3 (Berkeley) 6/28/90
|
||||
* $Id: cltp_var.h,v 1.3 1993/05/20 05:27:01 cgd Exp $
|
||||
* from: @(#)cltp_var.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: cltp_var.h,v 1.4 1994/05/13 06:08:31 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_CLTP_VAR_H_
|
||||
#define _NETISO_CLTP_VAR_H_
|
||||
|
||||
#define UD_TPDU_type 0x40 /* packet type */
|
||||
|
||||
#define CLTPOVAL_SRC 0xc1 /* Source TSAP -- required */
|
||||
@ -56,5 +53,3 @@ struct cltpstat {
|
||||
struct isopcb cltb;
|
||||
struct cltpstat cltpstat;
|
||||
#endif
|
||||
|
||||
#endif /* !_NETISO_CLTP_VAR_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)cons.h 7.3 (Berkeley) 5/6/91
|
||||
* $Id: cons.h,v 1.3 1993/05/20 05:27:02 cgd Exp $
|
||||
* from: @(#)cons.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: cons.h,v 1.4 1994/05/13 06:08:33 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_CONS_H_
|
||||
#define _NETISO_CONS_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -85,11 +82,9 @@ struct dte_addr {
|
||||
#define CONS_NOT_DGM 0x0
|
||||
|
||||
#ifndef PRC_NCMDS
|
||||
#include "protosw.h"
|
||||
#endif PRC_NCMDS
|
||||
#include <sys/protosw.h>
|
||||
#endif /* PRC_NCMDS */
|
||||
|
||||
#define PRC_CONS_SEND_DONE 2 /* something unused in protosw.h */
|
||||
|
||||
#endif KERNEL
|
||||
|
||||
#endif /* !_NETISO_CONS_H_ */
|
||||
#endif /* KERNEL */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)cons_pcb.h 7.4 (Berkeley) 5/6/91
|
||||
* $Id: cons_pcb.h,v 1.3 1993/05/20 05:27:04 cgd Exp $
|
||||
* from: @(#)cons_pcb.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: cons_pcb.h,v 1.4 1994/05/13 06:08:34 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_CONS_PCB_H_
|
||||
#define _NETISO_CONS_PCB_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -80,9 +77,9 @@ SOFTWARE.
|
||||
|
||||
#ifndef ARGO_DEBUG
|
||||
#define X25_TTL 600 /* 5 min */
|
||||
#else ARGO_DEBUG
|
||||
#else /* ARGO_DEBUG */
|
||||
#define X25_TTL 120 /* 1 min */
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
struct cons_pcb {
|
||||
struct isopcb _co_isopcb;
|
||||
@ -192,6 +189,4 @@ struct e_clear_data {
|
||||
|
||||
#ifdef KERNEL
|
||||
#define IncStat(XYZ) cons_stat.XYZ++
|
||||
#endif KERNEL
|
||||
|
||||
#endif /* !_NETISO_CONS_PCB_H_ */
|
||||
#endif /* KERNEL */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)eonvar.h 7.5 (Berkeley) 5/6/91
|
||||
* $Id: eonvar.h,v 1.3 1993/05/20 05:27:05 cgd Exp $
|
||||
* from: @(#)eonvar.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: eonvar.h,v 1.4 1994/05/13 06:08:36 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_EONVAR_H_
|
||||
#define _NETISO_EONVAR_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -172,5 +169,3 @@ struct eon_llinfo {
|
||||
};
|
||||
#define el_iphdr el_ei.ei_ip
|
||||
#define el_eonhdr el_ei.ei_eh
|
||||
|
||||
#endif /* !_NETISO_EONVAR_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)esis.c 7.19 (Berkeley) 6/27/91
|
||||
* $Id: esis.c,v 1.4 1993/12/18 00:42:59 mycroft Exp $
|
||||
* from: @(#)esis.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: esis.c,v 1.5 1994/05/13 06:08:39 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -63,7 +63,6 @@ SOFTWARE.
|
||||
|
||||
#ifdef ISO
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/mbuf.h>
|
||||
@ -118,6 +117,12 @@ extern char all_es_snpa[], all_is_snpa[];
|
||||
(m) = (m)->m_next;\
|
||||
(cp) = mtod((m), caddr_t);\
|
||||
}
|
||||
|
||||
void esis_input(), isis_input();
|
||||
#ifdef ISO_X25ESIS
|
||||
void x25esis_input();
|
||||
#endif /* ISO_X25ESIS */
|
||||
|
||||
/*
|
||||
* FUNCTION: esis_init
|
||||
*
|
||||
@ -129,13 +134,10 @@ extern char all_es_snpa[], all_is_snpa[];
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
void
|
||||
esis_init()
|
||||
{
|
||||
extern struct clnl_protosw clnl_protox[256];
|
||||
int esis_input(), isis_input();
|
||||
#ifdef ISO_X25ESIS
|
||||
int x25esis_input();
|
||||
#endif ISO_X25ESIS
|
||||
|
||||
esis_pcb.rcb_next = esis_pcb.rcb_prev = &esis_pcb;
|
||||
llinfo_llc.lc_next = llinfo_llc.lc_prev = &llinfo_llc;
|
||||
@ -147,7 +149,7 @@ esis_init()
|
||||
clnl_protox[ISO10589_ISIS].clnl_input = isis_input;
|
||||
#ifdef ISO_X25ESIS
|
||||
clnl_protox[ISO9542X25_ESIS].clnl_input = x25esis_input;
|
||||
#endif ISO_X25ESIS
|
||||
#endif /* ISO_X25ESIS */
|
||||
}
|
||||
|
||||
/*
|
||||
@ -243,6 +245,7 @@ release:
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
void
|
||||
esis_input(m0, shp)
|
||||
struct mbuf *m0; /* ptr to first mbuf of pkt */
|
||||
struct snpa_hdr *shp; /* subnetwork header */
|
||||
@ -444,7 +447,7 @@ struct rtentry *rt; /* snpa cache info regarding next hop of
|
||||
siso.siso_nlen = 6 + 1; /* should be taken from snpa_hdr */
|
||||
/* +1 is for AFI */
|
||||
bcopy(inbound_shp->snh_shost, siso.siso_data + 1, 6);
|
||||
(ifp->if_output)(ifp, m0, &siso, 0);
|
||||
(ifp->if_output)(ifp, m0, (struct sockaddr *)&siso, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -922,7 +925,7 @@ struct iso_addr *isoa;
|
||||
siso.siso_data[0] = AFI_SNA;
|
||||
siso.siso_nlen = sn_len + 1;
|
||||
bcopy(sn_addr, siso.siso_data + 1, (unsigned)sn_len);
|
||||
(ifp->if_output)(ifp, m0, &siso, 0);
|
||||
(ifp->if_output)(ifp, m0, (struct sockaddr *)&siso, 0);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -936,6 +939,7 @@ struct iso_addr *isoa;
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
void
|
||||
isis_input(m0, shp)
|
||||
struct mbuf *m0; /* ptr to first mbuf of pkt */
|
||||
struct snpa_hdr *shp; /* subnetwork header */
|
||||
@ -968,9 +972,10 @@ struct snpa_hdr *shp; /* subnetwork header */
|
||||
}
|
||||
if (mm = m_copy(m0, 0, M_COPYALL)) { /*can't block at interrupt level */
|
||||
if (sbappendaddr(&rp->rcb_socket->so_rcv,
|
||||
&esis_dl, mm, (struct mbuf *)0) != 0)
|
||||
(struct sockaddr *)&esis_dl, mm,
|
||||
(struct mbuf *)0) != 0) {
|
||||
sorwakeup(rp->rcb_socket);
|
||||
else {
|
||||
} else {
|
||||
IFDEBUG(D_ISISINPUT)
|
||||
printf("Error in sbappenaddr, mm = 0x%x\n", mm);
|
||||
ENDDEBUG
|
||||
@ -979,7 +984,7 @@ struct snpa_hdr *shp; /* subnetwork header */
|
||||
}
|
||||
}
|
||||
if (first_rp && sbappendaddr(&first_rp->rcb_socket->so_rcv,
|
||||
&esis_dl, m0, (struct mbuf *)0) != 0) {
|
||||
(struct sockaddr *)&esis_dl, m0, (struct mbuf *)0) != 0) {
|
||||
sorwakeup(first_rp->rcb_socket);
|
||||
return;
|
||||
}
|
||||
@ -996,7 +1001,7 @@ struct mbuf *m;
|
||||
int error = 0;
|
||||
unsigned sn_len;
|
||||
|
||||
ifa = ifa_ifwithnet(sdl); /* extract ifp from sockaddr_dl */
|
||||
ifa = ifa_ifwithnet((struct sockaddr *)sdl); /* get ifp from sdl */
|
||||
if (ifa == 0) {
|
||||
IFDEBUG(D_ISISOUTPUT)
|
||||
printf("isis_output: interface not found\n");
|
||||
@ -1049,6 +1054,7 @@ release:
|
||||
* The loop through iso_ifaddr is stupid because
|
||||
* back in if_down, we knew the ifp...
|
||||
*/
|
||||
void
|
||||
esis_ctlinput(req, siso)
|
||||
int req; /* request: we handle only PRC_IFDOWN */
|
||||
struct sockaddr_iso *siso; /* address of ifp */
|
||||
@ -1062,4 +1068,4 @@ struct sockaddr_iso *siso; /* address of ifp */
|
||||
}
|
||||
}
|
||||
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)esis.h 7.4 (Berkeley) 5/6/91
|
||||
* $Id: esis.h,v 1.4 1994/05/05 07:56:35 cgd Exp $
|
||||
* from: @(#)esis.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: esis.h,v 1.5 1994/05/13 06:08:41 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ESIS_H_
|
||||
#define _NETISO_ESIS_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,6 +61,8 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#include <machine/endian.h>
|
||||
|
||||
#define SNPAC_AGE 60 /* seconds */
|
||||
#define ESIS_CONFIG 60 /* seconds */
|
||||
#define ESIS_HT (ESIS_CONFIG * 2)
|
||||
@ -116,6 +115,4 @@ struct esis_stat {
|
||||
|
||||
#ifdef KERNEL
|
||||
struct esis_stat esis_stat;
|
||||
#endif KERNEL
|
||||
|
||||
#endif /* !_NETISO_ESIS_H_ */
|
||||
#endif /* KERNEL */
|
||||
|
180
sys/netiso/idrp_usrreq.c
Normal file
180
sys/netiso/idrp_usrreq.c
Normal file
@ -0,0 +1,180 @@
|
||||
/*
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)idrp_usrreq.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: idrp_usrreq.c,v 1.1 1994/05/13 06:08:42 mycroft Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/proc.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/malloc.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/errno.h>
|
||||
|
||||
#include <net/route.h>
|
||||
#include <net/if.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/clnp.h>
|
||||
#include <netiso/clnl.h>
|
||||
#include <netiso/iso_pcb.h>
|
||||
#include <netiso/iso_var.h>
|
||||
|
||||
void idrp_input();
|
||||
struct isopcb idrp_isop;
|
||||
static struct sockaddr_iso idrp_addrs[2] =
|
||||
{ { sizeof(idrp_addrs), AF_ISO, }, { sizeof(idrp_addrs[1]), AF_ISO, } };
|
||||
|
||||
/*
|
||||
* IDRP initialization
|
||||
*/
|
||||
void
|
||||
idrp_init()
|
||||
{
|
||||
extern struct clnl_protosw clnl_protox[256];
|
||||
|
||||
idrp_isop.isop_next = idrp_isop.isop_prev = &idrp_isop;
|
||||
idrp_isop.isop_faddr = &idrp_isop.isop_sfaddr;
|
||||
idrp_isop.isop_laddr = &idrp_isop.isop_sladdr;
|
||||
idrp_isop.isop_sladdr = idrp_addrs[1];
|
||||
idrp_isop.isop_sfaddr = idrp_addrs[1];
|
||||
clnl_protox[ISO10747_IDRP].clnl_input = idrp_input;
|
||||
}
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tpclnp_input().
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* Take a packet (m) from clnp, strip off the clnp header
|
||||
* and mke suitable for the idrp socket.
|
||||
* No return value.
|
||||
*/
|
||||
void
|
||||
idrp_input(m, src, dst)
|
||||
register struct mbuf *m;
|
||||
struct sockaddr_iso *src, *dst;
|
||||
{
|
||||
if (idrp_isop.isop_socket == 0) {
|
||||
bad: m_freem(m);
|
||||
return;
|
||||
}
|
||||
bzero(idrp_addrs[0].siso_data, sizeof(idrp_addrs[0].siso_data));
|
||||
bcopy((caddr_t)&(src->siso_addr), (caddr_t)&idrp_addrs[0].siso_addr,
|
||||
1 + src->siso_nlen);
|
||||
bzero(idrp_addrs[1].siso_data, sizeof(idrp_addrs[1].siso_data));
|
||||
bcopy((caddr_t)&(dst->siso_addr), (caddr_t)&idrp_addrs[1].siso_addr,
|
||||
1 + dst->siso_nlen);
|
||||
if (sbappendaddr(&idrp_isop.isop_socket->so_rcv,
|
||||
(struct sockaddr *)idrp_addrs, m, (struct mbuf *)0) == 0)
|
||||
goto bad;
|
||||
sorwakeup(idrp_isop.isop_socket);
|
||||
}
|
||||
|
||||
idrp_output(m, addr)
|
||||
struct mbuf *m, *addr;
|
||||
{
|
||||
register struct sockaddr_iso *siso = mtod(addr, struct sockaddr_iso *);
|
||||
int s = splnet(), i;
|
||||
|
||||
bcopy((caddr_t)&(siso->siso_addr),
|
||||
(caddr_t)&idrp_isop.isop_sfaddr.siso_addr, 1 + siso->siso_nlen);
|
||||
siso++;
|
||||
bcopy((caddr_t)&(siso->siso_addr),
|
||||
(caddr_t)&idrp_isop.isop_sladdr.siso_addr, 1 + siso->siso_nlen);
|
||||
i = clnp_output(m, idrp_isop, m->m_pkthdr.len, 0);
|
||||
splx(s);
|
||||
return (i);
|
||||
}
|
||||
|
||||
u_long idrp_sendspace = 3072; /* really max datagram size */
|
||||
u_long idrp_recvspace = 40 * 1024; /* 40 1K datagrams */
|
||||
|
||||
/*ARGSUSED*/
|
||||
idrp_usrreq(so, req, m, addr, control)
|
||||
struct socket *so;
|
||||
int req;
|
||||
struct mbuf *m, *addr, *control;
|
||||
{
|
||||
int error = 0;
|
||||
|
||||
/* Note: need to block idrp_input while changing
|
||||
* the udp pcb queue and/or pcb addresses.
|
||||
*/
|
||||
switch (req) {
|
||||
|
||||
case PRU_ATTACH:
|
||||
if (idrp_isop.isop_socket != NULL) {
|
||||
error = ENXIO;
|
||||
break;
|
||||
}
|
||||
idrp_isop.isop_socket = so;
|
||||
error = soreserve(so, idrp_sendspace, idrp_recvspace);
|
||||
break;
|
||||
|
||||
case PRU_SHUTDOWN:
|
||||
socantsendmore(so);
|
||||
break;
|
||||
|
||||
case PRU_SEND:
|
||||
return (idrp_output(m, addr));
|
||||
|
||||
case PRU_ABORT:
|
||||
soisdisconnected(so);
|
||||
case PRU_DETACH:
|
||||
idrp_isop.isop_socket = 0;
|
||||
break;
|
||||
|
||||
|
||||
case PRU_SENSE:
|
||||
/*
|
||||
* stat: don't bother with a blocksize.
|
||||
*/
|
||||
return (0);
|
||||
|
||||
default:
|
||||
return (EOPNOTSUPP); /* do not free mbuf's */
|
||||
}
|
||||
|
||||
release:
|
||||
if (control) {
|
||||
printf("idrp control data unexpectedly retained\n");
|
||||
m_freem(control);
|
||||
}
|
||||
if (m)
|
||||
m_freem(m);
|
||||
return (error);
|
||||
}
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)if_cons.c 7.10 (Berkeley) 5/29/91
|
||||
* $Id: if_cons.c,v 1.3 1993/12/18 00:43:02 mycroft Exp $
|
||||
* from: @(#)if_cons.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: if_cons.c,v 1.4 1994/05/13 06:08:44 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -71,11 +71,9 @@ SOFTWARE.
|
||||
#ifdef ARGO_DEBUG
|
||||
#define Static
|
||||
unsigned LAST_CALL_PCB;
|
||||
#else ARGO_DEBUG
|
||||
#else /* ARGO_DEBUG */
|
||||
#define Static static
|
||||
#endif ARGO_DEBUG
|
||||
|
||||
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
#ifndef SOCK_STREAM
|
||||
#include <sys/param.h>
|
||||
@ -86,7 +84,7 @@ unsigned LAST_CALL_PCB;
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/errno.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include "tsleep.h"
|
||||
#include <sys/tsleep.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#include <net/netisr.h>
|
||||
@ -116,7 +114,7 @@ unsigned LAST_CALL_PCB;
|
||||
#define MT_XCONFIRM MT_DATA
|
||||
#define MT_XDATA MT_DATA
|
||||
#define MT_XHEADER MT_HEADER
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
#define DONTCLEAR -1
|
||||
|
||||
@ -167,21 +165,12 @@ Static int issue_clear_req();
|
||||
|
||||
#ifndef PHASEONE
|
||||
extern struct ifaddr *ifa_ifwithnet();
|
||||
#endif PHASEONE
|
||||
#endif /* PHASEONE */
|
||||
|
||||
extern struct ifaddr *ifa_ifwithaddr();
|
||||
|
||||
Static struct socket dummysocket; /* for use by cosns */
|
||||
|
||||
extern struct isopcb tp_isopcb; /* chain of all TP pcbs */
|
||||
struct isopcb tp_incoming_pending; /* incoming connections
|
||||
for TP, pending */
|
||||
|
||||
struct isopcb *Xpcblist[] = {
|
||||
&tp_incoming_pending,
|
||||
&tp_isopcb,
|
||||
(struct isopcb *)0
|
||||
};
|
||||
|
||||
Static int parse_facil(), NSAPtoDTE(), make_partial_x25_packet();
|
||||
Static int FACILtoNSAP(), DTEtoNSAP();
|
||||
@ -297,6 +286,7 @@ nibble_match( src_octet, src_nibble, dst_octet, dst_nibble, len)
|
||||
* FUNCTION:
|
||||
* initialize the protocol
|
||||
*/
|
||||
void
|
||||
cons_init()
|
||||
{
|
||||
int tp_incoming(), clnp_incoming();
|
||||
@ -322,14 +312,13 @@ struct pklcd *lcp;
|
||||
register struct mbuf *m;
|
||||
{
|
||||
register struct isopcb *isop;
|
||||
extern struct isopcb tp_isopcb;
|
||||
int cons_tpinput();
|
||||
|
||||
if (iso_pcballoc((struct socket *)0, &tp_incoming_pending)) {
|
||||
if (iso_pcballoc((struct socket *)0, &tp_isopcb)) {
|
||||
pk_close(lcp);
|
||||
return;
|
||||
}
|
||||
isop = tp_incoming_pending.isop_next;
|
||||
isop = tp_isopcb.isop_next;
|
||||
lcp->lcd_upper = cons_tpinput;
|
||||
lcp->lcd_upnext = (caddr_t)isop;
|
||||
lcp->lcd_send(lcp); /* Confirms call */
|
||||
@ -338,7 +327,7 @@ register struct mbuf *m;
|
||||
isop->isop_faddr = &isop->isop_sfaddr;
|
||||
DTEtoNSAP(isop->isop_laddr, &lcp->lcd_laddr);
|
||||
DTEtoNSAP(isop->isop_faddr, &lcp->lcd_faddr);
|
||||
parse_facil(isop, lcp, &(mtod(m, struct x25_packet *)->packet_data),
|
||||
parse_facil(lcp, isop, &(mtod(m, struct x25_packet *)->packet_data),
|
||||
m->m_pkthdr.len - PKHEADERLN);
|
||||
}
|
||||
|
||||
@ -348,26 +337,20 @@ struct pklcd *lcp;
|
||||
{
|
||||
register struct isopcb *isop = (struct isopcb *)lcp->lcd_upnext;
|
||||
register struct x25_packet *xp;
|
||||
int cmd;
|
||||
int cmd, ptype = CLEAR;
|
||||
|
||||
if (isop == 0)
|
||||
return;
|
||||
if (m0 == 0) {
|
||||
isop->isop_chan = 0;
|
||||
isop->isop_refcnt = 0;
|
||||
lcp->lcd_upnext = 0;
|
||||
lcp->lcd_upper = 0;
|
||||
if (m0 == 0)
|
||||
goto dead;
|
||||
}
|
||||
switch(m0->m_type) {
|
||||
case MT_DATA:
|
||||
case MT_OOBDATA:
|
||||
tpcons_input(m0, isop->isop_faddr, isop->isop_laddr,
|
||||
(struct socket *)0, (caddr_t)lcp);
|
||||
tpcons_input(m0, isop->isop_faddr, isop->isop_laddr, (caddr_t)lcp);
|
||||
return;
|
||||
|
||||
case MT_CONTROL:
|
||||
switch (pk_decode(mtod(m0, struct x25_packet *))) {
|
||||
switch (ptype = pk_decode(mtod(m0, struct x25_packet *))) {
|
||||
|
||||
case RR:
|
||||
cmd = PRC_CONS_SEND_DONE;
|
||||
@ -381,12 +364,17 @@ struct pklcd *lcp;
|
||||
return;
|
||||
|
||||
dead:
|
||||
case RESET:
|
||||
case CLEAR:
|
||||
case CLEAR_CONF:
|
||||
lcp->lcd_upper = 0;
|
||||
lcp->lcd_upnext = 0;
|
||||
isop->isop_chan = 0;
|
||||
case RESET:
|
||||
cmd = PRC_ROUTEDEAD;
|
||||
}
|
||||
tpcons_ctlinput(cmd, isop->isop_faddr, isop);
|
||||
if (cmd = PRC_ROUTEDEAD && isop->isop_refcnt == 0)
|
||||
iso_pcbdetach(isop);
|
||||
}
|
||||
}
|
||||
|
||||
@ -447,6 +435,7 @@ cons_connect(isop)
|
||||
* NOTE: this takes 3rd arg. because cons uses it to inform itself
|
||||
* of things (timeouts, etc) but has a pcb instead of an address.
|
||||
*/
|
||||
void
|
||||
cons_ctlinput(cmd, sa, copcb)
|
||||
int cmd;
|
||||
struct sockaddr *sa;
|
||||
@ -524,7 +513,7 @@ done:
|
||||
|
||||
|
||||
|
||||
#endif KERNEL
|
||||
#endif /* KERNEL */
|
||||
|
||||
/*
|
||||
* NAME: make_partial_x25_packet()
|
||||
@ -553,9 +542,9 @@ done:
|
||||
|
||||
#ifdef X25_1984
|
||||
int cons_use_facils = 1;
|
||||
#else X25_1984
|
||||
#else /* X25_1984 */
|
||||
int cons_use_facils = 0;
|
||||
#endif X25_1984
|
||||
#endif /* X25_1984 */
|
||||
|
||||
int cons_use_udata = 1; /* KLUDGE FOR DEBUGGING */
|
||||
|
||||
@ -594,7 +583,7 @@ make_partial_x25_packet(isop, lcp)
|
||||
lcp->lcd_facilities = 0;
|
||||
return 0;
|
||||
}
|
||||
MGETHDR(m, MT_DATA, M_WAITOK);
|
||||
MGETHDR(m, M_WAITOK, MT_DATA);
|
||||
if (m == 0)
|
||||
return ENOBUFS;
|
||||
buf = mtod(m, caddr_t);
|
||||
@ -727,10 +716,15 @@ NSAPtoDTE(siso, sx25)
|
||||
dtelen = out - sx25->x25_addr;
|
||||
*out++ = 0;
|
||||
} else {
|
||||
register struct rtentry *rt = rtalloc1(siso, 1);
|
||||
/* error = iso_8208snparesolve(addr, x121string, &x121strlen);*/
|
||||
register struct rtentry *rt;
|
||||
extern struct sockaddr_iso blank_siso;
|
||||
struct sockaddr_iso nsiso;
|
||||
|
||||
if (rt) {
|
||||
nsiso = blank_siso;
|
||||
bcopy(nsiso.siso_data, siso->siso_data,
|
||||
nsiso.siso_nlen = siso->siso_nlen);
|
||||
if (rt = rtalloc1(&nsiso, 1)) {
|
||||
register struct sockaddr_x25 *sxx =
|
||||
(struct sockaddr_x25 *)rt->rt_gateway;
|
||||
register char *in = sxx->x25_addr;
|
||||
@ -754,16 +748,16 @@ NSAPtoDTE(siso, sx25)
|
||||
* Creates and NSAP in the sockaddr_iso (addr) from the
|
||||
* x.25 facility found at buf - 1.
|
||||
* RETURNS:
|
||||
* length of parameter if ok, -1 if error.
|
||||
* 0 if ok, -1 if error.
|
||||
*/
|
||||
|
||||
Static int
|
||||
FACILtoNSAP(addr, buf)
|
||||
u_char *buf;
|
||||
register u_char *buf;
|
||||
register struct sockaddr_iso *addr;
|
||||
{
|
||||
int len_in_nibbles, param_len = *buf++;
|
||||
u_char buf_len; /* in bytes */
|
||||
int len_in_nibbles = *++buf & 0x3f;
|
||||
u_char buf_len = (len_in_nibbles + 1) >> 1;; /* in bytes */
|
||||
|
||||
IFDEBUG(D_CADDR)
|
||||
printf("FACILtoNSAP( 0x%x, 0x%x, 0x%x )\n",
|
||||
@ -771,7 +765,6 @@ FACILtoNSAP(addr, buf)
|
||||
ENDDEBUG
|
||||
|
||||
len_in_nibbles = *buf & 0x3f;
|
||||
buf_len = (len_in_nibbles + 1) >> 1;
|
||||
/* despite the fact that X.25 makes us put a length in nibbles
|
||||
* here, the NSAP-addrs are always in full octets
|
||||
*/
|
||||
@ -793,10 +786,10 @@ FACILtoNSAP(addr, buf)
|
||||
/* Rather than blow away the connection, just ignore and use
|
||||
NSAP from DTE */;
|
||||
}
|
||||
return param_len;
|
||||
return 0;
|
||||
}
|
||||
|
||||
static
|
||||
Static
|
||||
init_siso(siso)
|
||||
register struct sockaddr_iso *siso;
|
||||
{
|
||||
@ -830,15 +823,17 @@ DTEtoNSAP(addr, sx)
|
||||
|
||||
|
||||
init_siso(addr);
|
||||
src_len = strlen(sx->x25_addr);
|
||||
in = sx->x25_addr;
|
||||
out = addr->siso_data + 1;
|
||||
if (*in == '0' && (src_len & 1 == 0)) {
|
||||
src_len = strlen(in);
|
||||
addr->siso_nlen = (src_len + 3) / 2;
|
||||
out = addr->siso_data;
|
||||
*out++ = 0x37;
|
||||
if (src_len & 1) {
|
||||
pad_tail = 0xf;
|
||||
src_len++;
|
||||
}
|
||||
for (first = 0; src_len > 0; src_len --) {
|
||||
first |= *in++;
|
||||
for (first = 0; src_len > 0; src_len--) {
|
||||
first |= 0xf & *in++;
|
||||
if (src_len & 1) {
|
||||
*out++ = first;
|
||||
first = 0;
|
||||
@ -858,15 +853,13 @@ DTEtoNSAP(addr, sx)
|
||||
* 0 if ok, E* otherwise.
|
||||
*/
|
||||
|
||||
static int
|
||||
Static int
|
||||
parse_facil(lcp, isop, buf, buf_len)
|
||||
caddr_t buf;
|
||||
u_char buf_len; /* in bytes */
|
||||
struct isopcb *isop;
|
||||
struct pklcd *lcp;
|
||||
{
|
||||
register struct sockaddr_iso *called = isop->isop_laddr;
|
||||
register struct sockaddr_iso *calling = isop->isop_faddr;
|
||||
register int i;
|
||||
register u_char *ptr = (u_char *)buf;
|
||||
u_char *ptr_lim, *facil_lim;
|
||||
@ -874,7 +867,7 @@ parse_facil(lcp, isop, buf, buf_len)
|
||||
|
||||
IFDEBUG(D_CADDR)
|
||||
printf("parse_facil(0x%x, 0x%x, 0x%x, 0x%x)\n",
|
||||
buf, buf_len, called, calling);
|
||||
lcp, isop, buf, buf_len);
|
||||
dump_buf(buf, buf_len);
|
||||
ENDDEBUG
|
||||
|
||||
@ -896,7 +889,7 @@ parse_facil(lcp, isop, buf, buf_len)
|
||||
printf("parse_facils: facil length is 0x%x\n", (int) facil_len);
|
||||
ENDDEBUG
|
||||
|
||||
while (ptr <= facil_lim) {
|
||||
while (ptr < facil_lim) {
|
||||
/* get NSAP addresses from facilities */
|
||||
switch (*ptr++) {
|
||||
case 0xcb:
|
||||
@ -929,6 +922,7 @@ parse_facil(lcp, isop, buf, buf_len)
|
||||
(example of intelligent protocol design) */
|
||||
case 0x04: /* charging info : requesting service */
|
||||
case 0x08: /* called line addr modified notification */
|
||||
case 0x00: /* marker to indicate beginning of CCITT facils */
|
||||
facil_param_len = 1;
|
||||
break;
|
||||
|
||||
@ -941,24 +935,26 @@ parse_facil(lcp, isop, buf, buf_len)
|
||||
facil_param_len = 2;
|
||||
break;
|
||||
|
||||
/* don't have any 3 octets */
|
||||
/*
|
||||
facil_param_len = 3;
|
||||
*/
|
||||
default:
|
||||
printf(
|
||||
"BOGUS FACILITY CODE facil_len 0x%x *facil_len 0x%x, ptr 0x%x *ptr 0x%x\n",
|
||||
ptr, facil_len, ptr - 1, ptr[-1]);
|
||||
/* facil that we don't handle */
|
||||
return E_CO_HLI_REJI;
|
||||
"BOGUS FACILITY CODE facil_lim 0x%x facil_len %d, ptr 0x%x *ptr 0x%x\n",
|
||||
facil_lim, facil_len, ptr - 1, ptr[-1]);
|
||||
/* facil that we don't handle
|
||||
return E_CO_HLI_REJI; */
|
||||
switch (ptr[-1] & 0xc0) {
|
||||
case 0x00: facil_param_len = 1; break;
|
||||
case 0x40: facil_param_len = 2; break;
|
||||
case 0x80: facil_param_len = 3; break;
|
||||
case 0xc0: facil_param_len = 0; break;
|
||||
}
|
||||
}
|
||||
if (facil_param_len == -1)
|
||||
return E_CO_REG_ICDA;
|
||||
if (facil_param_len == 0) /* variable length */
|
||||
facil_param_len = (int)*ptr; /* 1 + the real facil param */
|
||||
facil_param_len = (int)*ptr++; /* 1 + the real facil param */
|
||||
ptr += facil_param_len;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#endif TPCONS
|
||||
#endif /* TPCONS */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)if_eon.c 7.16 (Berkeley) 6/27/91
|
||||
* $Id: if_eon.c,v 1.6 1994/02/11 06:41:51 mycroft Exp $
|
||||
* from: @(#)if_eon.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: if_eon.c,v 1.7 1994/05/13 06:08:46 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -75,7 +75,6 @@ SOFTWARE.
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/buf.h>
|
||||
#include <sys/protosw.h>
|
||||
@ -104,8 +103,6 @@ SOFTWARE.
|
||||
#include <netiso/iso_errno.h>
|
||||
#include <netiso/eonvar.h>
|
||||
|
||||
#include <machine/cpu.h>
|
||||
|
||||
extern struct timeval time;
|
||||
extern struct ifnet loif;
|
||||
|
||||
@ -115,8 +112,7 @@ int eoninput();
|
||||
int eonoutput();
|
||||
int eonioctl();
|
||||
int eonattach();
|
||||
int eoninit();
|
||||
int eonrtrequest();
|
||||
void eonrtrequest();
|
||||
struct ifnet eonif[1];
|
||||
|
||||
eonprotoinit() {
|
||||
@ -195,7 +191,6 @@ eonioctl(ifp, cmd, data)
|
||||
ifp->if_flags |= IFF_UP;
|
||||
if (ifa->ifa_addr->sa_family != AF_LINK)
|
||||
ifa->ifa_rtrequest = eonrtrequest;
|
||||
ifa->ifa_llinfolen = sizeof(struct eon_llinfo);
|
||||
}
|
||||
break;
|
||||
}
|
||||
@ -260,6 +255,7 @@ caddr_t loc;
|
||||
*
|
||||
* RETURNS: nothing
|
||||
*/
|
||||
void
|
||||
eonrtrequest(cmd, rt, gate)
|
||||
register struct rtentry *rt;
|
||||
register struct sockaddr *gate;
|
||||
@ -297,7 +293,7 @@ register struct sockaddr *gate;
|
||||
if (gate || (gate = rt->rt_gateway)) switch (gate->sa_family) {
|
||||
case AF_LINK:
|
||||
#define SDL(x) ((struct sockaddr_dl *)x)
|
||||
if (SDL(gate)->sdl_alen = 1)
|
||||
if (SDL(gate)->sdl_alen == 1)
|
||||
el->el_snpaoffset = *(u_char *)LLADDR(SDL(gate));
|
||||
else
|
||||
ipaddrloc = LLADDR(SDL(gate));
|
||||
@ -316,21 +312,6 @@ register struct sockaddr *gate;
|
||||
- sizeof(el->el_ei);
|
||||
}
|
||||
|
||||
/*
|
||||
* FUNCTION: eoninit
|
||||
*
|
||||
* PURPOSE: initialization
|
||||
*
|
||||
* RETURNS: nothing
|
||||
*/
|
||||
|
||||
eoninit(unit)
|
||||
int unit;
|
||||
{
|
||||
printf("eon driver-init eon%d\n", unit);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* FUNCTION: eonoutput
|
||||
*
|
||||
@ -430,7 +411,7 @@ send:
|
||||
dump_buf(ei, sizeof(struct eon_iphdr));
|
||||
ENDDEBUG
|
||||
|
||||
error = ip_output(m, NULL, ro, 0, NULL); /* XXX */
|
||||
error = ip_output(m, (struct mbuf *)0, ro, 0, NULL);
|
||||
m = 0;
|
||||
if (error) {
|
||||
ifp->if_oerrors++;
|
||||
|
212
sys/netiso/iso.c
212
sys/netiso/iso.c
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso.c 7.14 (Berkeley) 6/27/91
|
||||
* $Id: iso.c,v 1.5 1994/02/14 06:42:43 cgd Exp $
|
||||
* from: @(#)iso.c 8.2 (Berkeley) 11/15/93
|
||||
* $Id: iso.c,v 1.6 1994/05/13 06:08:50 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -64,8 +64,8 @@ SOFTWARE.
|
||||
* iso.c: miscellaneous routines to support the iso address family
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/domain.h>
|
||||
@ -83,36 +83,16 @@ SOFTWARE.
|
||||
#include <netiso/iso_pcb.h>
|
||||
#include <netiso/clnp.h>
|
||||
#include <netiso/argo_debug.h>
|
||||
#ifdef TUBA
|
||||
#include <netiso/tuba_table.h>
|
||||
#endif
|
||||
|
||||
#ifdef ISO
|
||||
|
||||
int iso_interfaces = 0; /* number of external interfaces */
|
||||
extern struct ifnet loif; /* loopback interface */
|
||||
int ether_output(), llc_rtrequest();
|
||||
|
||||
|
||||
/*
|
||||
* FUNCTION: iso_init
|
||||
*
|
||||
* PURPOSE: initialize the iso address family
|
||||
*
|
||||
* RETURNS: nothing
|
||||
*
|
||||
* SIDE EFFECTS: 1) initializes the routing table.
|
||||
*
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
struct radix_node_head *iso_rnhead;
|
||||
iso_init()
|
||||
{
|
||||
static iso_init_done;
|
||||
|
||||
if (iso_init_done == 0) {
|
||||
iso_init_done++;
|
||||
rn_inithead(&iso_rnhead, 48, AF_ISO);
|
||||
}
|
||||
}
|
||||
int ether_output();
|
||||
void llc_rtrequest();
|
||||
|
||||
/*
|
||||
* FUNCTION: iso_addrmatch1
|
||||
@ -226,7 +206,7 @@ struct sockaddr_iso *sisoa, *sisob;
|
||||
|
||||
return ((lena == lenb) && (!bcmp(bufa, bufb, lena)));
|
||||
}
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
|
||||
/*
|
||||
* FUNCTION: iso_hashchar
|
||||
@ -280,6 +260,150 @@ register int len; /* length of buffer */
|
||||
|
||||
return(h);
|
||||
}
|
||||
#ifdef notdef
|
||||
/*
|
||||
* FUNCTION: iso_hash
|
||||
*
|
||||
* PURPOSE: Fill in fields of afhash structure based upon addr passed.
|
||||
*
|
||||
* RETURNS: none
|
||||
*
|
||||
* SIDE EFFECTS:
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
iso_hash(siso, hp)
|
||||
struct sockaddr_iso *siso; /* address to perform hash on */
|
||||
struct afhash *hp; /* RETURN: hash info here */
|
||||
{
|
||||
u_long buf[sizeof(struct sockaddr_iso)+1/4];
|
||||
register int bufsize;
|
||||
|
||||
|
||||
bzero(buf, sizeof(buf));
|
||||
|
||||
bufsize = iso_netof(&siso->siso_addr, buf);
|
||||
hp->afh_nethash = iso_hashchar((caddr_t)buf, bufsize);
|
||||
|
||||
IFDEBUG(D_ROUTE)
|
||||
printf("iso_hash: iso_netof: bufsize = %d\n", bufsize);
|
||||
ENDDEBUG
|
||||
|
||||
hp->afh_hosthash = iso_hashchar((caddr_t)&siso->siso_addr,
|
||||
siso->siso_addr.isoa_len);
|
||||
|
||||
IFDEBUG(D_ROUTE)
|
||||
printf("iso_hash: %s: nethash = x%x, hosthash = x%x\n",
|
||||
clnp_iso_addrp(&siso->siso_addr), hp->afh_nethash,
|
||||
hp->afh_hosthash);
|
||||
ENDDEBUG
|
||||
}
|
||||
/*
|
||||
* FUNCTION: iso_netof
|
||||
*
|
||||
* PURPOSE: Extract the network portion of the iso address.
|
||||
* The network portion of the iso address varies depending
|
||||
* on the type of address. The network portion of the
|
||||
* address will include the IDP. The network portion is:
|
||||
*
|
||||
* TYPE DESC
|
||||
* t37 The AFI and x.121 (IDI)
|
||||
* osinet The AFI, orgid, snetid
|
||||
* rfc986 The AFI, vers and network part of
|
||||
* internet address.
|
||||
*
|
||||
* RETURNS: number of bytes placed into buf.
|
||||
*
|
||||
* SIDE EFFECTS:
|
||||
*
|
||||
* NOTES: Buf is assumed to be big enough
|
||||
*/
|
||||
iso_netof(isoa, buf)
|
||||
struct iso_addr *isoa; /* address */
|
||||
caddr_t buf; /* RESULT: network portion of address here */
|
||||
{
|
||||
u_int len = 1; /* length of afi */
|
||||
|
||||
switch (isoa->isoa_afi) {
|
||||
case AFI_37:
|
||||
/*
|
||||
* Due to classic x.25 tunnel vision, there is no
|
||||
* net portion of an x.121 address. For our purposes
|
||||
* the AFI will do, so that all x.25 -type addresses
|
||||
* map to the single x.25 SNPA. (Cannot have more than
|
||||
* one, obviously).
|
||||
*/
|
||||
|
||||
break;
|
||||
|
||||
/* case AFI_OSINET:*/
|
||||
case AFI_RFC986: {
|
||||
u_short idi; /* value of idi */
|
||||
|
||||
/* osinet and rfc986 have idi in the same place */
|
||||
CTOH(isoa->rfc986_idi[0], isoa->rfc986_idi[1], idi);
|
||||
|
||||
if (idi == IDI_OSINET)
|
||||
/*
|
||||
* Network portion of OSINET address can only be the IDI. Clearly,
|
||||
* with one x25 interface, one could get to several orgids, and
|
||||
* several snetids.
|
||||
len += (ADDROSINET_IDI_LEN + OVLOSINET_ORGID_LEN +
|
||||
OVLOSINET_SNETID_LEN);
|
||||
*/
|
||||
len += ADDROSINET_IDI_LEN;
|
||||
else if (idi == IDI_RFC986) {
|
||||
u_long inetaddr;
|
||||
struct ovl_rfc986 *o986 = (struct ovl_rfc986 *)isoa;
|
||||
|
||||
/* bump len to include idi and version (1 byte) */
|
||||
len += ADDRRFC986_IDI_LEN + 1;
|
||||
|
||||
/* get inet addr long aligned */
|
||||
bcopy(o986->o986_inetaddr, &inetaddr, sizeof(inetaddr));
|
||||
inetaddr = ntohl(inetaddr); /* convert to host byte order */
|
||||
|
||||
IFDEBUG(D_ROUTE)
|
||||
printf("iso_netof: isoa ");
|
||||
dump_buf(isoa, sizeof(*isoa));
|
||||
printf("iso_netof: inetaddr 0x%x ", inetaddr);
|
||||
ENDDEBUG
|
||||
|
||||
/* bump len by size of network portion of inet address */
|
||||
if (IN_CLASSA(inetaddr)) {
|
||||
len += 4-IN_CLASSA_NSHIFT/8;
|
||||
IFDEBUG(D_ROUTE)
|
||||
printf("iso_netof: class A net len is now %d\n", len);
|
||||
ENDDEBUG
|
||||
} else if (IN_CLASSB(inetaddr)) {
|
||||
len += 4-IN_CLASSB_NSHIFT/8;
|
||||
IFDEBUG(D_ROUTE)
|
||||
printf("iso_netof: class B net len is now %d\n", len);
|
||||
ENDDEBUG
|
||||
} else {
|
||||
len += 4-IN_CLASSC_NSHIFT/8;
|
||||
IFDEBUG(D_ROUTE)
|
||||
printf("iso_netof: class C net len is now %d\n", len);
|
||||
ENDDEBUG
|
||||
}
|
||||
} else
|
||||
len = 0;
|
||||
} break;
|
||||
|
||||
default:
|
||||
len = 0;
|
||||
}
|
||||
|
||||
bcopy((caddr_t)isoa, buf, len);
|
||||
IFDEBUG(D_ROUTE)
|
||||
printf("iso_netof: isoa ");
|
||||
dump_buf(isoa, len);
|
||||
printf("iso_netof: net ");
|
||||
dump_buf(buf, len);
|
||||
ENDDEBUG
|
||||
return len;
|
||||
}
|
||||
#endif /* notdef */
|
||||
/*
|
||||
* Generic iso control operations (ioctl's).
|
||||
* Ifp is 0 if not an interface-specific ioctl.
|
||||
@ -324,6 +448,11 @@ iso_control(so, cmd, data, ifp)
|
||||
struct iso_ifaddr *nia;
|
||||
if (cmd == SIOCDIFADDR_ISO)
|
||||
return (EADDRNOTAVAIL);
|
||||
#ifdef TUBA
|
||||
/* XXXXXX can't be done in the proto init routines */
|
||||
if (tuba_tree == 0)
|
||||
tuba_table_init();
|
||||
#endif
|
||||
MALLOC(nia, struct iso_ifaddr *, sizeof(*nia),
|
||||
M_IFADDR, M_WAITOK);
|
||||
if (nia == (struct iso_ifaddr *)0)
|
||||
@ -430,7 +559,7 @@ iso_control(so, cmd, data, ifp)
|
||||
else
|
||||
printf("Didn't unlink isoifadr from list\n");
|
||||
}
|
||||
free((caddr_t)oia, M_IFADDR);
|
||||
IFAFREE((&oia->ia_ifa));
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -482,7 +611,8 @@ iso_ifinit(ifp, ia, siso, scrub)
|
||||
* if this is its first address,
|
||||
* and to validate the address if necessary.
|
||||
*/
|
||||
if (ifp->if_ioctl && (error = (*ifp->if_ioctl)(ifp, SIOCSIFADDR, ia))) {
|
||||
if (ifp->if_ioctl &&
|
||||
(error = (*ifp->if_ioctl)(ifp, SIOCSIFADDR, (caddr_t)ia))) {
|
||||
splx(s);
|
||||
ia->ia_addr = oldaddr;
|
||||
return (error);
|
||||
@ -497,7 +627,6 @@ iso_ifinit(ifp, ia, siso, scrub)
|
||||
if (ifp->if_output == ether_output) {
|
||||
ia->ia_ifa.ifa_rtrequest = llc_rtrequest;
|
||||
ia->ia_ifa.ifa_flags |= RTF_CLONING;
|
||||
ia->ia_ifa.ifa_llinfolen = sizeof(struct llinfo_llc);
|
||||
}
|
||||
/*
|
||||
* Add route for the network.
|
||||
@ -576,7 +705,7 @@ iso_ifwithidi(addr)
|
||||
return ((struct ifaddr *)0);
|
||||
}
|
||||
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
/*
|
||||
* FUNCTION: iso_ck_addr
|
||||
*
|
||||
@ -625,7 +754,7 @@ struct iso_addr *isoab; /* other addr to check */
|
||||
}
|
||||
return(0);
|
||||
}
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
/*
|
||||
* FUNCTION: iso_localifa()
|
||||
*
|
||||
@ -681,7 +810,7 @@ iso_localifa(siso)
|
||||
|
||||
#ifdef TPCONS
|
||||
#include <netiso/cons.h>
|
||||
#endif TPCONS
|
||||
#endif /* TPCONS */
|
||||
/*
|
||||
* FUNCTION: iso_nlctloutput
|
||||
*
|
||||
@ -742,15 +871,16 @@ struct mbuf *m; /* data for set, buffer for get */
|
||||
bcopy(data, (caddr_t)isop->isop_x25crud, (unsigned)data_len);
|
||||
isop->isop_x25crud_len = data_len;
|
||||
break;
|
||||
#endif TPCONS
|
||||
#endif /* TPCONS */
|
||||
|
||||
default:
|
||||
error = EOPNOTSUPP;
|
||||
}
|
||||
|
||||
if (cmd == PRCO_SETOPT)
|
||||
m_freem(m);
|
||||
return error;
|
||||
}
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
||||
#ifdef ARGO_DEBUG
|
||||
|
||||
@ -784,4 +914,4 @@ dump_isoaddr(s)
|
||||
}
|
||||
}
|
||||
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso.h 7.6 (Berkeley) 5/6/91
|
||||
* $Id: iso.h,v 1.3 1993/05/20 05:27:14 cgd Exp $
|
||||
* from: @(#)iso.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso.h,v 1.4 1994/05/13 06:08:51 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ISO_H_
|
||||
#define _NETISO_ISO_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,6 +61,9 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ISO_H_
|
||||
#define _NETISO_ISO_H_
|
||||
|
||||
/*
|
||||
* Return true if this is a multicast address
|
||||
* This assumes that the bit transmission is lsb first. This
|
||||
@ -77,6 +77,8 @@ SOFTWARE.
|
||||
/*
|
||||
* Protocols
|
||||
*/
|
||||
#define ISOPROTO_TCP 6 /* IETF experiment */
|
||||
#define ISOPROTO_UDP 17 /* IETF experiment */
|
||||
#define ISOPROTO_TP0 25 /* connection oriented transport protocol */
|
||||
#define ISOPROTO_TP1 26 /* not implemented */
|
||||
#define ISOPROTO_TP2 27 /* not implemented */
|
||||
@ -89,6 +91,7 @@ SOFTWARE.
|
||||
#define ISOPROTO_INACT_NL 33 /* inactive network layer! */
|
||||
#define ISOPROTO_ESIS 34 /* ES-IS protocol */
|
||||
#define ISOPROTO_INTRAISIS 35 /* IS-IS protocol */
|
||||
#define ISOPROTO_IDRP 36 /* Interdomain Routing Protocol */
|
||||
|
||||
#define ISOPROTO_RAW 255 /* raw clnp */
|
||||
#define ISOPROTO_MAX 256
|
||||
@ -120,11 +123,13 @@ SOFTWARE.
|
||||
#define ISO9542_ESIS 0x82
|
||||
#define ISO9542X25_ESIS 0x8a
|
||||
#define ISO10589_ISIS 0x83
|
||||
#define ISO8878A_CONS 0x84
|
||||
#define ISO10747_IDRP 0x85
|
||||
|
||||
|
||||
#ifndef IN_CLASSA_NET
|
||||
#include "../netinet/in.h"
|
||||
#endif IN_CLASSA_NET
|
||||
#include <netinet/in.h>
|
||||
#endif /* IN_CLASSA_NET */
|
||||
|
||||
|
||||
|
||||
@ -186,5 +191,4 @@ __END_DECLS
|
||||
#endif /* KERNEL */
|
||||
|
||||
#define _offsetof(t, m) ((int)((caddr_t)&((t *)0)->m))
|
||||
|
||||
#endif /* !_NETISO_ISO_H_ */
|
||||
#endif /* _NETISO_ISO_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_chksum.c 7.5 (Berkeley) 5/6/91
|
||||
* $Id: iso_chksum.c,v 1.3 1993/12/18 00:43:17 mycroft Exp $
|
||||
* from: @(#)iso_chksum.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_chksum.c,v 1.4 1994/05/13 06:08:53 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -81,15 +81,15 @@ SOFTWARE.
|
||||
*/
|
||||
|
||||
#ifdef ISO
|
||||
#include <sys/param.h>
|
||||
#include <sys/mbuf.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
#endif ISO
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/mbuf.h>
|
||||
#endif /* ISO */
|
||||
|
||||
#ifndef MNULL
|
||||
#define MNULL (struct mbuf *)0
|
||||
#endif MNULL
|
||||
#endif /* MNULL */
|
||||
|
||||
/*
|
||||
* FUNCTION: iso_check_csum
|
||||
@ -120,7 +120,7 @@ iso_check_csum(m, len)
|
||||
int l;
|
||||
|
||||
l = len;
|
||||
len = MIN(m->m_len, len);
|
||||
len = min(m->m_len, len);
|
||||
i = 0;
|
||||
|
||||
IFDEBUG(D_CHKSUM)
|
||||
@ -144,7 +144,7 @@ iso_check_csum(m, len)
|
||||
l,i,m->m_data);
|
||||
ENDDEBUG
|
||||
ASSERT( m != MNULL);
|
||||
len = MIN( m->m_len, l-i);
|
||||
len = min( m->m_len, l-i);
|
||||
p = mtod(m, u_char *);
|
||||
}
|
||||
}
|
||||
@ -196,9 +196,9 @@ iso_gen_csum(m,n,l)
|
||||
ENDDEBUG
|
||||
|
||||
while(i < l) {
|
||||
len = MIN(m->m_len, CLBYTES);
|
||||
len = min(m->m_len, CLBYTES);
|
||||
/* RAH: don't cksum more than l bytes */
|
||||
len = MIN(len, l - i);
|
||||
len = min(len, l - i);
|
||||
|
||||
cum +=len;
|
||||
p = mtod(m, u_char *);
|
||||
@ -252,22 +252,6 @@ iso_gen_csum(m,n,l)
|
||||
ENDDEBUG
|
||||
}
|
||||
|
||||
struct mbuf *
|
||||
m_append(head, m)
|
||||
struct mbuf *head, *m;
|
||||
{
|
||||
register struct mbuf *n;
|
||||
|
||||
if (m == 0)
|
||||
return head;
|
||||
if (head == 0)
|
||||
return m;
|
||||
n = head;
|
||||
while (n->m_next)
|
||||
n = n->m_next;
|
||||
n->m_next = m;
|
||||
return head;
|
||||
}
|
||||
/*
|
||||
* FUNCTION: m_datalen
|
||||
*
|
||||
@ -282,23 +266,13 @@ m_append(head, m)
|
||||
*/
|
||||
|
||||
int
|
||||
m_datalen (morig)
|
||||
struct mbuf *morig;
|
||||
m_datalen (m)
|
||||
register struct mbuf *m;
|
||||
{
|
||||
int s = splimp();
|
||||
register struct mbuf *n=morig;
|
||||
register int datalen = 0;
|
||||
register int datalen;
|
||||
|
||||
if( morig == (struct mbuf *)0)
|
||||
return 0;
|
||||
for(;;) {
|
||||
datalen += n->m_len;
|
||||
if (n->m_next == (struct mbuf *)0 ) {
|
||||
break;
|
||||
}
|
||||
n = n->m_next;
|
||||
}
|
||||
splx(s);
|
||||
for (datalen = 0; m; m = m->m_next)
|
||||
datalen += m->m_len;
|
||||
return datalen;
|
||||
}
|
||||
|
||||
@ -347,7 +321,7 @@ m_compress(in, out)
|
||||
int len;
|
||||
|
||||
len = M_TRAILINGSPACE(*out);
|
||||
len = MIN(len, in->m_len);
|
||||
len = min(len, in->m_len);
|
||||
datalen += len;
|
||||
|
||||
IFDEBUG(D_REQUEST)
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_errno.h 7.5 (Berkeley) 5/6/91
|
||||
* $Id: iso_errno.h,v 1.3 1993/05/20 05:27:17 cgd Exp $
|
||||
* from: @(#)iso_errno.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_errno.h,v 1.4 1994/05/13 06:08:54 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ISO_ERRNO_H_
|
||||
#define _NETISO_ISO_ERRNO_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,6 +61,9 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ISO_ERRNO_H_
|
||||
#define _NETISO_ISO_ERRNO_H_
|
||||
|
||||
#define ISO_ERROR_MASK 0x8000
|
||||
#define BSD_ERROR_MASK 0x0000
|
||||
#define TP_ERROR_MASK 0x8800 /* transport layer */
|
||||
@ -272,4 +272,4 @@ SOFTWARE.
|
||||
|
||||
#define CONL_ERROR_MAX 0x1c3
|
||||
|
||||
#endif /* !_NETISO_ISO_ERRNO_H_ */
|
||||
#endif /* _NETISO_ISO_ERRNO_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_pcb.c 7.10 (Berkeley) 6/27/91
|
||||
* $Id: iso_pcb.c,v 1.4 1994/01/06 23:57:36 mycroft Exp $
|
||||
* from: @(#)iso_pcb.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_pcb.c,v 1.5 1994/05/13 06:08:56 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -72,18 +72,16 @@ SOFTWARE.
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/errno.h>
|
||||
#include <sys/protosw.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#include <net/route.h>
|
||||
|
||||
#include <netinet/in_systm.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/clnp.h>
|
||||
#include <netinet/in_systm.h>
|
||||
#include <net/if.h>
|
||||
#include <net/route.h>
|
||||
#include <netiso/iso_pcb.h>
|
||||
#include <netiso/iso_var.h>
|
||||
#include <sys/protosw.h>
|
||||
|
||||
#ifdef TPCONS
|
||||
#include <netccitt/x25.h>
|
||||
@ -194,11 +192,6 @@ iso_pcbbind(isop, nam)
|
||||
if( (nam->m_len < 2) || (nam->m_len < siso->siso_len)) {
|
||||
return ENAMETOOLONG;
|
||||
}
|
||||
if (siso->siso_tlen) {
|
||||
register char *cp = TSEL(siso);
|
||||
suf.data[0] = cp[0];
|
||||
suf.data[1] = cp[1];
|
||||
}
|
||||
if (siso->siso_nlen) {
|
||||
/* non-zero net addr- better match one of our interfaces */
|
||||
IFDEBUG(D_ISO)
|
||||
@ -218,13 +211,17 @@ iso_pcbbind(isop, nam)
|
||||
isop->isop_laddr = mtod(nam, struct sockaddr_iso *);
|
||||
}
|
||||
bcopy((caddr_t)siso, (caddr_t)isop->isop_laddr, siso->siso_len);
|
||||
if (suf.s || siso->siso_tlen != 2) {
|
||||
if((suf.s < ISO_PORT_RESERVED) && (siso->siso_tlen <= 2) &&
|
||||
if (siso->siso_tlen == 0)
|
||||
goto noname;
|
||||
if ((isop->isop_socket->so_options & SO_REUSEADDR) == 0 &&
|
||||
iso_pcblookup(head, 0, (caddr_t)0, isop->isop_laddr))
|
||||
return EADDRINUSE;
|
||||
if (siso->siso_tlen <= 2) {
|
||||
bcopy(TSEL(siso), suf.data, sizeof(suf.data));
|
||||
suf.s = ntohs(suf.s);
|
||||
if((suf.s < ISO_PORT_RESERVED) &&
|
||||
(isop->isop_socket->so_state && SS_PRIV) == 0)
|
||||
return EACCES;
|
||||
if ((isop->isop_socket->so_options & SO_REUSEADDR) == 0 &&
|
||||
iso_pcblookup(head, 0, (caddr_t)0, isop->isop_laddr))
|
||||
return EADDRINUSE;
|
||||
} else {
|
||||
register char *cp;
|
||||
noname:
|
||||
@ -236,7 +233,7 @@ noname:
|
||||
if (head->isop_lport++ < ISO_PORT_RESERVED ||
|
||||
head->isop_lport > ISO_PORT_USERRESERVED)
|
||||
head->isop_lport = ISO_PORT_RESERVED;
|
||||
suf.s = head->isop_lport;
|
||||
suf.s = htons(head->isop_lport);
|
||||
cp[0] = suf.data[0];
|
||||
cp[1] = suf.data[1];
|
||||
} while (iso_pcblookup(head, 0, (caddr_t)0, isop->isop_laddr));
|
||||
@ -457,12 +454,15 @@ iso_pcbdetach(isop)
|
||||
isop, isop->isop_socket, so);
|
||||
ENDDEBUG
|
||||
#ifdef TPCONS
|
||||
if (isop->isop_refcnt) {
|
||||
if (isop->isop_chan) {
|
||||
register struct pklcd *lcp = (struct pklcd *)isop->isop_chan;
|
||||
if (--isop->isop_refcnt > 0)
|
||||
return;
|
||||
if (lcp && lcp->lcd_state == DATA_TRANSFER)
|
||||
if (lcp && lcp->lcd_state == DATA_TRANSFER) {
|
||||
lcp->lcd_upper = 0;
|
||||
lcp->lcd_upnext = 0;
|
||||
pk_disconnect(lcp);
|
||||
}
|
||||
isop->isop_chan = 0;
|
||||
}
|
||||
#endif
|
||||
@ -612,4 +612,4 @@ iso_pcblookup(head, fportlen, fport, laddr)
|
||||
}
|
||||
return (struct isopcb *)0;
|
||||
}
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_pcb.h 7.5 (Berkeley) 5/6/91
|
||||
* $Id: iso_pcb.h,v 1.3 1993/05/20 05:27:20 cgd Exp $
|
||||
* from: @(#)iso_pcb.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_pcb.h,v 1.4 1994/05/13 06:08:58 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ISO_PCB_H_
|
||||
#define _NETISO_ISO_PCB_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -86,6 +83,7 @@ struct isopcb {
|
||||
caddr_t isop_chan; /* actually struct pklcb * */
|
||||
u_short isop_refcnt; /* mult TP4 tpcb's -> here */
|
||||
u_short isop_lport; /* MISLEADLING work var */
|
||||
u_short isop_tuba_cached; /* for tuba address ref cnts */
|
||||
int isop_x25crud_len; /* x25 call request ud */
|
||||
char isop_x25crud[MAXX25CRUDLEN];
|
||||
struct ifaddr *isop_ifa; /* ESIS interface assoc w/sock */
|
||||
@ -112,5 +110,3 @@ struct rawisopcb {
|
||||
#ifdef KERNEL
|
||||
struct isopcb *iso_pcblookup();
|
||||
#endif
|
||||
|
||||
#endif /* !_NETISO_ISO_PCB_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_proto.c 7.8 (Berkeley) 5/6/91
|
||||
* $Id: iso_proto.c,v 1.3 1993/12/18 00:43:24 mycroft Exp $
|
||||
* from: @(#)iso_proto.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_proto.c,v 1.4 1994/05/13 06:08:59 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -60,36 +60,40 @@ SOFTWARE.
|
||||
/*
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/* iso_proto.c : protocol switch tables in the ISO domain
|
||||
/*
|
||||
* iso_proto.c : protocol switch tables in the ISO domain
|
||||
*
|
||||
* ISO protocol family includes TP, CLTP, CLNP, 8208
|
||||
* TP and CLNP are implemented here.
|
||||
*/
|
||||
|
||||
#ifdef ISO
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/domain.h>
|
||||
#include <sys/mbuf.h>
|
||||
|
||||
#include <net/radix.h>
|
||||
|
||||
#include <netiso/iso.h>
|
||||
|
||||
int clnp_output(), clnp_init(),clnp_slowtimo(),clnp_drain();
|
||||
int rclnp_input(), rclnp_output(), rclnp_ctloutput(), raw_usrreq();
|
||||
int clnp_usrreq();
|
||||
int clnp_output(), rclnp_output(), rclnp_ctloutput();
|
||||
int raw_usrreq(), clnp_usrreq();
|
||||
void clnp_init(), clnp_slowtimo(), clnp_drain(), rclnp_input();
|
||||
|
||||
int tp_ctloutput();
|
||||
int tpclnp_ctlinput();
|
||||
int tpclnp_input();
|
||||
int tp_usrreq();
|
||||
int tp_init(), tp_slowtimo(), tp_drain();
|
||||
int cons_init(), tpcons_input();
|
||||
int tp_ctloutput(), tp_usrreq(), tpcons_input();
|
||||
void tp_init(), tp_fasttimo(), tp_slowtimo(), tp_drain(), cons_init();
|
||||
void tpclnp_input(), tpclnp_ctlinput();
|
||||
|
||||
int esis_input(), esis_ctlinput(), esis_init(), esis_usrreq();
|
||||
int cltp_input(), cltp_ctlinput(), cltp_init(), cltp_usrreq(), cltp_output();
|
||||
int isis_input();
|
||||
int esis_usrreq(), idrp_usrreq(), cltp_usrreq(), cltp_output();
|
||||
void esis_init(), idrp_init(), cltp_init(), isis_input(), esis_input();
|
||||
void idrp_input(), cltp_input(), esis_ctlinput(), cltp_ctlinput();
|
||||
|
||||
#ifdef TUBA
|
||||
int tuba_usrreq(), tuba_ctloutput(), tuba_tcpinput();
|
||||
void tuba_init(), tuba_slowtimo(), tuba_fasttimo();
|
||||
#endif
|
||||
|
||||
struct protosw isosw[] = {
|
||||
/*
|
||||
@ -141,13 +145,28 @@ struct protosw isosw[] = {
|
||||
0, 0, 0, 0
|
||||
},
|
||||
|
||||
/* ISOPROTO_IDRP */
|
||||
{ SOCK_DGRAM, &isodomain, ISOPROTO_IDRP, PR_ATOMIC|PR_ADDR,
|
||||
idrp_input, 0, 0, 0,
|
||||
idrp_usrreq,
|
||||
idrp_init, 0, 0, 0
|
||||
},
|
||||
|
||||
/* ISOPROTO_TP */
|
||||
{ SOCK_SEQPACKET, &isodomain, ISOPROTO_TP, PR_CONNREQUIRED|PR_WANTRCVD,
|
||||
tpclnp_input, 0, tpclnp_ctlinput, tp_ctloutput,
|
||||
tpclnp_input, 0, tpclnp_ctlinput, tp_ctloutput,
|
||||
tp_usrreq,
|
||||
tp_init, 0, tp_slowtimo, tp_drain,
|
||||
tp_init, tp_fasttimo, tp_slowtimo, tp_drain,
|
||||
},
|
||||
|
||||
#ifdef TUBA
|
||||
{ SOCK_STREAM, &isodomain, ISOPROTO_TCP, PR_CONNREQUIRED|PR_WANTRCVD,
|
||||
tuba_tcpinput, 0, 0, tuba_ctloutput,
|
||||
tuba_usrreq,
|
||||
tuba_init, tuba_fasttimo, tuba_fasttimo, 0
|
||||
},
|
||||
#endif
|
||||
|
||||
#ifdef TPCONS
|
||||
/* ISOPROTO_TP */
|
||||
{ SOCK_SEQPACKET, &isodomain, ISOPROTO_TP0, PR_CONNREQUIRED|PR_WANTRCVD,
|
||||
@ -159,15 +178,18 @@ struct protosw isosw[] = {
|
||||
|
||||
};
|
||||
|
||||
int iso_init();
|
||||
|
||||
struct domain isodomain = {
|
||||
AF_ISO, /* family */
|
||||
"iso-domain", /* name */
|
||||
iso_init, /* initialize routine */
|
||||
0, /* initialize routine */
|
||||
0, /* externalize access rights */
|
||||
0, /* dispose of internalized rights */
|
||||
isosw, /* protosw */
|
||||
&isosw[sizeof(isosw)/sizeof(isosw[0])] /* NPROTOSW */
|
||||
&isosw[sizeof(isosw)/sizeof(isosw[0])], /* NPROTOSW */
|
||||
0, /* next */
|
||||
rn_inithead, /* rtattach */
|
||||
48, /* rtoffset */
|
||||
sizeof(struct sockaddr_iso) /* maxkeylen */
|
||||
};
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_snpac.c 7.14 (Berkeley) 6/27/91
|
||||
* $Id: iso_snpac.c,v 1.4 1993/12/18 00:43:26 mycroft Exp $
|
||||
* from: @(#)iso_snpac.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_snpac.c,v 1.5 1994/05/13 06:09:01 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -63,7 +63,6 @@ SOFTWARE.
|
||||
|
||||
#ifdef ISO
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/mbuf.h>
|
||||
@ -90,9 +89,9 @@ SOFTWARE.
|
||||
int iso_systype = SNPA_ES; /* default to be an ES */
|
||||
extern short esis_holding_time, esis_config_time, esis_esconfig_time;
|
||||
extern struct timeval time;
|
||||
extern void esis_config();
|
||||
extern int hz;
|
||||
static void snpac_fixdstandmask();
|
||||
extern void esis_config();
|
||||
extern int hz;
|
||||
static void snpac_fixdstandmask();
|
||||
|
||||
struct sockaddr_iso blank_siso = {sizeof(blank_siso), AF_ISO};
|
||||
extern u_long iso_hashchar();
|
||||
@ -101,7 +100,7 @@ static struct sockaddr_iso
|
||||
gte = {sizeof(dst), AF_ISO},
|
||||
src = {sizeof(dst), AF_ISO},
|
||||
msk = {sizeof(dst), AF_ISO},
|
||||
zmk = {1};
|
||||
zmk = {0};
|
||||
#define zsi blank_siso
|
||||
#define zero_isoa zsi.siso_addr
|
||||
#define zap_isoaddr(a, b) {Bzero(&a.siso_addr, sizeof(*r)); r = b; \
|
||||
@ -163,59 +162,27 @@ struct sockaddr *sa;
|
||||
struct rtentry *rt2;
|
||||
struct ifnet *ifp = rt->rt_ifp;
|
||||
int addrlen = ifp->if_addrlen;
|
||||
static struct rtentry *recursing = 0;
|
||||
#define LLC_SIZE 3 /* XXXXXX do this right later */
|
||||
|
||||
IFDEBUG (D_SNPA)
|
||||
printf("llc_rtrequest(%d, %x, %x)\n", req, rt, sa);
|
||||
ENDDEBUG
|
||||
if (rt->rt_flags & RTF_GATEWAY) {
|
||||
if (recursing) {
|
||||
log(LOG_DEBUG, "llc_rtrequest: gateway route points to same type %x %x\n",
|
||||
recursing, rt);
|
||||
} else switch (req) {
|
||||
case RTM_RESOLVE:
|
||||
case RTM_ADD:
|
||||
recursing = rt;
|
||||
rt->rt_llinfo = (caddr_t)rtalloc1(&gate->sa, 1);
|
||||
recursing = 0;
|
||||
if (rt->rt_rmx.rmx_mtu == 0) {
|
||||
rt->rt_rmx.rmx_mtu =
|
||||
((rt2 = (struct rtentry *)rt->rt_llinfo) &&
|
||||
(rt2->rt_rmx.rmx_mtu)) ?
|
||||
rt2->rt_rmx.rmx_mtu :
|
||||
rt->rt_ifp->if_mtu - LLC_SIZE;
|
||||
}
|
||||
return;
|
||||
|
||||
case RTM_DELETE:
|
||||
if (lc)
|
||||
RTFREE((struct rtentry *)lc);
|
||||
rt->rt_llinfo = 0;
|
||||
}
|
||||
} else switch (req) {
|
||||
if (rt->rt_flags & RTF_GATEWAY)
|
||||
return;
|
||||
else switch (req) {
|
||||
case RTM_ADD:
|
||||
/*
|
||||
* Case 1: This route may come from a route to iface with mask
|
||||
* or from a default route.
|
||||
*/
|
||||
if (rt->rt_flags & RTF_CLONING) {
|
||||
register struct ifaddr *ifa;
|
||||
register struct sockaddr *sa;
|
||||
for (ifa = ifp->if_addrlist; ifa; ifa->ifa_next)
|
||||
if ((sa = ifa->ifa_addr)->sa_family == AF_LINK) {
|
||||
if (sa->sa_len > gate->sa.sa_len)
|
||||
log(LOG_DEBUG, "llc_rtrequest: cloning address too small\n");
|
||||
else {
|
||||
Bcopy(sa, gate, gate->sa.sa_len);
|
||||
gate->sdl.sdl_alen = 0;
|
||||
}
|
||||
break;
|
||||
}
|
||||
if (ifa == 0)
|
||||
log(LOG_DEBUG, "llc_rtrequest: can't find LL ifaddr for iface\n");
|
||||
break;
|
||||
iso_setmcasts(ifp, req);
|
||||
rt_setgate(rt, rt_key(rt),
|
||||
(struct sockaddr *)&blank_dl);
|
||||
return;
|
||||
}
|
||||
if (lc != 0)
|
||||
return; /* happens on a route change */
|
||||
/* FALLTHROUGH */
|
||||
case RTM_RESOLVE:
|
||||
/*
|
||||
@ -226,8 +193,6 @@ struct sockaddr *sa;
|
||||
log(LOG_DEBUG, "llc_rtrequest: got non-link non-gateway route\n");
|
||||
break;
|
||||
}
|
||||
if (lc != 0)
|
||||
return; /* happens on a route change */
|
||||
R_Malloc(lc, struct llinfo_llc *, sizeof (*lc));
|
||||
rt->rt_llinfo = (caddr_t)lc;
|
||||
if (lc == 0) {
|
||||
@ -246,7 +211,9 @@ struct sockaddr *sa;
|
||||
lc->lc_flags = (SNPA_ES | SNPA_VALID | SNPA_PERM);
|
||||
break;
|
||||
case RTM_DELETE:
|
||||
if (lc == 0 || (rt->rt_flags & RTF_CLONING))
|
||||
if (rt->rt_flags & RTF_CLONING)
|
||||
iso_setmcasts(ifp, req);
|
||||
if (lc == 0)
|
||||
return;
|
||||
remque(lc);
|
||||
Free(lc);
|
||||
@ -258,6 +225,41 @@ struct sockaddr *sa;
|
||||
rt->rt_rmx.rmx_mtu = rt->rt_ifp->if_mtu - LLC_SIZE;
|
||||
}
|
||||
}
|
||||
/*
|
||||
* FUNCTION: iso_setmcasts
|
||||
*
|
||||
* PURPOSE: Enable/Disable ESIS/ISIS multicast reception on interfaces.
|
||||
*
|
||||
* NOTES: This also does a lot of obscure magic;
|
||||
*/
|
||||
iso_setmcasts(ifp, req)
|
||||
struct ifnet *ifp;
|
||||
int req;
|
||||
{
|
||||
static char *addrlist[] =
|
||||
{ all_es_snpa, all_is_snpa, all_l1is_snpa, all_l2is_snpa, 0};
|
||||
struct ifreq ifr;
|
||||
register caddr_t *cpp;
|
||||
int doreset = 0;
|
||||
|
||||
bzero((caddr_t)&ifr, sizeof(ifr));
|
||||
for (cpp = (caddr_t *)addrlist; *cpp; cpp++) {
|
||||
bcopy(*cpp, (caddr_t)ifr.ifr_addr.sa_data, 6);
|
||||
if (req == RTM_ADD)
|
||||
if (ether_addmulti(&ifr, (struct arpcom *)ifp) == ENETRESET)
|
||||
doreset++;
|
||||
else
|
||||
if (ether_delmulti(&ifr, (struct arpcom *)ifp) == ENETRESET)
|
||||
doreset++;
|
||||
}
|
||||
if (doreset) {
|
||||
if (ifp->if_reset)
|
||||
(*ifp->if_reset)(ifp->if_unit);
|
||||
else
|
||||
printf("iso_setmcasts: %s%d needs reseting to receive iso mcasts\n",
|
||||
ifp->if_name, ifp->if_unit);
|
||||
}
|
||||
}
|
||||
/*
|
||||
* FUNCTION: iso_snparesolve
|
||||
*
|
||||
@ -385,7 +387,7 @@ int nsellength; /* nsaps may differ only in trailing bytes */
|
||||
struct rtentry *mrt = 0;
|
||||
register struct iso_addr *r; /* for zap_isoaddr macro */
|
||||
int snpalen = min(ifp->if_addrlen, MAX_SNPALEN);
|
||||
int new_entry = 0, index = ifp->if_index;
|
||||
int new_entry = 0, index = ifp->if_index, iftype = ifp->if_type;
|
||||
|
||||
IFDEBUG(D_SNPA)
|
||||
printf("snpac_add(%x, %x, %x, %x, %x, %x)\n",
|
||||
@ -408,6 +410,7 @@ int nsellength; /* nsaps may differ only in trailing bytes */
|
||||
}
|
||||
new_entry = 1;
|
||||
zap_linkaddr((>e_dl), snpa, snpalen, index);
|
||||
gte_dl.sdl_type = iftype;
|
||||
if (rtrequest(RTM_ADD, S(dst), S(gte_dl), netmask, flags, &mrt) ||
|
||||
mrt == 0)
|
||||
return (0);
|
||||
@ -420,8 +423,9 @@ int nsellength; /* nsaps may differ only in trailing bytes */
|
||||
goto add;
|
||||
if (nsellength && (rt->rt_flags & RTF_HOST)) {
|
||||
if (rt->rt_refcnt == 0) {
|
||||
rtrequest(RTM_DELETE, S(dst), (struct sockaddr *)0,
|
||||
(struct sockaddr *)0, 0, (struct rtentry *)0);
|
||||
rtrequest(RTM_DELETE, S(dst),
|
||||
(struct sockaddr *)0, (struct sockaddr *)0,
|
||||
0, (struct rtentry **)0);
|
||||
rt = 0;
|
||||
goto add;
|
||||
} else {
|
||||
@ -441,6 +445,7 @@ int nsellength; /* nsaps may differ only in trailing bytes */
|
||||
}
|
||||
zap_linkaddr(sdl, snpa, snpalen, index);
|
||||
sdl->sdl_len = old_sdl_len;
|
||||
sdl->sdl_type = iftype;
|
||||
new_entry = 1;
|
||||
}
|
||||
}
|
||||
@ -448,7 +453,7 @@ int nsellength; /* nsaps may differ only in trailing bytes */
|
||||
panic("snpac_rtrequest");
|
||||
rt->rt_rmx.rmx_expire = ht + time.tv_sec;
|
||||
lc->lc_flags = SNPA_VALID | type;
|
||||
if (type & SNPA_IS)
|
||||
if ((type & SNPA_IS) && !(iso_systype & SNPA_IS))
|
||||
snpac_logdefis(rt);
|
||||
return (new_entry);
|
||||
}
|
||||
@ -541,23 +546,23 @@ register struct rtentry *sc;
|
||||
{
|
||||
register struct iso_addr *r;
|
||||
register struct sockaddr_dl *sdl = (struct sockaddr_dl *)sc->rt_gateway;
|
||||
register struct rtentry *rt = rtalloc1((struct sockaddr *)&zsi, 0);
|
||||
register struct rtentry *rt;
|
||||
|
||||
zap_linkaddr((>e_dl), LLADDR(sdl), sdl->sdl_alen, sdl->sdl_index);
|
||||
if (known_is == 0)
|
||||
known_is = sc;
|
||||
if (known_is != sc) {
|
||||
rtfree(known_is);
|
||||
known_is = sc;
|
||||
}
|
||||
if (rt == 0) {
|
||||
rtrequest(RTM_ADD, S(zsi), S(gte_dl), S(zmk),
|
||||
RTF_DYNAMIC|RTF_GATEWAY|RTF_CLONING, 0);
|
||||
if (known_is == sc || !(sc->rt_flags & RTF_HOST))
|
||||
return;
|
||||
if (known_is) {
|
||||
RTFREE(known_is);
|
||||
}
|
||||
rt->rt_refcnt--;
|
||||
if (rt->rt_flags & (RTF_DYNAMIC | RTF_MODIFIED)) {
|
||||
*((struct sockaddr_dl *)rt->rt_gateway) = gte_dl;
|
||||
known_is = sc;
|
||||
sc->rt_refcnt++;
|
||||
rt = rtalloc1((struct sockaddr *)&zsi, 0);
|
||||
if (rt == 0)
|
||||
rtrequest(RTM_ADD, S(zsi), rt_key(sc), S(zmk),
|
||||
RTF_DYNAMIC|RTF_GATEWAY, 0);
|
||||
else {
|
||||
if ((rt->rt_flags & RTF_DYNAMIC) &&
|
||||
(rt->rt_flags & RTF_GATEWAY) && rt_mask(rt)->sa_len == 0)
|
||||
rt_setgate(rt, rt_key(rt), rt_key(sc));
|
||||
}
|
||||
}
|
||||
|
||||
@ -592,12 +597,10 @@ snpac_age()
|
||||
|
||||
for (lc = llinfo_llc.lc_next; lc != & llinfo_llc; lc = nlc) {
|
||||
nlc = lc->lc_next;
|
||||
if (((lc->lc_flags & SNPA_PERM) == 0) && (lc->lc_flags & SNPA_VALID)) {
|
||||
if (lc->lc_flags & SNPA_VALID) {
|
||||
rt = lc->lc_rt;
|
||||
if (rt->rt_rmx.rmx_expire && rt->rt_rmx.rmx_expire < time.tv_sec)
|
||||
snpac_free(lc);
|
||||
else
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -731,4 +734,4 @@ struct iso_addr *host, *gateway, *netmask;
|
||||
rtredirect(S(dst), S(gte), (struct sockaddr *)0,
|
||||
RTF_DONE | RTF_HOST, S(gte), 0);
|
||||
}
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_snpac.h 7.8 (Berkeley) 5/6/91
|
||||
* $Id: iso_snpac.h,v 1.3 1993/05/20 05:27:24 cgd Exp $
|
||||
* from: @(#)iso_snpac.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_snpac.h,v 1.4 1994/05/13 06:09:03 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ISO_SNPAC_H_
|
||||
#define _NETISO_ISO_SNPAC_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -113,6 +110,4 @@ struct llinfo_llc {
|
||||
|
||||
#ifdef KERNEL
|
||||
struct llinfo_llc llinfo_llc; /* head for linked lists */
|
||||
#endif KERNEL
|
||||
|
||||
#endif /* !_NETISO_ISO_SNPAC_H_ */
|
||||
#endif /* KERNEL */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1988, 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1988, 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)iso_var.h 7.5 (Berkeley) 5/6/91
|
||||
* $Id: iso_var.h,v 1.3 1993/05/20 05:27:25 cgd Exp $
|
||||
* from: @(#)iso_var.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: iso_var.h,v 1.4 1994/05/13 06:09:04 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_ISO_VAR_H_
|
||||
#define _NETISO_ISO_VAR_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -135,6 +132,4 @@ struct snpa_hdr {
|
||||
struct iso_ifaddr *iso_ifaddr; /* linked list of iso address ifaces */
|
||||
struct iso_ifaddr *iso_localifa(); /* linked list of iso address ifaces */
|
||||
struct ifqueue clnlintrq; /* clnl packet input queue */
|
||||
#endif KERNEL
|
||||
|
||||
#endif /* !_NETISO_ISO_VAR_H_ */
|
||||
#endif /* KERNEL */
|
||||
|
@ -1,6 +1,7 @@
|
||||
/* NEW */
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +31,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp.trans 7.9 (Berkeley) 5/7/91
|
||||
* $Id: tp.trans,v 1.2 1993/05/20 05:27:27 cgd Exp $
|
||||
* from: @(#)tp.trans 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp.trans,v 1.3 1994/05/13 06:09:06 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -84,23 +85,25 @@ SOFTWARE.
|
||||
|
||||
*INCLUDE
|
||||
{
|
||||
/* @(#)tp.trans 7.9 (Berkeley) 5/7/91 */
|
||||
#include "param.h"
|
||||
#include "socket.h"
|
||||
#include "socketvar.h"
|
||||
#include "protosw.h"
|
||||
#include "mbuf.h"
|
||||
#include "time.h"
|
||||
#include "errno.h"
|
||||
#include "../netiso/tp_param.h"
|
||||
#include "../netiso/tp_stat.h"
|
||||
#include "../netiso/tp_pcb.h"
|
||||
#include "../netiso/tp_tpdu.h"
|
||||
#include "../netiso/argo_debug.h"
|
||||
#include "../netiso/tp_trace.h"
|
||||
#include "../netiso/iso_errno.h"
|
||||
#include "../netiso/tp_seq.h"
|
||||
#include "../netiso/cons.h"
|
||||
/* @(#)tp.trans 8.1 (Berkeley) 6/10/93 */
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/errno.h>
|
||||
|
||||
#include <netiso/tp_param.h>
|
||||
#include <netiso/tp_stat.h>
|
||||
#include <netiso/tp_pcb.h>
|
||||
#include <netiso/tp_tpdu.h>
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/tp_trace.h>
|
||||
#include <netiso/iso_errno.h>
|
||||
#include <netiso/tp_seq.h>
|
||||
#include <netiso/cons.h>
|
||||
|
||||
#define DRIVERTRACE TPPTdriver
|
||||
#define sbwakeup(sb) sowakeup(p->tp_sock, sb);
|
||||
@ -115,9 +118,11 @@ int tp_emit(),
|
||||
void tp_indicate(), tp_getoptions(),
|
||||
tp_soisdisconnecting(), tp_soisdisconnected(),
|
||||
tp_recycle_tsuffix(),
|
||||
#ifdef TP_DEBUG_TIMERS
|
||||
tp_etimeout(), tp_euntimeout(),
|
||||
tp_euntimeout_lss(), tp_ctimeout(),
|
||||
tp_cuntimeout(), tp_ctimeout_MIN(),
|
||||
tp_ctimeout(), tp_cuntimeout(),
|
||||
tp_ctimeout_MIN(),
|
||||
#endif
|
||||
tp_freeref(), tp_detach(),
|
||||
tp0_stash(), tp0_send(),
|
||||
tp_netcmd(), tp_send()
|
||||
@ -157,14 +162,12 @@ TP_CONFIRMING /* Local to this implementation */
|
||||
*/
|
||||
|
||||
TM_sendack
|
||||
/* TM_sendack does dual duty - keepalive AND sendack.
|
||||
/* TM_sendack does dual duty - keepalive AND closed-window
|
||||
* Probes.
|
||||
* It's set w/ keepalive-ticks every time an ack is sent.
|
||||
* (this is done in (void) tp_emit() ).
|
||||
* It's cancelled and reset whenever a DT
|
||||
* arrives and it doesn't require immediate acking.
|
||||
* Note that in this case it's set w/ the minimum of
|
||||
* its prev value and the sendack-ticks value so the
|
||||
* purpose of the keepalive is preserved.
|
||||
* Whenever a DT arrives which doesn't require immediate acking,
|
||||
* a separate fast-timeout flag is set ensuring 200ms response.
|
||||
*/
|
||||
TM_notused
|
||||
|
||||
@ -329,7 +332,7 @@ TP_CLOSED <== [ TP_LISTENING, TP_CLOSED ] T_DETACH
|
||||
TP_CONFIRMING <== TP_LISTENING CR_TPDU
|
||||
( $P.tp_class == TP_CLASS_0)
|
||||
{
|
||||
$P.tp_refp->tpr_state = REF_OPEN; /* has timers ??? */
|
||||
$P.tp_refstate = REF_OPEN; /* has timers ??? */
|
||||
}
|
||||
;
|
||||
|
||||
@ -342,7 +345,7 @@ TP_CONFIRMING <== TP_LISTENING CR_TPDU
|
||||
IFDEBUG(D_CONN)
|
||||
printf("CR datalen 0x%x data 0x%x", $$.e_datalen, $$.e_data);
|
||||
ENDDEBUG
|
||||
$P.tp_refp->tpr_state = REF_OPEN; /* has timers */
|
||||
$P.tp_refstate = REF_OPEN; /* has timers */
|
||||
$P.tp_fcredit = $$.e_cdt;
|
||||
|
||||
if ($$.e_datalen > 0) {
|
||||
@ -380,11 +383,12 @@ TP_AKWAIT <== TP_CONFIRMING T_ACPT_req
|
||||
IFDEBUG(D_CONN)
|
||||
printf("Confirming connection: $P" );
|
||||
ENDDEBUG
|
||||
tp_getoptions($P);
|
||||
soisconnecting($P.tp_sock);
|
||||
if (($P.tp_rx_strat & TPRX_FASTSTART) && ($P.tp_fcredit > 0))
|
||||
$P.tp_cong_win = $P.tp_fcredit;
|
||||
$P.tp_cong_win = $P.tp_fcredit * $P.tp_l_tpdusize;
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_cc_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_cc_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -392,14 +396,12 @@ TP_AKWAIT <== TP_CONFIRMING T_ACPT_req
|
||||
TP_CLOSED <== TP_CONFIRMING T_ACPT_req
|
||||
DEFAULT /* emit failed */
|
||||
{
|
||||
register struct tp_ref *r = $P.tp_refp;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("event: CR_TPDU emit CC failed done " );
|
||||
ENDDEBUG
|
||||
soisdisconnected($P.tp_sock);
|
||||
tp_recycle_tsuffix( $P );
|
||||
tp_freeref(r);
|
||||
tp_recycle_tsuffix($P);
|
||||
tp_freeref($P.tp_lref);
|
||||
tp_detach($P);
|
||||
}
|
||||
;
|
||||
@ -427,10 +429,10 @@ TP_CRSENT <== TP_CLOSED T_CONN_req
|
||||
if (error = tp_emit(CR_TPDU_type, $P, 0, 0, data) )
|
||||
return error; /* driver WON'T change state; will return error */
|
||||
|
||||
$P.tp_refp->tpr_state = REF_OPEN; /* has timers */
|
||||
$P.tp_refstate = REF_OPEN; /* has timers */
|
||||
if($P.tp_class != TP_CLASS_0) {
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_cr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_cr_ticks);
|
||||
}
|
||||
}
|
||||
;
|
||||
@ -444,16 +446,26 @@ TP_REFWAIT <== [ TP_CRSENT, TP_AKWAIT, TP_OPEN ] DR_TPDU
|
||||
sbappendrecord(&$P.tp_Xrcv, $$.e_data);
|
||||
$$.e_data = MNULL;
|
||||
}
|
||||
tp_indicate(T_DISCONNECT, $P, 0);
|
||||
if ($P.tp_state == TP_OPEN)
|
||||
tp_indicate(T_DISCONNECT, $P, 0);
|
||||
else {
|
||||
int so_error = ECONNREFUSED;
|
||||
if ($$.e_reason != (E_TP_NO_SESSION ^ TP_ERROR_MASK) &&
|
||||
$$.e_reason != (E_TP_NO_CR_ON_NC ^ TP_ERROR_MASK) &&
|
||||
$$.e_reason != (E_TP_REF_OVERFLOW ^ TP_ERROR_MASK))
|
||||
so_error = ECONNABORTED;
|
||||
tp_indicate(T_DISCONNECT, $P, so_error);
|
||||
}
|
||||
tp_soisdisconnected($P);
|
||||
if ($P.tp_class != TP_CLASS_0) {
|
||||
if ($P.tp_state == TP_OPEN ) {
|
||||
tp_euntimeout($P.tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P.tp_refp, TM_inact);
|
||||
tp_cuntimeout($P.tp_refp, TM_sendack);
|
||||
tp_euntimeout($P, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
tp_cuntimeout($P, TM_inact);
|
||||
tp_cuntimeout($P, TM_sendack);
|
||||
$P.tp_flags &= ~TPF_DELACK;
|
||||
}
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
if( $$.e_sref != 0 )
|
||||
(void) tp_emit(DC_TPDU_type, $P, 0, 0, MNULL);
|
||||
}
|
||||
@ -466,8 +478,8 @@ SAME <== TP_CLOSED DR_TPDU
|
||||
if( $$.e_sref != 0 )
|
||||
(void) tp_emit(DC_TPDU_type, $P, 0, 0, MNULL);
|
||||
/* reference timer already set - reset it to be safe (???) */
|
||||
tp_euntimeout($P.tp_refp, TM_reference); /* all */
|
||||
tp_etimeout($P.tp_refp, TM_reference, 0, 0, 0, (int)$P.tp_refer_ticks);
|
||||
tp_euntimeout($P, TM_reference); /* all */
|
||||
tp_etimeout($P, TM_reference, (int)$P.tp_refer_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -475,7 +487,7 @@ SAME <== TP_CLOSED DR_TPDU
|
||||
TP_REFWAIT <== TP_CRSENT ER_TPDU
|
||||
DEFAULT
|
||||
{
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
tp_indicate(ER_TPDU, $P, $$.e_reason);
|
||||
tp_soisdisconnected($P);
|
||||
}
|
||||
@ -485,7 +497,7 @@ TP_REFWAIT <== TP_CRSENT ER_TPDU
|
||||
TP_REFWAIT <== TP_CLOSING DR_TPDU
|
||||
DEFAULT
|
||||
{
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
tp_soisdisconnected($P);
|
||||
}
|
||||
;
|
||||
@ -497,7 +509,7 @@ TP_REFWAIT <== TP_CLOSING ER_TPDU
|
||||
DEFAULT
|
||||
{
|
||||
tp_indicate(ER_TPDU, $P, $$.e_reason);
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
tp_soisdisconnected($P);
|
||||
}
|
||||
;
|
||||
@ -505,7 +517,7 @@ TP_REFWAIT <== TP_CLOSING ER_TPDU
|
||||
TP_REFWAIT <== TP_CLOSING DC_TPDU
|
||||
DEFAULT
|
||||
{
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
tp_soisdisconnected($P);
|
||||
}
|
||||
;
|
||||
@ -534,14 +546,14 @@ TP_CLOSING <== [ TP_AKWAIT, TP_OPEN ] ER_TPDU
|
||||
DEFAULT
|
||||
{
|
||||
if ($P.tp_state == TP_OPEN) {
|
||||
tp_euntimeout($P.tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P.tp_refp, TM_inact);
|
||||
tp_cuntimeout($P.tp_refp, TM_sendack);
|
||||
tp_euntimeout($P, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P, TM_inact);
|
||||
tp_cuntimeout($P, TM_sendack);
|
||||
}
|
||||
tp_soisdisconnecting($P.tp_sock);
|
||||
tp_indicate(ER_TPDU, $P, $$.e_reason);
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
(void) tp_emit(DR_TPDU_type, $P, 0, E_TP_PROTO_ERR, MNULL);
|
||||
}
|
||||
;
|
||||
@ -549,7 +561,7 @@ TP_CLOSING <== [ TP_AKWAIT, TP_OPEN ] ER_TPDU
|
||||
TP_OPEN <== TP_CRSENT CC_TPDU
|
||||
($P.tp_class == TP_CLASS_0)
|
||||
{
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
IncStat(ts_tp0_conn);
|
||||
$P.tp_fcredit = 1;
|
||||
soisconnected($P.tp_sock);
|
||||
@ -566,11 +578,10 @@ TP_OPEN <== TP_CRSENT CC_TPDU
|
||||
IncStat(ts_tp4_conn);
|
||||
$P.tp_fref = $$.e_sref;
|
||||
$P.tp_fcredit = $$.e_cdt;
|
||||
$P.tp_ackrcvd = 0;
|
||||
if (($P.tp_rx_strat & TPRX_FASTSTART) && ($$.e_cdt > 0))
|
||||
$P.tp_cong_win = $$.e_cdt;
|
||||
$P.tp_cong_win = $$.e_cdt * $P.tp_l_tpdusize;
|
||||
tp_getoptions($P);
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
if ($P.tp_ucddata) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf("dropping user connect data cc 0x%x\n",
|
||||
@ -587,7 +598,7 @@ TP_OPEN <== TP_CRSENT CC_TPDU
|
||||
}
|
||||
|
||||
(void) tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 0, MNULL);
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -599,8 +610,7 @@ SAME <== TP_CRSENT TM_retrans
|
||||
int error;
|
||||
|
||||
IncStat(ts_retrans_cr);
|
||||
$P.tp_cong_win = 1;
|
||||
$P.tp_ackrcvd = 0;
|
||||
$P.tp_cong_win = 1 * $P.tp_l_tpdusize;
|
||||
data = MCPY($P.tp_ucddata, M_NOWAIT);
|
||||
if($P.tp_ucddata) {
|
||||
IFDEBUG(D_CONN)
|
||||
@ -615,7 +625,7 @@ SAME <== TP_CRSENT TM_retrans
|
||||
if( error = tp_emit(CR_TPDU_type, $P, 0, 0, data) ) {
|
||||
$P.tp_sock->so_error = error;
|
||||
}
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_cr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_cr_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -645,7 +655,7 @@ SAME <== TP_AKWAIT CR_TPDU
|
||||
$P.tp_sock->so_error = error;
|
||||
}
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_cc_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_cc_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -664,11 +674,10 @@ TP_OPEN <== TP_AKWAIT DT_TPDU
|
||||
m_freem($P.tp_ucddata);
|
||||
$P.tp_ucddata = 0;
|
||||
}
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
soisconnected($P.tp_sock);
|
||||
tp_getoptions($P);
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
|
||||
/* see also next 2 transitions, if you make any changes */
|
||||
|
||||
@ -677,11 +686,11 @@ TP_OPEN <== TP_AKWAIT DT_TPDU
|
||||
printf("tp_stash returns %d\n",doack);
|
||||
ENDDEBUG
|
||||
|
||||
if(doack) {
|
||||
if (doack) {
|
||||
(void) tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 0, MNULL );
|
||||
tp_ctimeout($P.tp_refp, TM_sendack, (int)$P.tp_keepalive_ticks);
|
||||
tp_ctimeout($P, TM_sendack, (int)$P.tp_keepalive_ticks);
|
||||
} else
|
||||
tp_ctimeout( $P.tp_refp, TM_sendack, (int)$P.tp_sendack_ticks);
|
||||
tp_ctimeout( $P, TM_sendack, (int)$P.tp_sendack_ticks);
|
||||
|
||||
IFDEBUG(D_DATA)
|
||||
printf("after stash calling sbwakeup\n");
|
||||
@ -708,7 +717,7 @@ SAME <== TP_OPEN DT_TPDU
|
||||
{
|
||||
int doack; /* tells if we must ack immediately */
|
||||
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
sbwakeup( &$P.tp_sock->so_rcv );
|
||||
|
||||
doack = tp_stash($P, $E);
|
||||
@ -719,7 +728,7 @@ SAME <== TP_OPEN DT_TPDU
|
||||
if(doack)
|
||||
(void) tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 0, MNULL );
|
||||
else
|
||||
tp_ctimeout_MIN( $P.tp_refp, TM_sendack, (int)$P.tp_sendack_ticks);
|
||||
tp_ctimeout_MIN( $P, TM_sendack, (int)$P.tp_sendack_ticks);
|
||||
|
||||
IFDEBUG(D_DATA)
|
||||
printf("after stash calling sbwakeup\n");
|
||||
@ -746,7 +755,7 @@ SAME <== [ TP_OPEN, TP_AKWAIT ] DT_TPDU
|
||||
ENDTRACE
|
||||
IncStat(ts_dt_niw);
|
||||
m_freem($$.e_data);
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
(void) tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 0, MNULL );
|
||||
}
|
||||
;
|
||||
@ -760,9 +769,8 @@ TP_OPEN <== TP_AKWAIT AK_TPDU
|
||||
$P.tp_ucddata = 0;
|
||||
}
|
||||
(void) tp_goodack($P, $$.e_cdt, $$.e_seq, $$.e_subseq);
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
|
||||
tp_getoptions($P);
|
||||
soisconnected($P.tp_sock);
|
||||
IFTRACE(D_CONN)
|
||||
struct socket *so = $P.tp_sock;
|
||||
@ -774,8 +782,8 @@ TP_OPEN <== TP_AKWAIT AK_TPDU
|
||||
so->so_qlen, so->so_error, so->so_rcv.sb_cc, so->so_head);
|
||||
ENDTRACE
|
||||
|
||||
tp_ctimeout($P.tp_refp, TM_sendack, (int)$P.tp_keepalive_ticks);
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_sendack, (int)$P.tp_keepalive_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -788,11 +796,10 @@ TP_OPEN <== [ TP_OPEN, TP_AKWAIT ] XPD_TPDU
|
||||
m_freem($P.tp_ucddata);
|
||||
$P.tp_ucddata = 0;
|
||||
}
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_getoptions($P);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
soisconnected($P.tp_sock);
|
||||
tp_ctimeout($P.tp_refp, TM_sendack, (int)$P.tp_keepalive_ticks);
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_sendack, (int)$P.tp_keepalive_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
}
|
||||
IFTRACE(D_XPD)
|
||||
tptrace(TPPTmisc, "XPD tpdu accepted Xrcvnxt, e_seq datalen m_len\n",
|
||||
@ -860,7 +867,7 @@ SAME <== [ TP_AKWAIT, TP_OPEN ] XPD_TPDU
|
||||
IncStat(ts_xpd_dup);
|
||||
}
|
||||
m_freem($$.e_data);
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
/* don't send an xack because the xak gives "last one received", not
|
||||
* "next one i expect" (dumb)
|
||||
*/
|
||||
@ -906,7 +913,7 @@ TP_CLOSING <== [ TP_CLOSING, TP_AKWAIT, TP_CRSENT, TP_CONFIRMING ] T_DETACH
|
||||
data = MCPY($P.tp_ucddata, M_NOWAIT);
|
||||
(void) tp_emit(DR_TPDU_type, $P, 0, E_TP_NORMAL_DISC, data);
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
}
|
||||
}
|
||||
;
|
||||
@ -927,9 +934,10 @@ TP_CLOSING <== [ TP_AKWAIT, TP_OPEN, TP_CRSENT, TP_CONFIRMING ] T_DISC_req
|
||||
struct mbuf *data = MCPY($P.tp_ucddata, M_WAIT);
|
||||
|
||||
if($P.tp_state == TP_OPEN) {
|
||||
tp_euntimeout($P.tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P.tp_refp, TM_inact);
|
||||
tp_cuntimeout($P.tp_refp, TM_sendack);
|
||||
tp_euntimeout($P, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P, TM_inact);
|
||||
tp_cuntimeout($P, TM_sendack);
|
||||
$P.tp_flags &= ~TPF_DELACK;
|
||||
}
|
||||
if (data) {
|
||||
IFDEBUG(D_CONN)
|
||||
@ -940,7 +948,7 @@ TP_CLOSING <== [ TP_AKWAIT, TP_OPEN, TP_CRSENT, TP_CONFIRMING ] T_DISC_req
|
||||
}
|
||||
tp_soisdisconnecting($P.tp_sock);
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
|
||||
if( trick_hc )
|
||||
return tp_emit(DR_TPDU_type, $P, 0, $$.e_reason, data);
|
||||
@ -956,12 +964,11 @@ SAME <== TP_AKWAIT TM_retrans
|
||||
|
||||
IncStat(ts_retrans_cc);
|
||||
$P.tp_retrans --;
|
||||
$P.tp_cong_win = 1;
|
||||
$P.tp_ackrcvd = 0;
|
||||
$P.tp_cong_win = 1 * $P.tp_l_tpdusize;
|
||||
|
||||
if( error = tp_emit(CC_TPDU_type, $P, 0, 0, data) )
|
||||
$P.tp_sock->so_error = error;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_cc_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_cc_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -975,7 +982,7 @@ TP_CLOSING <== TP_AKWAIT TM_retrans
|
||||
tp_indicate(T_DISCONNECT, $P, ETIMEDOUT);
|
||||
(void) tp_emit(DR_TPDU_type, $P, 0, E_TP_CONGEST, MNULL);
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -988,9 +995,9 @@ TP_CLOSING <== TP_AKWAIT TM_retrans
|
||||
TP_CLOSING <== TP_OPEN [ TM_inact, TM_retrans, TM_data_retrans ]
|
||||
DEFAULT
|
||||
{
|
||||
tp_euntimeout($P.tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P.tp_refp, TM_inact);
|
||||
tp_cuntimeout($P.tp_refp, TM_sendack);
|
||||
tp_euntimeout($P, TM_data_retrans); /* all */
|
||||
tp_cuntimeout($P, TM_inact);
|
||||
tp_cuntimeout($P, TM_sendack);
|
||||
|
||||
IncStat(ts_conn_gaveup);
|
||||
tp_soisdisconnecting($P.tp_sock);
|
||||
@ -998,7 +1005,7 @@ TP_CLOSING <== TP_OPEN [ TM_inact, TM_retrans, TM_data_retrans ]
|
||||
tp_indicate(T_DISCONNECT, $P, ETIMEDOUT);
|
||||
(void) tp_emit(DR_TPDU_type, $P, 0, E_TP_CONGEST_2, MNULL);
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -1006,18 +1013,15 @@ TP_CLOSING <== TP_OPEN [ TM_inact, TM_retrans, TM_data_retrans ]
|
||||
SAME <== TP_OPEN TM_retrans
|
||||
( $P.tp_retrans > 0 )
|
||||
{
|
||||
$P.tp_cong_win = 1;
|
||||
$P.tp_ackrcvd = 0;
|
||||
$P.tp_cong_win = 1 * $P.tp_l_tpdusize;
|
||||
/* resume XPD */
|
||||
if ( $P.tp_Xsnd.sb_mb ) {
|
||||
struct mbuf *m = m_copy($P.tp_Xsnd.sb_mb, 0, (int)$P.tp_Xsnd.sb_cc);
|
||||
/* m_copy doesn't preserve the m_xlink field, but at this pt.
|
||||
* that doesn't matter
|
||||
*/
|
||||
int shift;
|
||||
|
||||
IFTRACE(D_XPD)
|
||||
tptrace(TPPTmisc, "XPD retrans: Xuna Xsndnxt sndhiwat snduna",
|
||||
$P.tp_Xuna, $P.tp_Xsndnxt, $P.tp_sndhiwat,
|
||||
tptrace(TPPTmisc, "XPD retrans: Xuna Xsndnxt sndnxt snduna",
|
||||
$P.tp_Xuna, $P.tp_Xsndnxt, $P.tp_sndnxt,
|
||||
$P.tp_snduna);
|
||||
ENDTRACE
|
||||
IFDEBUG(D_XPD)
|
||||
@ -1025,68 +1029,19 @@ SAME <== TP_OPEN TM_retrans
|
||||
ENDDEBUG
|
||||
IncStat(ts_retrans_xpd);
|
||||
$P.tp_retrans --;
|
||||
shift = max($P.tp_Nretrans - $P.tp_retrans, 6);
|
||||
(void) tp_emit(XPD_TPDU_type, $P, $P.tp_Xuna, 1, m);
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_xpd_ticks);
|
||||
tp_ctimeout($P, TM_retrans, ((int)$P.tp_dt_ticks) << shift);
|
||||
}
|
||||
}
|
||||
;
|
||||
|
||||
/* TP4 only */
|
||||
SAME <== TP_OPEN TM_data_retrans
|
||||
( $$.e_retrans > 0 )
|
||||
($P.tp_rxtshift < TP_NRETRANS)
|
||||
{
|
||||
register SeqNum low, lowsave = 0;
|
||||
register struct tp_rtc *r = $P.tp_snduna_rtc;
|
||||
register struct mbuf *m;
|
||||
register SeqNum high = $$.e_high;
|
||||
|
||||
low = $P.tp_snduna;
|
||||
lowsave = high = low;
|
||||
|
||||
tp_euntimeout_lss($P.tp_refp, TM_data_retrans,
|
||||
SEQ_ADD($P, $P.tp_sndhiwat, 1));
|
||||
$P.tp_retrans_hiwat = $P.tp_sndhiwat;
|
||||
|
||||
if (($P.tp_rx_strat & TPRX_EACH) == 0)
|
||||
high = (high>low)?low:high;
|
||||
|
||||
if( $P.tp_rx_strat & TPRX_USE_CW ) {
|
||||
register int i;
|
||||
|
||||
$P.tp_cong_win = 1;
|
||||
$P.tp_ackrcvd = 0;
|
||||
i = SEQ_ADD($P, low, $P.tp_cong_win);
|
||||
|
||||
high = SEQ_MIN($P, high, $P.tp_sndhiwat);
|
||||
|
||||
}
|
||||
|
||||
while( SEQ_LEQ($P, low, high) ){
|
||||
if ( r == (struct tp_rtc *)0 ){
|
||||
IFDEBUG(D_RTC)
|
||||
printf( "tp: retrans rtc list is GONE!\n");
|
||||
ENDDEBUG
|
||||
break;
|
||||
}
|
||||
if ( r->tprt_seq == low ){
|
||||
if(( m = m_copy(r->tprt_data, 0, r->tprt_octets ))== MNULL)
|
||||
break;
|
||||
(void) tp_emit(DT_TPDU_type, $P, low, r->tprt_eot, m);
|
||||
IncStat(ts_retrans_dt);
|
||||
SEQ_INC($P, low );
|
||||
}
|
||||
r = r->tprt_next;
|
||||
}
|
||||
/* CE_BIT
|
||||
if ( SEQ_LEQ($P, lowsave, high) ){
|
||||
*/
|
||||
$$.e_retrans --;
|
||||
tp_etimeout($P.tp_refp, TM_data_retrans, (caddr_t)lowsave,
|
||||
(caddr_t)high, $$.e_retrans,
|
||||
($P.tp_Nretrans - $$.e_retrans) * (int)$P.tp_dt_ticks);
|
||||
/* CE_BIT
|
||||
}
|
||||
*/
|
||||
$P.tp_rxtshift++;
|
||||
(void) tp_data_retrans($P);
|
||||
}
|
||||
;
|
||||
|
||||
@ -1097,7 +1052,7 @@ SAME <== TP_CLOSING TM_retrans
|
||||
$P.tp_retrans --;
|
||||
(void) tp_emit(DR_TPDU_type, $P, 0, E_TP_DR_NO_REAS, MNULL);
|
||||
IncStat(ts_retrans_dr);
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_dr_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -1106,9 +1061,9 @@ TP_REFWAIT <== TP_CLOSING TM_retrans
|
||||
DEFAULT /* no more retrans - gave up */
|
||||
{
|
||||
$P.tp_sock->so_error = ETIMEDOUT;
|
||||
$P.tp_refp->tpr_state = REF_FROZEN;
|
||||
$P.tp_refstate = REF_FROZEN;
|
||||
tp_recycle_tsuffix( $P );
|
||||
tp_etimeout($P.tp_refp, TM_reference, 0,0,0, (int)$P.tp_refer_ticks);
|
||||
tp_etimeout($P, TM_reference, (int)$P.tp_refer_ticks);
|
||||
}
|
||||
;
|
||||
|
||||
@ -1120,7 +1075,7 @@ TP_REFWAIT <== TP_CLOSING TM_retrans
|
||||
TP_CLOSED <== TP_REFWAIT TM_reference
|
||||
DEFAULT
|
||||
{
|
||||
tp_freeref($P.tp_refp);
|
||||
tp_freeref($P.tp_lref);
|
||||
tp_detach($P);
|
||||
}
|
||||
;
|
||||
@ -1131,7 +1086,7 @@ SAME <== TP_OPEN [ CR_TPDU, CC_TPDU ]
|
||||
DEFAULT
|
||||
{
|
||||
if( $P.tp_class != TP_CLASS_0) {
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
if ( $E.ev_number == CC_TPDU )
|
||||
(void) tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 0, MNULL);
|
||||
}
|
||||
@ -1144,8 +1099,8 @@ SAME <== TP_OPEN T_DATA_req
|
||||
DEFAULT
|
||||
{
|
||||
IFTRACE(D_DATA)
|
||||
tptrace(TPPTmisc, "T_DATA_req sndhiwat snduna fcredit, tpcb",
|
||||
$P.tp_sndhiwat, $P.tp_snduna, $P.tp_fcredit, $P);
|
||||
tptrace(TPPTmisc, "T_DATA_req sndnxt snduna fcredit, tpcb",
|
||||
$P.tp_sndnxt, $P.tp_snduna, $P.tp_fcredit, $P);
|
||||
ENDTRACE
|
||||
|
||||
tp_send($P);
|
||||
@ -1170,8 +1125,8 @@ SAME <== TP_OPEN T_XPD_req
|
||||
*/
|
||||
|
||||
IFTRACE(D_XPD)
|
||||
tptrace(TPPTmisc, "XPD req: Xuna Xsndnxt sndhiwat snduna",
|
||||
$P.tp_Xuna, $P.tp_Xsndnxt, $P.tp_sndhiwat,
|
||||
tptrace(TPPTmisc, "XPD req: Xuna Xsndnxt sndnxt snduna",
|
||||
$P.tp_Xuna, $P.tp_Xsndnxt, $P.tp_sndnxt,
|
||||
$P.tp_snduna);
|
||||
ENDTRACE
|
||||
IFDEBUG(D_XPD)
|
||||
@ -1181,7 +1136,8 @@ SAME <== TP_OPEN T_XPD_req
|
||||
error =
|
||||
tp_emit(XPD_TPDU_type, $P, $P.tp_Xuna, 1, m);
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_xpd_ticks);
|
||||
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_rxtcur);
|
||||
SEQ_INC($P, $P.tp_Xsndnxt);
|
||||
}
|
||||
if(trick_hc)
|
||||
@ -1198,59 +1154,17 @@ SAME <== TP_OPEN AK_TPDU
|
||||
* OR no news but the credit should be processed.
|
||||
*/
|
||||
{
|
||||
struct sockbuf *sb = &$P.tp_sock->so_snd;
|
||||
|
||||
IFDEBUG(D_ACKRECV)
|
||||
printf("GOOD ACK seq 0x%x cdt 0x%x\n", $$.e_seq, $$.e_cdt);
|
||||
ENDDEBUG
|
||||
if( $P.tp_class != TP_CLASS_0) {
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_euntimeout_lss($P.tp_refp, TM_data_retrans, $$.e_seq);
|
||||
}
|
||||
sbwakeup( &$P.tp_sock->so_snd );
|
||||
|
||||
if ($P.tp_sndhiwat <= $P.tp_retrans_hiwat &&
|
||||
$P.tp_snduna <= $P.tp_retrans_hiwat) {
|
||||
|
||||
register struct mbuf *m;
|
||||
/* extern struct mbuf *m_copy(); */
|
||||
register struct tp_rtc *r;
|
||||
SeqNum high, retrans, low_save;
|
||||
|
||||
high = SEQ_MIN($P, SEQ_ADD($P, $P.tp_snduna,
|
||||
MIN($P.tp_cong_win, $P.tp_fcredit)) - 1,
|
||||
$P.tp_sndhiwat);
|
||||
low_save = retrans = SEQ_MAX($P, SEQ_ADD($P, $P.tp_last_retrans, 1),
|
||||
$P.tp_snduna);
|
||||
for (; SEQ_LEQ($P, retrans, high); SEQ_INC($P, retrans)) {
|
||||
|
||||
for (r = $P.tp_snduna_rtc; r; r = r->tprt_next){
|
||||
if ( r->tprt_seq == retrans ){
|
||||
if(( m = m_copy(r->tprt_data, 0, r->tprt_octets ))
|
||||
== MNULL)
|
||||
break;
|
||||
(void) tp_emit(DT_TPDU_type, $P, retrans,
|
||||
r->tprt_eot, m);
|
||||
$P.tp_last_retrans = retrans;
|
||||
IncStat(ts_retrans_dt);
|
||||
break;
|
||||
}
|
||||
}
|
||||
if ( r == (struct tp_rtc *)0 ){
|
||||
IFDEBUG(D_RTC)
|
||||
printf( "tp: retrans rtc list is GONE!\n");
|
||||
ENDDEBUG
|
||||
break;
|
||||
}
|
||||
}
|
||||
tp_etimeout($P.tp_refp, TM_data_retrans, (caddr_t)low_save,
|
||||
(caddr_t)high, $P.tp_retrans, (int)$P.tp_dt_ticks);
|
||||
if (SEQ_DEC($P, retrans) == $P.tp_retrans_hiwat)
|
||||
tp_send($P);
|
||||
}
|
||||
else {
|
||||
tp_send($P);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
}
|
||||
sbwakeup(sb);
|
||||
IFDEBUG(D_ACKRECV)
|
||||
printf("GOOD ACK new sndhiwat 0x%x\n", $P.tp_sndhiwat);
|
||||
printf("GOOD ACK new sndnxt 0x%x\n", $P.tp_sndnxt);
|
||||
ENDDEBUG
|
||||
}
|
||||
;
|
||||
@ -1270,7 +1184,7 @@ SAME <== TP_OPEN AK_TPDU
|
||||
IncStat( ts_ackreason[_ACK_FCC_] );
|
||||
(void) tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 1, MNULL);
|
||||
}
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
}
|
||||
}
|
||||
;
|
||||
@ -1284,7 +1198,7 @@ SAME <== TP_OPEN AK_TPDU
|
||||
|
||||
(void) tp_emit(XPD_TPDU_type, $P, $P.tp_Xuna, 1, m);
|
||||
$P.tp_retrans = $P.tp_Nretrans;
|
||||
tp_ctimeout($P.tp_refp, TM_retrans, (int)$P.tp_xpd_ticks);
|
||||
tp_ctimeout($P, TM_retrans, (int)$P.tp_xpd_ticks);
|
||||
SEQ_INC($P, $P.tp_Xsndnxt);
|
||||
}
|
||||
*/
|
||||
@ -1298,8 +1212,8 @@ SAME <== TP_OPEN XAK_TPDU
|
||||
* also updates tp_Xuna
|
||||
*/
|
||||
{
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_cuntimeout($P.tp_refp, TM_retrans);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_cuntimeout($P, TM_retrans);
|
||||
|
||||
sbwakeup( &$P.tp_sock->so_snd );
|
||||
|
||||
@ -1316,7 +1230,7 @@ SAME <== TP_OPEN XAK_TPDU
|
||||
tptrace(TPPTmisc, "BOGUS XACK eventtype ", $E.ev_number, 0, 0,0);
|
||||
ENDTRACE
|
||||
if( $P.tp_class != TP_CLASS_0 ) {
|
||||
tp_ctimeout($P.tp_refp, TM_inact, (int)$P.tp_inact_ticks);
|
||||
tp_ctimeout($P, TM_inact, (int)$P.tp_inact_ticks);
|
||||
}
|
||||
}
|
||||
;
|
||||
@ -1325,12 +1239,20 @@ SAME <== TP_OPEN XAK_TPDU
|
||||
SAME <== TP_OPEN TM_sendack
|
||||
DEFAULT
|
||||
{
|
||||
int timo;
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTsendack, -1, $P.tp_lcredit, $P.tp_sent_uwe,
|
||||
$P.tp_sent_lcdt, 0);
|
||||
ENDTRACE
|
||||
IncPStat($P, tps_n_TMsendack);
|
||||
(void) tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 0, MNULL);
|
||||
if ($P.tp_fcredit == 0) {
|
||||
if ($P.tp_rxtshift < TP_MAXRXTSHIFT)
|
||||
$P.tp_rxtshift++;
|
||||
timo = ($P.tp_dt_ticks) << $P.tp_rxtshift;
|
||||
} else
|
||||
timo = $P.tp_sendack_ticks;
|
||||
tp_ctimeout($P, TM_sendack, timo);
|
||||
}
|
||||
;
|
||||
|
||||
@ -1357,14 +1279,22 @@ SAME <== TP_OPEN T_USR_rcvd
|
||||
DEFAULT
|
||||
{
|
||||
if( trick_hc ) {
|
||||
IncStat(ts_ackreason[_ACK_USRRCV_]);
|
||||
|
||||
/* send an ACK only if there's new information */
|
||||
LOCAL_CREDIT( $P );
|
||||
if (($P.tp_rcvnxt != $P.tp_sent_rcvnxt) ||
|
||||
($P.tp_lcredit != $P.tp_sent_lcdt))
|
||||
|
||||
SeqNum ack_thresh;
|
||||
/*
|
||||
* If the upper window edge has advanced a reasonable
|
||||
* amount beyond what was known, send an ACK.
|
||||
* A reasonable amount is 2 packets, unless the max window
|
||||
* is only 1 or 2 packets, in which case we
|
||||
* should send an ack for any advance in the upper window edge.
|
||||
*/
|
||||
LOCAL_CREDIT($P);
|
||||
ack_thresh = SEQ_SUB($P, $P.tp_lcredit + $P.tp_rcvnxt,
|
||||
($P.tp_maxlcredit > 2 ? 2 : 1));
|
||||
if (SEQ_GT($P, ack_thresh, $P.tp_sent_uwe)) {
|
||||
IncStat(ts_ackreason[_ACK_USRRCV_]);
|
||||
$P.tp_flags &= ~TPF_DELACK;
|
||||
return tp_emit(AK_TPDU_type, $P, $P.tp_rcvnxt, 0, MNULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
;
|
||||
|
75
sys/netiso/tp_astring.c
Normal file
75
sys/netiso/tp_astring.c
Normal file
@ -0,0 +1,75 @@
|
||||
/*-
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_astring.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_astring.c,v 1.1 1994/05/13 06:09:09 mycroft Exp $
|
||||
*/
|
||||
|
||||
char *tp_sstring[] = {
|
||||
"ST_ERROR(0x0)",
|
||||
"TP_CLOSED(0x1)",
|
||||
"TP_CRSENT(0x2)",
|
||||
"TP_AKWAIT(0x3)",
|
||||
"TP_OPEN(0x4)",
|
||||
"TP_CLOSING(0x5)",
|
||||
"TP_REFWAIT(0x6)",
|
||||
"TP_LISTENING(0x7)",
|
||||
"TP_CONFIRMING(0x8)",
|
||||
};
|
||||
|
||||
char *tp_estring[] = {
|
||||
"TM_inact(0x0)",
|
||||
"TM_retrans(0x1)",
|
||||
"TM_sendack(0x2)",
|
||||
"TM_notused(0x3)",
|
||||
"TM_reference(0x4)",
|
||||
"TM_data_retrans(0x5)",
|
||||
"ER_TPDU(0x6)",
|
||||
"CR_TPDU(0x7)",
|
||||
"DR_TPDU(0x8)",
|
||||
"DC_TPDU(0x9)",
|
||||
"CC_TPDU(0xa)",
|
||||
"AK_TPDU(0xb)",
|
||||
"DT_TPDU(0xc)",
|
||||
"XPD_TPDU(0xd)",
|
||||
"XAK_TPDU(0xe)",
|
||||
"T_CONN_req(0xf)",
|
||||
"T_DISC_req(0x10)",
|
||||
"T_LISTEN_req(0x11)",
|
||||
"T_DATA_req(0x12)",
|
||||
"T_XPD_req(0x13)",
|
||||
"T_USR_rcvd(0x14)",
|
||||
"T_USR_Xrcvd(0x15)",
|
||||
"T_DETACH(0x16)",
|
||||
"T_NETRESET(0x17)",
|
||||
"T_ACPT_req(0x18)",
|
||||
};
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_clnp.h 7.3 (Berkeley) 5/6/91
|
||||
* $Id: tp_clnp.h,v 1.3 1993/05/20 05:27:30 cgd Exp $
|
||||
* from: @(#)tp_clnp.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_clnp.h,v 1.4 1994/05/13 06:09:11 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_CLNP_H_
|
||||
#define _NETISO_TP_CLNP_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,28 +61,28 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* AF_ISO net-dependent structures and include files
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_CLNP_H_
|
||||
#define _NETISO_TP_CLNP_H_
|
||||
|
||||
#ifndef SOCK_STREAM
|
||||
#include "socket.h"
|
||||
#endif SOCK_STREAM
|
||||
#include <sys/socket.h>
|
||||
#endif /* SOCK_STREAM */
|
||||
|
||||
#ifndef RTFREE
|
||||
#include "../net/route.h"
|
||||
#include <net/route.h>
|
||||
#endif
|
||||
#include "../netiso/iso.h"
|
||||
#include "../netiso/clnp.h"
|
||||
#include "../netiso/iso_pcb.h"
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/clnp.h>
|
||||
#include <netiso/iso_pcb.h>
|
||||
#ifndef IF_DEQUEUE
|
||||
#include "../net/if.h"
|
||||
#include <net/if.h>
|
||||
#endif
|
||||
#include "../netiso/iso_var.h"
|
||||
#include <netiso/iso_var.h>
|
||||
|
||||
struct isopcb tp_isopcb;
|
||||
/* queue of active inpcbs for tp ; for tp with dod ip */
|
||||
|
||||
#endif /* !_NETISO_TP_CLNP_H_ */
|
||||
#endif /* _NETISO_TP_CLNP_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_cons.c 7.8 (Berkeley) 5/9/91
|
||||
* $Id: tp_cons.c,v 1.4 1993/12/18 04:58:03 mycroft Exp $
|
||||
* from: @(#)tp_cons.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_cons.c,v 1.5 1994/05/13 06:09:12 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* Here is where you find the iso- and cons-dependent code. We've tried
|
||||
* keep all net-level and (primarily) address-family-dependent stuff
|
||||
* out of the tp source, and everthing here is reached indirectly
|
||||
@ -107,7 +105,6 @@ SOFTWARE.
|
||||
#include <netccitt/pk_var.h>
|
||||
|
||||
#include <netiso/if_cons.c>
|
||||
|
||||
int tpcons_output();
|
||||
|
||||
/*
|
||||
@ -146,22 +143,24 @@ register struct mbuf *nam;
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* THIS MAYBE BELONGS IN SOME OTHER PLACE??? but i think not -
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tpcons_ctlinput(cmd, siso, isop)
|
||||
int cmd;
|
||||
struct sockaddr_iso *siso;
|
||||
struct isopcb *isop;
|
||||
{
|
||||
register struct tp_pcb *tpcb = 0;
|
||||
|
||||
if (isop->isop_socket)
|
||||
tpcb = (struct tp_pcb *)isop->isop_socket->so_pcb;
|
||||
switch (cmd) {
|
||||
|
||||
case PRC_CONS_SEND_DONE:
|
||||
if( isop->isop_socket ) { /* tp 0 only */
|
||||
register struct tp_pcb *tpcb =
|
||||
(struct tp_pcb *)isop->isop_socket->so_tpcb;
|
||||
if (tpcb) {
|
||||
struct tp_event E;
|
||||
int error = 0;
|
||||
|
||||
if( tpcb->tp_class == TP_CLASS_0 ) {
|
||||
if (tpcb->tp_class == TP_CLASS_0) {
|
||||
/* only if class is exactly class zero, not
|
||||
* still in class negotiation
|
||||
*/
|
||||
@ -184,18 +183,17 @@ tpcons_ctlinput(cmd, siso, isop)
|
||||
tpcb->tp_sock->so_error = error;
|
||||
}
|
||||
} /* else ignore it */
|
||||
}
|
||||
}
|
||||
break;
|
||||
case PRC_ROUTEDEAD:
|
||||
if( isop->isop_socket ) { /* tp 0 only */
|
||||
if (tpcb && tpcb->tp_class == TP_CLASS_0) {
|
||||
tpiso_reset(isop);
|
||||
break;
|
||||
} /* else drop through */
|
||||
default:
|
||||
(void) tpclnp_ctlinput(cmd, siso);
|
||||
tpclnp_ctlinput(cmd, siso);
|
||||
break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -206,14 +204,14 @@ tpcons_ctlinput(cmd, siso, isop)
|
||||
* ignore the socket argument, and call tp_input.
|
||||
* No return value.
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tpcons_input(m, faddr, laddr, channel)
|
||||
struct mbuf *m;
|
||||
struct sockaddr_iso *faddr, *laddr;
|
||||
caddr_t channel;
|
||||
{
|
||||
if( m == MNULL)
|
||||
return 0;
|
||||
return;
|
||||
|
||||
m = (struct mbuf *)tp_inputprep(m);
|
||||
|
||||
@ -222,7 +220,6 @@ tpcons_input(m, faddr, laddr, channel)
|
||||
dump_buf( m, 12+ m->m_len);
|
||||
ENDDEBUG
|
||||
tp_input(m, faddr, laddr, channel, tpcons_output, 0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -262,9 +259,25 @@ tpcons_output(isop, m0, datalen, nochksum)
|
||||
m->m_next = m0;
|
||||
}
|
||||
m->m_pkthdr.len = datalen;
|
||||
error = pk_send(isop->isop_chan, m);
|
||||
IncStat(ts_tpdu_sent);
|
||||
|
||||
if (isop->isop_chan == 0) {
|
||||
/* got a restart maybe? */
|
||||
if ((isop->isop_chan = (caddr_t) pk_attach((struct socket *)0)) == 0) {
|
||||
IFDEBUG(D_CCONS)
|
||||
printf("tpcons_output: no pklcd\n");
|
||||
ENDDEBUG
|
||||
error = ENOBUFS;
|
||||
}
|
||||
if (error = cons_connect(isop)) {
|
||||
pk_disconnect((struct pklcd *)isop->isop_chan);
|
||||
isop->isop_chan = 0;
|
||||
IFDEBUG(D_CCONS)
|
||||
printf("tpcons_output: can't reconnect\n");
|
||||
ENDDEBUG
|
||||
}
|
||||
} else {
|
||||
error = pk_send(isop->isop_chan, m);
|
||||
IncStat(ts_tpdu_sent);
|
||||
}
|
||||
return error;
|
||||
}
|
||||
/*
|
||||
@ -286,5 +299,5 @@ tpcons_dg_output(chan, m0, datalen)
|
||||
{
|
||||
return tpcons_output(((struct pklcd *)chan)->lcd_upnext, m0, datalen, 0);
|
||||
}
|
||||
#endif TPCONS
|
||||
#endif ISO
|
||||
#endif /* TPCONS */
|
||||
#endif /* ISO */
|
||||
|
@ -1,17 +1,19 @@
|
||||
/* $Id: tp_driver.c,v 1.4 1993/12/18 04:55:38 mycroft Exp $ */
|
||||
|
||||
#define _XEBEC_PG static
|
||||
|
||||
#include <netiso/tp_states.h>
|
||||
#include "tp_states.h"
|
||||
|
||||
static struct act_ent {
|
||||
int a_newstate;
|
||||
int a_action;
|
||||
} statetable[] = { {0,0},
|
||||
#include <netiso/tp_states.init>
|
||||
#include "tp_states.init"
|
||||
};
|
||||
|
||||
/* from: @(#)tp.trans 8.1 (Berkeley) 6/10/93 */
|
||||
/* $Id: tp_driver.c,v 1.5 1994/05/13 06:09:15 mycroft Exp $ */
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/protosw.h>
|
||||
@ -42,9 +44,11 @@ int tp_emit(),
|
||||
void tp_indicate(), tp_getoptions(),
|
||||
tp_soisdisconnecting(), tp_soisdisconnected(),
|
||||
tp_recycle_tsuffix(),
|
||||
#ifdef TP_DEBUG_TIMERS
|
||||
tp_etimeout(), tp_euntimeout(),
|
||||
tp_euntimeout_lss(), tp_ctimeout(),
|
||||
tp_cuntimeout(), tp_ctimeout_MIN(),
|
||||
tp_ctimeout(), tp_cuntimeout(),
|
||||
tp_ctimeout_MIN(),
|
||||
#endif
|
||||
tp_freeref(), tp_detach(),
|
||||
tp0_stash(), tp0_send(),
|
||||
tp_netcmd(), tp_send()
|
||||
@ -56,7 +60,7 @@ typedef struct tp_pcb tpcb_struct;
|
||||
|
||||
typedef tpcb_struct tp_PCB_;
|
||||
|
||||
#include <netiso/tp_events.h>
|
||||
#include "tp_events.h"
|
||||
|
||||
_XEBEC_PG int _Xebec_action(a,e,p)
|
||||
int a;
|
||||
@ -95,7 +99,7 @@ case 0x4:
|
||||
break;
|
||||
case 0x5:
|
||||
{
|
||||
p->tp_refp->tpr_state = REF_OPEN; /* has timers ??? */
|
||||
p->tp_refstate = REF_OPEN; /* has timers ??? */
|
||||
}
|
||||
break;
|
||||
case 0x6:
|
||||
@ -106,7 +110,7 @@ case 0x6:
|
||||
IFDEBUG(D_CONN)
|
||||
printf("CR datalen 0x%x data 0x%x", e->ev_union.EV_CR_TPDU.e_datalen, e->ev_union.EV_CR_TPDU.e_data);
|
||||
ENDDEBUG
|
||||
p->tp_refp->tpr_state = REF_OPEN; /* has timers */
|
||||
p->tp_refstate = REF_OPEN; /* has timers */
|
||||
p->tp_fcredit = e->ev_union.EV_CR_TPDU.e_cdt;
|
||||
|
||||
if (e->ev_union.EV_CR_TPDU.e_datalen > 0) {
|
||||
@ -140,23 +144,22 @@ case 0x8:
|
||||
IFDEBUG(D_CONN)
|
||||
printf("Confirming connection: p" );
|
||||
ENDDEBUG
|
||||
tp_getoptions(p);
|
||||
soisconnecting(p->tp_sock);
|
||||
if ((p->tp_rx_strat & TPRX_FASTSTART) && (p->tp_fcredit > 0))
|
||||
p->tp_cong_win = p->tp_fcredit;
|
||||
p->tp_cong_win = p->tp_fcredit * p->tp_l_tpdusize;
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_cc_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_cc_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x9:
|
||||
{
|
||||
register struct tp_ref *r = p->tp_refp;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("event: CR_TPDU emit CC failed done " );
|
||||
ENDDEBUG
|
||||
soisdisconnected(p->tp_sock);
|
||||
tp_recycle_tsuffix( p );
|
||||
tp_freeref(r);
|
||||
tp_recycle_tsuffix(p);
|
||||
tp_freeref(p->tp_lref);
|
||||
tp_detach(p);
|
||||
}
|
||||
break;
|
||||
@ -181,10 +184,10 @@ case 0xa:
|
||||
if (error = tp_emit(CR_TPDU_type, p, 0, 0, data) )
|
||||
return error; /* driver WON'T change state; will return error */
|
||||
|
||||
p->tp_refp->tpr_state = REF_OPEN; /* has timers */
|
||||
p->tp_refstate = REF_OPEN; /* has timers */
|
||||
if(p->tp_class != TP_CLASS_0) {
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_cr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_cr_ticks);
|
||||
}
|
||||
}
|
||||
break;
|
||||
@ -195,17 +198,26 @@ case 0xb:
|
||||
sbappendrecord(&p->tp_Xrcv, e->ev_union.EV_DR_TPDU.e_data);
|
||||
e->ev_union.EV_DR_TPDU.e_data = MNULL;
|
||||
}
|
||||
/* must return no error, or disc data and reason can't be read */
|
||||
tp_indicate(T_DISCONNECT, p, 0);
|
||||
if (p->tp_state == TP_OPEN)
|
||||
tp_indicate(T_DISCONNECT, p, 0);
|
||||
else {
|
||||
int so_error = ECONNREFUSED;
|
||||
if (e->ev_union.EV_DR_TPDU.e_reason != (E_TP_NO_SESSION ^ TP_ERROR_MASK) &&
|
||||
e->ev_union.EV_DR_TPDU.e_reason != (E_TP_NO_CR_ON_NC ^ TP_ERROR_MASK) &&
|
||||
e->ev_union.EV_DR_TPDU.e_reason != (E_TP_REF_OVERFLOW ^ TP_ERROR_MASK))
|
||||
so_error = ECONNABORTED;
|
||||
tp_indicate(T_DISCONNECT, p, so_error);
|
||||
}
|
||||
tp_soisdisconnected(p);
|
||||
if (p->tp_class != TP_CLASS_0) {
|
||||
if (p->tp_state == TP_OPEN ) {
|
||||
tp_euntimeout(p->tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p->tp_refp, TM_inact);
|
||||
tp_cuntimeout(p->tp_refp, TM_sendack);
|
||||
tp_euntimeout(p, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
tp_cuntimeout(p, TM_inact);
|
||||
tp_cuntimeout(p, TM_sendack);
|
||||
p->tp_flags &= ~TPF_DELACK;
|
||||
}
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
if( e->ev_union.EV_DR_TPDU.e_sref != 0 )
|
||||
(void) tp_emit(DC_TPDU_type, p, 0, 0, MNULL);
|
||||
}
|
||||
@ -216,33 +228,33 @@ case 0xc:
|
||||
if( e->ev_union.EV_DR_TPDU.e_sref != 0 )
|
||||
(void) tp_emit(DC_TPDU_type, p, 0, 0, MNULL);
|
||||
/* reference timer already set - reset it to be safe (???) */
|
||||
tp_euntimeout(p->tp_refp, TM_reference); /* all */
|
||||
tp_etimeout(p->tp_refp, TM_reference, 0, 0, 0, (int)p->tp_refer_ticks);
|
||||
tp_euntimeout(p, TM_reference); /* all */
|
||||
tp_etimeout(p, TM_reference, (int)p->tp_refer_ticks);
|
||||
}
|
||||
break;
|
||||
case 0xd:
|
||||
{
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
tp_indicate(ER_TPDU, p, e->ev_union.EV_ER_TPDU.e_reason);
|
||||
tp_soisdisconnected(p);
|
||||
}
|
||||
break;
|
||||
case 0xe:
|
||||
{
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
tp_soisdisconnected(p);
|
||||
}
|
||||
break;
|
||||
case 0xf:
|
||||
{
|
||||
tp_indicate(ER_TPDU, p, e->ev_union.EV_ER_TPDU.e_reason);
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
tp_soisdisconnected(p);
|
||||
}
|
||||
break;
|
||||
case 0x10:
|
||||
{
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
tp_soisdisconnected(p);
|
||||
}
|
||||
break;
|
||||
@ -263,20 +275,20 @@ case 0x12:
|
||||
case 0x13:
|
||||
{
|
||||
if (p->tp_state == TP_OPEN) {
|
||||
tp_euntimeout(p->tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p->tp_refp, TM_inact);
|
||||
tp_cuntimeout(p->tp_refp, TM_sendack);
|
||||
tp_euntimeout(p, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p, TM_inact);
|
||||
tp_cuntimeout(p, TM_sendack);
|
||||
}
|
||||
tp_soisdisconnecting(p->tp_sock);
|
||||
tp_indicate(ER_TPDU, p, e->ev_union.EV_ER_TPDU.e_reason);
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_dr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_dr_ticks);
|
||||
(void) tp_emit(DR_TPDU_type, p, 0, E_TP_PROTO_ERR, MNULL);
|
||||
}
|
||||
break;
|
||||
case 0x14:
|
||||
{
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
IncStat(ts_tp0_conn);
|
||||
p->tp_fcredit = 1;
|
||||
soisconnected(p->tp_sock);
|
||||
@ -291,11 +303,10 @@ case 0x15:
|
||||
IncStat(ts_tp4_conn);
|
||||
p->tp_fref = e->ev_union.EV_CC_TPDU.e_sref;
|
||||
p->tp_fcredit = e->ev_union.EV_CC_TPDU.e_cdt;
|
||||
p->tp_ackrcvd = 0;
|
||||
if ((p->tp_rx_strat & TPRX_FASTSTART) && (e->ev_union.EV_CC_TPDU.e_cdt > 0))
|
||||
p->tp_cong_win = e->ev_union.EV_CC_TPDU.e_cdt;
|
||||
p->tp_cong_win = e->ev_union.EV_CC_TPDU.e_cdt * p->tp_l_tpdusize;
|
||||
tp_getoptions(p);
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
if (p->tp_ucddata) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf("dropping user connect data cc 0x%x\n",
|
||||
@ -312,7 +323,7 @@ case 0x15:
|
||||
}
|
||||
|
||||
(void) tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 0, MNULL);
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x16:
|
||||
@ -321,8 +332,7 @@ case 0x16:
|
||||
int error;
|
||||
|
||||
IncStat(ts_retrans_cr);
|
||||
p->tp_cong_win = 1;
|
||||
p->tp_ackrcvd = 0;
|
||||
p->tp_cong_win = 1 * p->tp_l_tpdusize;
|
||||
data = MCPY(p->tp_ucddata, M_NOWAIT);
|
||||
if(p->tp_ucddata) {
|
||||
IFDEBUG(D_CONN)
|
||||
@ -337,7 +347,7 @@ case 0x16:
|
||||
if( error = tp_emit(CR_TPDU_type, p, 0, 0, data) ) {
|
||||
p->tp_sock->so_error = error;
|
||||
}
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_cr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_cr_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x17:
|
||||
@ -357,7 +367,7 @@ case 0x18:
|
||||
p->tp_sock->so_error = error;
|
||||
}
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_cc_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_cc_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x19:
|
||||
@ -372,11 +382,10 @@ case 0x19:
|
||||
m_freem(p->tp_ucddata);
|
||||
p->tp_ucddata = 0;
|
||||
}
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
soisconnected(p->tp_sock);
|
||||
tp_getoptions(p);
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
|
||||
/* see also next 2 transitions, if you make any changes */
|
||||
|
||||
@ -385,11 +394,11 @@ case 0x19:
|
||||
printf("tp_stash returns %d\n",doack);
|
||||
ENDDEBUG
|
||||
|
||||
if(doack) {
|
||||
if (doack) {
|
||||
(void) tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 0, MNULL );
|
||||
tp_ctimeout(p->tp_refp, TM_sendack, (int)p->tp_keepalive_ticks);
|
||||
tp_ctimeout(p, TM_sendack, (int)p->tp_keepalive_ticks);
|
||||
} else
|
||||
tp_ctimeout( p->tp_refp, TM_sendack, (int)p->tp_sendack_ticks);
|
||||
tp_ctimeout( p, TM_sendack, (int)p->tp_sendack_ticks);
|
||||
|
||||
IFDEBUG(D_DATA)
|
||||
printf("after stash calling sbwakeup\n");
|
||||
@ -410,7 +419,7 @@ case 0x1b:
|
||||
{
|
||||
int doack; /* tells if we must ack immediately */
|
||||
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
sbwakeup( &p->tp_sock->so_rcv );
|
||||
|
||||
doack = tp_stash(p, e);
|
||||
@ -421,7 +430,7 @@ case 0x1b:
|
||||
if(doack)
|
||||
(void) tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 0, MNULL );
|
||||
else
|
||||
tp_ctimeout_MIN( p->tp_refp, TM_sendack, (int)p->tp_sendack_ticks);
|
||||
tp_ctimeout_MIN( p, TM_sendack, (int)p->tp_sendack_ticks);
|
||||
|
||||
IFDEBUG(D_DATA)
|
||||
printf("after stash calling sbwakeup\n");
|
||||
@ -436,7 +445,7 @@ case 0x1c:
|
||||
ENDTRACE
|
||||
IncStat(ts_dt_niw);
|
||||
m_freem(e->ev_union.EV_DT_TPDU.e_data);
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
(void) tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 0, MNULL );
|
||||
}
|
||||
break;
|
||||
@ -447,9 +456,8 @@ case 0x1d:
|
||||
p->tp_ucddata = 0;
|
||||
}
|
||||
(void) tp_goodack(p, e->ev_union.EV_AK_TPDU.e_cdt, e->ev_union.EV_AK_TPDU.e_seq, e->ev_union.EV_AK_TPDU.e_subseq);
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
|
||||
tp_getoptions(p);
|
||||
soisconnected(p->tp_sock);
|
||||
IFTRACE(D_CONN)
|
||||
struct socket *so = p->tp_sock;
|
||||
@ -461,8 +469,8 @@ case 0x1d:
|
||||
so->so_qlen, so->so_error, so->so_rcv.sb_cc, so->so_head);
|
||||
ENDTRACE
|
||||
|
||||
tp_ctimeout(p->tp_refp, TM_sendack, (int)p->tp_keepalive_ticks);
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_sendack, (int)p->tp_keepalive_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x1e:
|
||||
@ -472,11 +480,10 @@ case 0x1e:
|
||||
m_freem(p->tp_ucddata);
|
||||
p->tp_ucddata = 0;
|
||||
}
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_getoptions(p);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
soisconnected(p->tp_sock);
|
||||
tp_ctimeout(p->tp_refp, TM_sendack, (int)p->tp_keepalive_ticks);
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_sendack, (int)p->tp_keepalive_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
}
|
||||
IFTRACE(D_XPD)
|
||||
tptrace(TPPTmisc, "XPD tpdu accepted Xrcvnxt, e_seq datalen m_len\n",
|
||||
@ -518,7 +525,7 @@ case 0x20:
|
||||
IncStat(ts_xpd_dup);
|
||||
}
|
||||
m_freem(e->ev_union.EV_XPD_TPDU.e_data);
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
/* don't send an xack because the xak gives "last one received", not
|
||||
* "next one i expect" (dumb)
|
||||
*/
|
||||
@ -555,7 +562,7 @@ case 0x22:
|
||||
data = MCPY(p->tp_ucddata, M_NOWAIT);
|
||||
(void) tp_emit(DR_TPDU_type, p, 0, E_TP_NORMAL_DISC, data);
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_dr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_dr_ticks);
|
||||
}
|
||||
}
|
||||
break;
|
||||
@ -571,9 +578,10 @@ case 0x24:
|
||||
struct mbuf *data = MCPY(p->tp_ucddata, M_WAIT);
|
||||
|
||||
if(p->tp_state == TP_OPEN) {
|
||||
tp_euntimeout(p->tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p->tp_refp, TM_inact);
|
||||
tp_cuntimeout(p->tp_refp, TM_sendack);
|
||||
tp_euntimeout(p, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p, TM_inact);
|
||||
tp_cuntimeout(p, TM_sendack);
|
||||
p->tp_flags &= ~TPF_DELACK;
|
||||
}
|
||||
if (data) {
|
||||
IFDEBUG(D_CONN)
|
||||
@ -584,7 +592,7 @@ case 0x24:
|
||||
}
|
||||
tp_soisdisconnecting(p->tp_sock);
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_dr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_dr_ticks);
|
||||
|
||||
if( trick_hc )
|
||||
return tp_emit(DR_TPDU_type, p, 0, e->ev_union.EV_T_DISC_req.e_reason, data);
|
||||
@ -597,12 +605,11 @@ case 0x25:
|
||||
|
||||
IncStat(ts_retrans_cc);
|
||||
p->tp_retrans --;
|
||||
p->tp_cong_win = 1;
|
||||
p->tp_ackrcvd = 0;
|
||||
p->tp_cong_win = 1 * p->tp_l_tpdusize;
|
||||
|
||||
if( error = tp_emit(CC_TPDU_type, p, 0, 0, data) )
|
||||
p->tp_sock->so_error = error;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_cc_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_cc_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x26:
|
||||
@ -613,14 +620,14 @@ case 0x26:
|
||||
tp_indicate(T_DISCONNECT, p, ETIMEDOUT);
|
||||
(void) tp_emit(DR_TPDU_type, p, 0, E_TP_CONGEST, MNULL);
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_dr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_dr_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x27:
|
||||
{
|
||||
tp_euntimeout(p->tp_refp, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p->tp_refp, TM_inact);
|
||||
tp_cuntimeout(p->tp_refp, TM_sendack);
|
||||
tp_euntimeout(p, TM_data_retrans); /* all */
|
||||
tp_cuntimeout(p, TM_inact);
|
||||
tp_cuntimeout(p, TM_sendack);
|
||||
|
||||
IncStat(ts_conn_gaveup);
|
||||
tp_soisdisconnecting(p->tp_sock);
|
||||
@ -628,23 +635,20 @@ case 0x27:
|
||||
tp_indicate(T_DISCONNECT, p, ETIMEDOUT);
|
||||
(void) tp_emit(DR_TPDU_type, p, 0, E_TP_CONGEST_2, MNULL);
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_dr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_dr_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x28:
|
||||
{
|
||||
p->tp_cong_win = 1;
|
||||
p->tp_ackrcvd = 0;
|
||||
p->tp_cong_win = 1 * p->tp_l_tpdusize;
|
||||
/* resume XPD */
|
||||
if ( p->tp_Xsnd.sb_mb ) {
|
||||
struct mbuf *m = m_copy(p->tp_Xsnd.sb_mb, 0, (int)p->tp_Xsnd.sb_cc);
|
||||
/* m_copy doesn't preserve the m_xlink field, but at this pt.
|
||||
* that doesn't matter
|
||||
*/
|
||||
int shift;
|
||||
|
||||
IFTRACE(D_XPD)
|
||||
tptrace(TPPTmisc, "XPD retrans: Xuna Xsndnxt sndhiwat snduna",
|
||||
p->tp_Xuna, p->tp_Xsndnxt, p->tp_sndhiwat,
|
||||
tptrace(TPPTmisc, "XPD retrans: Xuna Xsndnxt sndnxt snduna",
|
||||
p->tp_Xuna, p->tp_Xsndnxt, p->tp_sndnxt,
|
||||
p->tp_snduna);
|
||||
ENDTRACE
|
||||
IFDEBUG(D_XPD)
|
||||
@ -652,65 +656,16 @@ case 0x28:
|
||||
ENDDEBUG
|
||||
IncStat(ts_retrans_xpd);
|
||||
p->tp_retrans --;
|
||||
shift = max(p->tp_Nretrans - p->tp_retrans, 6);
|
||||
(void) tp_emit(XPD_TPDU_type, p, p->tp_Xuna, 1, m);
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_xpd_ticks);
|
||||
tp_ctimeout(p, TM_retrans, ((int)p->tp_dt_ticks) << shift);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0x29:
|
||||
{
|
||||
register SeqNum low, lowsave = 0;
|
||||
register struct tp_rtc *r = p->tp_snduna_rtc;
|
||||
register struct mbuf *m;
|
||||
register SeqNum high = e->ev_union.EV_TM_data_retrans.e_high;
|
||||
|
||||
low = p->tp_snduna;
|
||||
lowsave = high = low;
|
||||
|
||||
tp_euntimeout_lss(p->tp_refp, TM_data_retrans,
|
||||
SEQ_ADD(p, p->tp_sndhiwat, 1));
|
||||
p->tp_retrans_hiwat = p->tp_sndhiwat;
|
||||
|
||||
if ((p->tp_rx_strat & TPRX_EACH) == 0)
|
||||
high = (high>low)?low:high;
|
||||
|
||||
if( p->tp_rx_strat & TPRX_USE_CW ) {
|
||||
register int i;
|
||||
|
||||
p->tp_cong_win = 1;
|
||||
p->tp_ackrcvd = 0;
|
||||
i = SEQ_ADD(p, low, p->tp_cong_win);
|
||||
|
||||
high = SEQ_MIN(p, high, p->tp_sndhiwat);
|
||||
|
||||
}
|
||||
|
||||
while( SEQ_LEQ(p, low, high) ){
|
||||
if ( r == (struct tp_rtc *)0 ){
|
||||
IFDEBUG(D_RTC)
|
||||
printf( "tp: retrans rtc list is GONE!\n");
|
||||
ENDDEBUG
|
||||
break;
|
||||
}
|
||||
if ( r->tprt_seq == low ){
|
||||
if(( m = m_copy(r->tprt_data, 0, r->tprt_octets ))== MNULL)
|
||||
break;
|
||||
(void) tp_emit(DT_TPDU_type, p, low, r->tprt_eot, m);
|
||||
IncStat(ts_retrans_dt);
|
||||
SEQ_INC(p, low );
|
||||
}
|
||||
r = r->tprt_next;
|
||||
}
|
||||
/* CE_BIT
|
||||
if ( SEQ_LEQ(p, lowsave, high) ){
|
||||
*/
|
||||
e->ev_union.EV_TM_data_retrans.e_retrans --;
|
||||
tp_etimeout(p->tp_refp, TM_data_retrans, (caddr_t)lowsave,
|
||||
(caddr_t)high, e->ev_union.EV_TM_data_retrans.e_retrans,
|
||||
(p->tp_Nretrans - e->ev_union.EV_TM_data_retrans.e_retrans) * (int)p->tp_dt_ticks);
|
||||
/* CE_BIT
|
||||
}
|
||||
*/
|
||||
p->tp_rxtshift++;
|
||||
(void) tp_data_retrans(p);
|
||||
}
|
||||
break;
|
||||
case 0x2a:
|
||||
@ -718,27 +673,27 @@ case 0x2a:
|
||||
p->tp_retrans --;
|
||||
(void) tp_emit(DR_TPDU_type, p, 0, E_TP_DR_NO_REAS, MNULL);
|
||||
IncStat(ts_retrans_dr);
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_dr_ticks);
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_dr_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x2b:
|
||||
{
|
||||
p->tp_sock->so_error = ETIMEDOUT;
|
||||
p->tp_refp->tpr_state = REF_FROZEN;
|
||||
p->tp_refstate = REF_FROZEN;
|
||||
tp_recycle_tsuffix( p );
|
||||
tp_etimeout(p->tp_refp, TM_reference, 0,0,0, (int)p->tp_refer_ticks);
|
||||
tp_etimeout(p, TM_reference, (int)p->tp_refer_ticks);
|
||||
}
|
||||
break;
|
||||
case 0x2c:
|
||||
{
|
||||
tp_freeref(p->tp_refp);
|
||||
tp_freeref(p->tp_lref);
|
||||
tp_detach(p);
|
||||
}
|
||||
break;
|
||||
case 0x2d:
|
||||
{
|
||||
if( p->tp_class != TP_CLASS_0) {
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
if ( e->ev_number == CC_TPDU )
|
||||
(void) tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 0, MNULL);
|
||||
}
|
||||
@ -748,8 +703,8 @@ case 0x2d:
|
||||
case 0x2e:
|
||||
{
|
||||
IFTRACE(D_DATA)
|
||||
tptrace(TPPTmisc, "T_DATA_req sndhiwat snduna fcredit, tpcb",
|
||||
p->tp_sndhiwat, p->tp_snduna, p->tp_fcredit, p);
|
||||
tptrace(TPPTmisc, "T_DATA_req sndnxt snduna fcredit, tpcb",
|
||||
p->tp_sndnxt, p->tp_snduna, p->tp_fcredit, p);
|
||||
ENDTRACE
|
||||
|
||||
tp_send(p);
|
||||
@ -767,8 +722,8 @@ case 0x2f:
|
||||
*/
|
||||
|
||||
IFTRACE(D_XPD)
|
||||
tptrace(TPPTmisc, "XPD req: Xuna Xsndnxt sndhiwat snduna",
|
||||
p->tp_Xuna, p->tp_Xsndnxt, p->tp_sndhiwat,
|
||||
tptrace(TPPTmisc, "XPD req: Xuna Xsndnxt sndnxt snduna",
|
||||
p->tp_Xuna, p->tp_Xsndnxt, p->tp_sndnxt,
|
||||
p->tp_snduna);
|
||||
ENDTRACE
|
||||
IFDEBUG(D_XPD)
|
||||
@ -778,7 +733,8 @@ case 0x2f:
|
||||
error =
|
||||
tp_emit(XPD_TPDU_type, p, p->tp_Xuna, 1, m);
|
||||
p->tp_retrans = p->tp_Nretrans;
|
||||
tp_ctimeout(p->tp_refp, TM_retrans, (int)p->tp_xpd_ticks);
|
||||
|
||||
tp_ctimeout(p, TM_retrans, (int)p->tp_rxtcur);
|
||||
SEQ_INC(p, p->tp_Xsndnxt);
|
||||
}
|
||||
if(trick_hc)
|
||||
@ -787,59 +743,17 @@ case 0x2f:
|
||||
break;
|
||||
case 0x30:
|
||||
{
|
||||
struct sockbuf *sb = &p->tp_sock->so_snd;
|
||||
|
||||
IFDEBUG(D_ACKRECV)
|
||||
printf("GOOD ACK seq 0x%x cdt 0x%x\n", e->ev_union.EV_AK_TPDU.e_seq, e->ev_union.EV_AK_TPDU.e_cdt);
|
||||
ENDDEBUG
|
||||
if( p->tp_class != TP_CLASS_0) {
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_euntimeout_lss(p->tp_refp, TM_data_retrans, e->ev_union.EV_AK_TPDU.e_seq);
|
||||
}
|
||||
sbwakeup( &p->tp_sock->so_snd );
|
||||
|
||||
if (p->tp_sndhiwat <= p->tp_retrans_hiwat &&
|
||||
p->tp_snduna <= p->tp_retrans_hiwat) {
|
||||
|
||||
register struct mbuf *m;
|
||||
/* extern struct mbuf *m_copy(); */
|
||||
register struct tp_rtc *r;
|
||||
SeqNum high, retrans, low_save;
|
||||
|
||||
high = SEQ_MIN(p, SEQ_ADD(p, p->tp_snduna,
|
||||
MIN(p->tp_cong_win, p->tp_fcredit)) - 1,
|
||||
p->tp_sndhiwat);
|
||||
low_save = retrans = SEQ_MAX(p, SEQ_ADD(p, p->tp_last_retrans, 1),
|
||||
p->tp_snduna);
|
||||
for (; SEQ_LEQ(p, retrans, high); SEQ_INC(p, retrans)) {
|
||||
|
||||
for (r = p->tp_snduna_rtc; r; r = r->tprt_next){
|
||||
if ( r->tprt_seq == retrans ){
|
||||
if(( m = m_copy(r->tprt_data, 0, r->tprt_octets ))
|
||||
== MNULL)
|
||||
break;
|
||||
(void) tp_emit(DT_TPDU_type, p, retrans,
|
||||
r->tprt_eot, m);
|
||||
p->tp_last_retrans = retrans;
|
||||
IncStat(ts_retrans_dt);
|
||||
break;
|
||||
}
|
||||
}
|
||||
if ( r == (struct tp_rtc *)0 ){
|
||||
IFDEBUG(D_RTC)
|
||||
printf( "tp: retrans rtc list is GONE!\n");
|
||||
ENDDEBUG
|
||||
break;
|
||||
}
|
||||
}
|
||||
tp_etimeout(p->tp_refp, TM_data_retrans, (caddr_t)low_save,
|
||||
(caddr_t)high, p->tp_retrans, (int)p->tp_dt_ticks);
|
||||
if (SEQ_DEC(p, retrans) == p->tp_retrans_hiwat)
|
||||
tp_send(p);
|
||||
}
|
||||
else {
|
||||
tp_send(p);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
}
|
||||
sbwakeup(sb);
|
||||
IFDEBUG(D_ACKRECV)
|
||||
printf("GOOD ACK new sndhiwat 0x%x\n", p->tp_sndhiwat);
|
||||
printf("GOOD ACK new sndnxt 0x%x\n", p->tp_sndnxt);
|
||||
ENDDEBUG
|
||||
}
|
||||
break;
|
||||
@ -856,14 +770,14 @@ case 0x31:
|
||||
IncStat( ts_ackreason[_ACK_FCC_] );
|
||||
(void) tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 1, MNULL);
|
||||
}
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0x32:
|
||||
{
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_cuntimeout(p->tp_refp, TM_retrans);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_cuntimeout(p, TM_retrans);
|
||||
|
||||
sbwakeup( &p->tp_sock->so_snd );
|
||||
|
||||
@ -877,18 +791,26 @@ case 0x33:
|
||||
tptrace(TPPTmisc, "BOGUS XACK eventtype ", e->ev_number, 0, 0,0);
|
||||
ENDTRACE
|
||||
if( p->tp_class != TP_CLASS_0 ) {
|
||||
tp_ctimeout(p->tp_refp, TM_inact, (int)p->tp_inact_ticks);
|
||||
tp_ctimeout(p, TM_inact, (int)p->tp_inact_ticks);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case 0x34:
|
||||
{
|
||||
int timo;
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTsendack, -1, p->tp_lcredit, p->tp_sent_uwe,
|
||||
p->tp_sent_lcdt, 0);
|
||||
ENDTRACE
|
||||
IncPStat(p, tps_n_TMsendack);
|
||||
(void) tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 0, MNULL);
|
||||
if (p->tp_fcredit == 0) {
|
||||
if (p->tp_rxtshift < TP_MAXRXTSHIFT)
|
||||
p->tp_rxtshift++;
|
||||
timo = (p->tp_dt_ticks) << p->tp_rxtshift;
|
||||
} else
|
||||
timo = p->tp_sendack_ticks;
|
||||
tp_ctimeout(p, TM_sendack, timo);
|
||||
}
|
||||
break;
|
||||
case 0x35:
|
||||
@ -900,14 +822,22 @@ case 0x35:
|
||||
case 0x36:
|
||||
{
|
||||
if( trick_hc ) {
|
||||
IncStat(ts_ackreason[_ACK_USRRCV_]);
|
||||
|
||||
/* send an ACK only if there's new information */
|
||||
LOCAL_CREDIT( p );
|
||||
if ((p->tp_rcvnxt != p->tp_sent_rcvnxt) ||
|
||||
(p->tp_lcredit != p->tp_sent_lcdt))
|
||||
|
||||
SeqNum ack_thresh;
|
||||
/*
|
||||
* If the upper window edge has advanced a reasonable
|
||||
* amount beyond what was known, send an ACK.
|
||||
* A reasonable amount is 2 packets, unless the max window
|
||||
* is only 1 or 2 packets, in which case we
|
||||
* should send an ack for any advance in the upper window edge.
|
||||
*/
|
||||
LOCAL_CREDIT(p);
|
||||
ack_thresh = SEQ_SUB(p, p->tp_lcredit + p->tp_rcvnxt,
|
||||
(p->tp_maxlcredit > 2 ? 2 : 1));
|
||||
if (SEQ_GT(p, ack_thresh, p->tp_sent_uwe)) {
|
||||
IncStat(ts_ackreason[_ACK_USRRCV_]);
|
||||
p->tp_flags &= ~TPF_DELACK;
|
||||
return tp_emit(AK_TPDU_type, p, p->tp_rcvnxt, 0, MNULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
break;
|
||||
@ -947,7 +877,7 @@ case 0x15:
|
||||
if ( p->tp_retrans > 0 ) return 0x34;
|
||||
else return 0x35;
|
||||
case 0x54:
|
||||
if ( e->ev_union.EV_TM_data_retrans.e_retrans > 0 ) return 0x33;
|
||||
if (p->tp_rxtshift < TP_NRETRANS) return 0x33;
|
||||
else return 0x31;
|
||||
case 0x64:
|
||||
if (p->tp_class == TP_CLASS_0) return 0x1a;
|
||||
@ -1059,7 +989,6 @@ register struct tp_event *e;
|
||||
error = _Xebec_action( a->a_action, e, p );
|
||||
IFTRACE(D_DRIVER)
|
||||
tptrace(DRIVERTRACE, a->a_newstate, p->tp_state, e->ev_number, a->a_action, 0);
|
||||
|
||||
ENDTRACE
|
||||
if(error==0)
|
||||
p->tp_state = a->a_newstate;
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_emit.c 7.9 (Berkeley) 5/9/91
|
||||
* $Id: tp_emit.c,v 1.3 1993/12/18 00:43:31 mycroft Exp $
|
||||
* from: @(#)tp_emit.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_emit.c,v 1.4 1994/05/13 06:09:16 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* This file contains tp_emit() and tp_error_emit(), which
|
||||
* form TPDUs and hand them to ip.
|
||||
* They take data in the form of mbuf chain, allocate mbufs as
|
||||
@ -78,16 +76,14 @@ SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/errno.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <net/if.h>
|
||||
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/iso_pcb.h>
|
||||
#include <netiso/argo_debug.h>
|
||||
@ -101,6 +97,7 @@ SOFTWARE.
|
||||
#include <netiso/tp_seq.h>
|
||||
#include <netiso/iso_errno.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#ifdef TRUE
|
||||
#undef FALSE
|
||||
#undef TRUE
|
||||
@ -174,6 +171,8 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
int csum_offset=0;
|
||||
int datalen = 0;
|
||||
int error = 0;
|
||||
SeqNum olduwe;
|
||||
int acking_ooo;
|
||||
|
||||
/* NOTE:
|
||||
* here we treat tpdu_li as if it DID include the li field, up until
|
||||
@ -240,26 +239,21 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
|
||||
case CR_TPDU_type:
|
||||
hdr->tpdu_CRdref_0 = 0; /* must be zero */
|
||||
case CC_TPDU_type:
|
||||
if (!tpcb->tp_cebit_off) {
|
||||
tpcb->tp_win_recv = tp_start_win << 8;
|
||||
LOCAL_CREDIT(tpcb);
|
||||
CONG_INIT_SAMPLE(tpcb);
|
||||
tpcb->tp_ackrcvd = 0;
|
||||
}
|
||||
else
|
||||
} else
|
||||
LOCAL_CREDIT(tpcb);
|
||||
|
||||
|
||||
case CC_TPDU_type:
|
||||
{
|
||||
/* Case CC_TPDU_type used to be here */
|
||||
{
|
||||
u_char x;
|
||||
|
||||
hdr->tpdu_CCsref = htons(tpcb->tp_lref); /* same as CRsref */
|
||||
|
||||
if( tpcb->tp_class > TP_CLASS_1 ) {
|
||||
/* ifdef CE_BIT, we did this in tp_input when the CR came in */
|
||||
if (tpcb->tp_cebit_off)
|
||||
LOCAL_CREDIT( tpcb );
|
||||
tpcb->tp_sent_uwe = tpcb->tp_lcredit -1;
|
||||
tpcb->tp_sent_rcvnxt = 1;
|
||||
tpcb->tp_sent_lcdt = tpcb->tp_lcredit;
|
||||
@ -313,6 +307,19 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
| (tpcb->tp_xpd_service? TPAO_USE_TXPD: 0);
|
||||
ADDOPTION(TPP_addl_opt, hdr, 1, x);
|
||||
|
||||
if ((tpcb->tp_l_tpdusize ^ (1 << tpcb->tp_tpdusize)) != 0) {
|
||||
u_short size_s = tpcb->tp_l_tpdusize >> 7;
|
||||
u_char size_c = size_s;
|
||||
ASSERT(tpcb->tp_l_tpdusize < 65536 * 128);
|
||||
if (dutype == CR_TPDU_type)
|
||||
tpcb->tp_ptpdusize = size_s;
|
||||
if (size_s < 256) {
|
||||
ADDOPTION(TPP_ptpdu_size, hdr, 1, size_c);
|
||||
} else {
|
||||
size_s = htons(size_s);
|
||||
ADDOPTION(TPP_ptpdu_size, hdr, 2, size_s);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if( (dutype == CR_TPDU_type) && (tpcb->tp_class != TP_CLASS_0)){
|
||||
@ -377,7 +384,7 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
hdr->tpdu_seqeotX = htonl(seqeotX.s_seqeot);
|
||||
#else
|
||||
hdr->tpdu_XAKseqX = seq;
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else {
|
||||
hdr->tpdu_XAKseq = seq;
|
||||
}
|
||||
@ -398,7 +405,7 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
#else
|
||||
hdr->tpdu_XPDseqX = seq;
|
||||
hdr->tpdu_XPDeotX = 1; /* always 1 for XPD tpdu */
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else {
|
||||
hdr->tpdu_XPDseq = seq;
|
||||
hdr->tpdu_XPDeot = 1; /* always 1 for XPD tpdu */
|
||||
@ -431,7 +438,7 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
#else
|
||||
hdr->tpdu_DTseqX = seq;
|
||||
hdr->tpdu_DTeotX = eot;
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else if (tpcb->tp_class == TP_CLASS_0) {
|
||||
IFDEBUG(D_EMIT)
|
||||
printf("DT tpdu: class 0 m 0x%x hdr 0x%x\n", m, hdr);
|
||||
@ -457,68 +464,71 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
case AK_TPDU_type:/* ak not used in class 0 */
|
||||
ASSERT( tpcb->tp_class != TP_CLASS_0);
|
||||
data = (struct mbuf *)0;
|
||||
{ SeqNum olduwe = tpcb->tp_sent_uwe;
|
||||
olduwe = tpcb->tp_sent_uwe;
|
||||
|
||||
if (seq != tpcb->tp_sent_rcvnxt || tpcb->tp_rsycnt == 0) {
|
||||
LOCAL_CREDIT( tpcb );
|
||||
tpcb->tp_sent_uwe =
|
||||
SEQ(tpcb,tpcb->tp_rcvnxt + tpcb->tp_lcredit -1);
|
||||
LOCAL_CREDIT( tpcb );
|
||||
tpcb->tp_sent_lcdt = tpcb->tp_lcredit;
|
||||
acking_ooo = 0;
|
||||
} else
|
||||
acking_ooo = 1;
|
||||
|
||||
IFDEBUG(D_RENEG)
|
||||
/* occasionally fake a reneging so
|
||||
you can test subsequencing */
|
||||
if( olduwe & 0x1 ) {
|
||||
tpcb->tp_reneged = 1;
|
||||
IncStat(ts_ldebug);
|
||||
}
|
||||
ENDDEBUG
|
||||
/* Are we about to reneg on credit?
|
||||
* When might we do so?
|
||||
* a) when using optimistic credit (which we no longer do).
|
||||
* b) when drain() gets implemented (not in the plans).
|
||||
* c) when D_RENEG is on.
|
||||
* d) when DEC BIT response is implemented.
|
||||
* (not- when we do this, we'll need to implement flow control
|
||||
* confirmation)
|
||||
*/
|
||||
if( SEQ_LT(tpcb, tpcb->tp_sent_uwe, olduwe) ) {
|
||||
IFDEBUG(D_RENEG)
|
||||
/* occasionally fake a reneging so
|
||||
you can test subsequencing */
|
||||
if( olduwe & 0x1 ) {
|
||||
tpcb->tp_reneged = 1;
|
||||
IncStat(ts_lcdt_reduced);
|
||||
IFTRACE(D_CREDIT)
|
||||
tptraceTPCB(TPPTmisc,
|
||||
"RENEG: olduwe newuwe lcredit rcvnxt",
|
||||
olduwe,
|
||||
tpcb->tp_sent_uwe, tpcb->tp_lcredit,
|
||||
tpcb->tp_rcvnxt);
|
||||
ENDTRACE
|
||||
IncStat(ts_ldebug);
|
||||
}
|
||||
|
||||
IFPERF(tpcb)
|
||||
/* new lwe is less than old uwe means we're
|
||||
* acking before we received a whole window full
|
||||
*/
|
||||
if( SEQ_LT( tpcb, tpcb->tp_rcvnxt, olduwe) ) {
|
||||
/* tmp1 = number of pkts fewer than the full window */
|
||||
register int tmp1 =
|
||||
(int) SEQ_SUB( tpcb, olduwe, tpcb->tp_rcvnxt);
|
||||
|
||||
if(tmp1 > TP_PM_MAX)
|
||||
tmp1 = TP_PM_MAX;
|
||||
IncPStat( tpcb, tps_ack_early[tmp1] );
|
||||
|
||||
/* tmp1 = amt of new cdt we're advertising */
|
||||
tmp1 = SEQ_SUB( tpcb, seq, tpcb->tp_sent_rcvnxt);
|
||||
if(tmp1 > TP_PM_MAX )
|
||||
tmp1 = TP_PM_MAX;
|
||||
|
||||
IncPStat( tpcb,
|
||||
tps_cdt_acked [ tmp1 ]
|
||||
[ ((tpcb->tp_lcredit > TP_PM_MAX)?
|
||||
TP_PM_MAX:tpcb->tp_lcredit) ] );
|
||||
|
||||
}
|
||||
ENDPERF
|
||||
ENDDEBUG
|
||||
/* Are we about to reneg on credit?
|
||||
* When might we do so?
|
||||
* a) when using optimistic credit (which we no longer do).
|
||||
* b) when drain() gets implemented (not in the plans).
|
||||
* c) when D_RENEG is on.
|
||||
* d) when DEC BIT response is implemented.
|
||||
* (not- when we do this, we'll need to implement flow control
|
||||
* confirmation)
|
||||
*/
|
||||
if( SEQ_LT(tpcb, tpcb->tp_sent_uwe, olduwe) ) {
|
||||
tpcb->tp_reneged = 1;
|
||||
IncStat(ts_lcdt_reduced);
|
||||
IFTRACE(D_CREDIT)
|
||||
tptraceTPCB(TPPTmisc,
|
||||
"RENEG: olduwe newuwe lcredit rcvnxt",
|
||||
olduwe,
|
||||
tpcb->tp_sent_uwe, tpcb->tp_lcredit,
|
||||
tpcb->tp_rcvnxt);
|
||||
ENDTRACE
|
||||
}
|
||||
IFPERF(tpcb)
|
||||
/* new lwe is less than old uwe means we're
|
||||
* acking before we received a whole window full
|
||||
*/
|
||||
if( SEQ_LT( tpcb, tpcb->tp_rcvnxt, olduwe) ) {
|
||||
/* tmp1 = number of pkts fewer than the full window */
|
||||
register int tmp1 =
|
||||
(int) SEQ_SUB( tpcb, olduwe, tpcb->tp_rcvnxt);
|
||||
|
||||
if(tmp1 > TP_PM_MAX)
|
||||
tmp1 = TP_PM_MAX;
|
||||
IncPStat( tpcb, tps_ack_early[tmp1] );
|
||||
|
||||
/* tmp1 = amt of new cdt we're advertising */
|
||||
tmp1 = SEQ_SUB( tpcb, seq, tpcb->tp_sent_rcvnxt);
|
||||
if(tmp1 > TP_PM_MAX )
|
||||
tmp1 = TP_PM_MAX;
|
||||
|
||||
IncPStat( tpcb,
|
||||
tps_cdt_acked [ tmp1 ]
|
||||
[ ((tpcb->tp_lcredit > TP_PM_MAX)?
|
||||
TP_PM_MAX:tpcb->tp_lcredit) ] );
|
||||
|
||||
}
|
||||
ENDPERF
|
||||
|
||||
IFTRACE(D_ACKSEND)
|
||||
tptraceTPCB(TPPTack, seq, tpcb->tp_lcredit, tpcb->tp_sent_uwe,
|
||||
tpcb->tp_r_subseq, 0);
|
||||
@ -535,12 +545,13 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
hdr->tpdu_cdt = 0;
|
||||
hdr->tpdu_AKseqX = seq;
|
||||
hdr->tpdu_AKcdtX = tpcb->tp_lcredit;
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else {
|
||||
hdr->tpdu_AKseq = seq;
|
||||
hdr->tpdu_AKcdt = tpcb->tp_lcredit;
|
||||
}
|
||||
if ((tpcb->tp_class == TP_CLASS_4) && tpcb->tp_reneged ) {
|
||||
if ((tpcb->tp_class == TP_CLASS_4) &&
|
||||
(tpcb->tp_reneged || acking_ooo)) {
|
||||
/*
|
||||
* Ack subsequence parameter req'd if WE reneged on
|
||||
* credit offered. (ISO 8073, 12.2.3.8.2, p. 74)
|
||||
@ -620,8 +631,14 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
}
|
||||
tpcb->tp_reneged = 0;
|
||||
tpcb->tp_sent_rcvnxt = seq;
|
||||
tp_ctimeout(tpcb->tp_refp, TM_sendack,
|
||||
(int)tpcb->tp_keepalive_ticks);
|
||||
if (tpcb->tp_fcredit == 0) {
|
||||
int timo = tpcb->tp_keepalive_ticks;
|
||||
if (tpcb->tp_rxtshift < TP_MAXRXTSHIFT)
|
||||
tpcb->tp_rxtshift++;
|
||||
timo = min(timo, ((int)tpcb->tp_dt_ticks) << tpcb->tp_rxtshift);
|
||||
tp_ctimeout(tpcb, TM_sendack, timo);
|
||||
} else
|
||||
tp_ctimeout(tpcb, TM_sendack, tpcb->tp_keepalive_ticks);
|
||||
IncStat(ts_AK_sent);
|
||||
IncPStat(tpcb, tps_AK_sent);
|
||||
IFDEBUG(D_ACKSEND)
|
||||
@ -717,9 +734,13 @@ tp_emit(dutype, tpcb, seq, eot, data)
|
||||
tpcb->tp_nlproto->nlp_output, tpcb->tp_netservice, error, datalen);
|
||||
ENDTRACE
|
||||
done:
|
||||
if( error == E_CO_QFULL ) {
|
||||
tp_quench(tpcb, PRC_QUENCH);
|
||||
return 0;
|
||||
if (error) {
|
||||
if (dutype == AK_TPDU_type)
|
||||
tp_ctimeout(tpcb, TM_sendack, 1);
|
||||
if (error == E_CO_QFULL) {
|
||||
tp_quench(tpcb, PRC_QUENCH);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
return error;
|
||||
}
|
||||
@ -757,7 +778,7 @@ tp_error_emit(error, sref, faddr, laddr, erdata, erlen, tpcb, cons_channel,
|
||||
struct mbuf *erdata;
|
||||
int erlen;
|
||||
struct tp_pcb *tpcb;
|
||||
int cons_channel;
|
||||
caddr_t cons_channel;
|
||||
int (*dgout_routine)();
|
||||
{
|
||||
int dutype;
|
||||
@ -834,6 +855,7 @@ tp_error_emit(error, sref, faddr, laddr, erdata, erlen, tpcb, cons_channel,
|
||||
IncStat(ts_ER_sent);
|
||||
hdr->tpdu_li = 5;
|
||||
hdr->tpdu_ERreason = (char)error;
|
||||
hdr->tpdu_ERdref = htons(sref);
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -899,8 +921,7 @@ tp_error_emit(error, sref, faddr, laddr, erdata, erlen, tpcb, cons_channel,
|
||||
ENDTRACE
|
||||
|
||||
datalen = m_datalen( m);
|
||||
|
||||
if(tpcb) {
|
||||
if (tpcb) {
|
||||
if( tpcb->tp_use_checksum ) {
|
||||
IFTRACE(D_ERROR_EMIT)
|
||||
tptrace(TPPTmisc, "before gen csum datalen", datalen,0,0,0);
|
||||
@ -917,11 +938,27 @@ tp_error_emit(error, sref, faddr, laddr, erdata, erlen, tpcb, cons_channel,
|
||||
printf("OUTPUT: tpcb 0x%x, isop 0x%x, so 0x%x\n",
|
||||
tpcb, tpcb->tp_npcb, tpcb->tp_sock);
|
||||
ENDDEBUG
|
||||
/* Problem: if packet comes in on ISO but sock is listening
|
||||
* in INET, this assertion will fail.
|
||||
* Have to believe the argument, not the nlp_proto.
|
||||
ASSERT( tpcb->tp_nlproto->nlp_dgoutput == dgout_routine );
|
||||
*/
|
||||
}
|
||||
if (cons_channel) {
|
||||
#ifdef TPCONS
|
||||
struct pklcd *lcp = (struct pklcd *)cons_channel;
|
||||
struct isopcb *isop = (struct isopcb *)lcp->lcd_upnext;
|
||||
|
||||
tpcons_dg_output(cons_channel, m, datalen);
|
||||
/* was if (tpcb == 0) iso_pcbdetach(isop); */
|
||||
/* but other side may want to try again over same VC,
|
||||
so, we'll depend on him closing it, but in case it gets forgotten
|
||||
we'll mark it for garbage collection */
|
||||
lcp->lcd_flags |= X25_DG_CIRCUIT;
|
||||
IFDEBUG(D_ERROR_EMIT)
|
||||
printf("OUTPUT: dutype 0x%x channel 0x%x\n",
|
||||
dutype, cons_channel);
|
||||
ENDDEBUG
|
||||
#else
|
||||
printf("TP panic! cons channel 0x%x but not cons configured\n",
|
||||
cons_channel);
|
||||
#endif
|
||||
} else if (tpcb) {
|
||||
|
||||
IFDEBUG(D_ERROR_EMIT)
|
||||
printf("tp_error_emit 1 sending DG: Laddr\n");
|
||||
@ -934,38 +971,22 @@ tp_error_emit(error, sref, faddr, laddr, erdata, erlen, tpcb, cons_channel,
|
||||
&faddr->siso_addr,
|
||||
m, datalen,
|
||||
/* no route */ (caddr_t)0, !tpcb->tp_use_checksum);
|
||||
} else {
|
||||
if( cons_channel ) {
|
||||
#ifdef TPCONS
|
||||
tpcons_dg_output(cons_channel, m, datalen);
|
||||
pk_disconnect((struct pklcd *)cons_channel);
|
||||
IFDEBUG(D_ERROR_EMIT)
|
||||
printf("OUTPUT: dutype 0x%x channel 0x%x\n",
|
||||
dutype, cons_channel);
|
||||
ENDDEBUG
|
||||
#else
|
||||
printf("TP panic! cons channel 0x%x but not cons configured\n",
|
||||
cons_channel);
|
||||
#endif
|
||||
} else {
|
||||
#ifndef notdef
|
||||
} else if (dgout_routine) {
|
||||
IFDEBUG(D_ERROR_EMIT)
|
||||
printf("tp_error_emit sending DG: Laddr\n");
|
||||
dump_addr((struct sockaddr *)laddr);
|
||||
printf("Faddr\n");
|
||||
dump_addr((struct sockaddr *)faddr);
|
||||
ENDDEBUG
|
||||
return (*dgout_routine)( &laddr->siso_addr, &faddr->siso_addr,
|
||||
m, datalen, /* no route */
|
||||
(caddr_t)0, /* nochecksum==false */0);
|
||||
#else notdef
|
||||
return (*dgout_routine)( &laddr->siso_addr, &faddr->siso_addr,
|
||||
m, datalen, /* no route */
|
||||
(caddr_t)0, /* nochecksum==false */0);
|
||||
} else {
|
||||
IFDEBUG(D_ERROR_EMIT)
|
||||
printf("tp_error_emit DROPPING \n", m);
|
||||
ENDDEBUG
|
||||
IncStat(ts_send_drop);
|
||||
m_freem(m);
|
||||
return 0;
|
||||
#endif notdef
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $Id: tp_events.h,v 1.2 1993/05/20 05:27:37 cgd Exp $ */
|
||||
/* $Id: tp_events.h,v 1.3 1994/05/13 06:09:18 mycroft Exp $ */
|
||||
|
||||
struct tp_event {
|
||||
int ev_number;
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_inet.c 7.8 (Berkeley) 5/6/91
|
||||
* $Id: tp_inet.c,v 1.5 1994/01/10 22:01:47 mycroft Exp $
|
||||
* from: @(#)tp_inet.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_inet.c,v 1.6 1994/05/13 06:09:20 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* Here is where you find the inet-dependent code. We've tried
|
||||
* keep all net-level and (primarily) address-family-dependent stuff
|
||||
* out of the tp source, and everthing here is reached indirectly
|
||||
@ -100,9 +98,7 @@ SOFTWARE.
|
||||
#include <netiso/tp_trace.h>
|
||||
#include <netiso/tp_stat.h>
|
||||
#include <netiso/tp_tpdu.h>
|
||||
|
||||
#include <netinet/in_var.h>
|
||||
#include <netinet/ip_var.h>
|
||||
|
||||
#ifndef ISO
|
||||
#include <netiso/iso_chksum.c>
|
||||
@ -313,102 +309,32 @@ in_getnetaddr( inp, name, which)
|
||||
* NAME: tpip_mtu()
|
||||
*
|
||||
* CALLED FROM:
|
||||
* tp_input() on incoming CR, CC, and pr_usrreq() for PRU_CONNECT
|
||||
* tp_route_to() on incoming CR, CC, and pr_usrreq() for PRU_CONNECT
|
||||
*
|
||||
* FUNCTION, ARGUMENTS, and RETURN VALUE:
|
||||
*
|
||||
* Determine the proper maximum transmission unit, i.e., MTU, to use, given
|
||||
* a) the header size for the network protocol and the max transmission
|
||||
* unit on the subnet interface, determined from the information in (inp),
|
||||
* b) the max size negotiated so far (negot)
|
||||
* c) the window size used by the tp connection (found in so),
|
||||
*
|
||||
* The result is put in the integer *size in its integer form and in
|
||||
* *negot in its logarithmic form.
|
||||
*
|
||||
* The rules are:
|
||||
* a) can only negotiate down from the value found in *negot.
|
||||
* b) the MTU must be < the windowsize,
|
||||
* c) If src and dest are on the same net,
|
||||
* we will negotiate the closest size larger than MTU but really USE
|
||||
* the actual device mtu - ll hdr sizes.
|
||||
* otherwise we negotiate the closest size smaller than MTU - ll hdr sizes.
|
||||
* Perform subnetwork dependent part of determining MTU information.
|
||||
* It appears that setting a double pointer to the rtentry associated with
|
||||
* the destination, and returning the header size for the network protocol
|
||||
* suffices.
|
||||
*
|
||||
* SIDE EFFECTS:
|
||||
* changes the values addressed by the arguments (size) and (negot)
|
||||
* and
|
||||
* when the peer is not on one of our directly connected subnets, it
|
||||
* looks up a route, leaving the route in the inpcb addressed by (inp)
|
||||
* Sets tp_routep pointer in pcb.
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
|
||||
void
|
||||
tpip_mtu(so, inp, size, negot)
|
||||
struct socket *so;
|
||||
struct inpcb *inp;
|
||||
int *size;
|
||||
u_char *negot;
|
||||
tpip_mtu(tpcb)
|
||||
register struct tp_pcb *tpcb;
|
||||
{
|
||||
register struct ifnet *ifp;
|
||||
struct ifnet *tpip_route();
|
||||
struct in_ifaddr *ia;
|
||||
register int i;
|
||||
int windowsize = so->so_rcv.sb_hiwat;
|
||||
struct inpcb *inp = (struct inpcb *)tpcb->tp_npcb;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tpip_mtu(0x%x,0x%x,0x%x,0x%x)\n",
|
||||
so, inp, size, negot);
|
||||
printf("tpip_mtu routing to addr 0x%x\n", inp->inp_faddr);
|
||||
printf("tpip_mtu(tpcb)\n", tpcb);
|
||||
printf("tpip_mtu routing to addr 0x%x\n", inp->inp_faddr.s_addr);
|
||||
ENDDEBUG
|
||||
IFTRACE(D_CONN)
|
||||
tptrace(TPPTmisc, "ENTER GET MTU: size negot \n",*size, *negot, 0, 0);
|
||||
ENDTRACE
|
||||
|
||||
*size = 1 << *negot;
|
||||
|
||||
if( *size > windowsize ) {
|
||||
*size = windowsize;
|
||||
}
|
||||
|
||||
ia = in_iaonnetof(in_netof(inp->inp_faddr));
|
||||
if ( ia == (struct in_ifaddr *)0 ) {
|
||||
ifp = tpip_route(&inp->inp_faddr);
|
||||
if( ifp == (struct ifnet *)0 )
|
||||
return ;
|
||||
} else
|
||||
ifp = ia->ia_ifp;
|
||||
|
||||
|
||||
/****************************************************************
|
||||
* TODO - make this indirect off the socket structure to the
|
||||
* network layer to get headersize
|
||||
* After all, who knows what lies below the IP layer?
|
||||
* Who knows how big the NL header will be?
|
||||
***************************************************************/
|
||||
|
||||
if( *size > ifp->if_mtu - sizeof(struct ip)) {
|
||||
*size = ifp->if_mtu - sizeof(struct ip);
|
||||
}
|
||||
for(i=TP_MIN_TPDUSIZE; (i<TP_MAX_TPDUSIZE && ((1<<i)<*size)) ; i++)
|
||||
;
|
||||
i--;
|
||||
|
||||
if (in_netof(inp->inp_laddr) != in_netof(inp->inp_faddr)) {
|
||||
i++;
|
||||
} else {
|
||||
*size = 1<<i;
|
||||
}
|
||||
*negot = i;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("GET MTU RETURNS: ifp %s size 0x%x negot 0x%x\n",
|
||||
ifp->if_name, *size, *negot);
|
||||
ENDDEBUG
|
||||
IFTRACE(D_CONN)
|
||||
tptrace(TPPTmisc, "EXIT GET MTU: tpcb size negot \n",
|
||||
*size, *negot, 0, 0);
|
||||
ENDTRACE
|
||||
tpcb->tp_routep = &(inp->inp_route.ro_rt);
|
||||
return (sizeof (struct ip));
|
||||
|
||||
}
|
||||
|
||||
@ -505,7 +431,7 @@ tpip_output_dg(laddr, faddr, m0, datalen, ro, nochksum)
|
||||
dump_mbuf(m, "tpip_output_dg before ip_output\n");
|
||||
ENDDEBUG
|
||||
|
||||
error = ip_output(m, NULL, ro, IP_ALLOWBROADCAST, NULL); /* XXX */
|
||||
error = ip_output(m, (struct mbuf *)0, ro, IP_ALLOWBROADCAST, NULL);
|
||||
|
||||
IFDEBUG(D_EMIT)
|
||||
printf("tpip_output_dg after ip_output\n");
|
||||
@ -534,7 +460,7 @@ bad:
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tpip_input(m, iplen)
|
||||
struct mbuf *m;
|
||||
int iplen;
|
||||
@ -601,9 +527,9 @@ tpip_input(m, iplen)
|
||||
dst.sin_family = AF_INET;
|
||||
dst.sin_len = sizeof(dst);
|
||||
|
||||
(void) tp_input(m, (struct sockaddr *)&src, (struct sockaddr *)&dst,
|
||||
0, tpip_output_dg, 0);
|
||||
return 0;
|
||||
tp_input(m, (struct sockaddr *)&src, (struct sockaddr *)&dst, 0,
|
||||
tpip_output_dg, 0);
|
||||
return;
|
||||
|
||||
discard:
|
||||
IFDEBUG(D_TPINPUT)
|
||||
@ -615,7 +541,6 @@ discard:
|
||||
m_freem(m);
|
||||
IncStat(ts_recv_drop);
|
||||
splx(s);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
||||
@ -641,7 +566,7 @@ void
|
||||
tpin_quench(inp)
|
||||
struct inpcb *inp;
|
||||
{
|
||||
tp_quench((struct tp_pcb *)inp->inp_socket->so_tpcb, PRC_QUENCH);
|
||||
tp_quench((struct tp_pcb *)inp->inp_socket->so_pcb, PRC_QUENCH);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -664,27 +589,27 @@ tpin_quench(inp)
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tpip_ctlinput(cmd, sin)
|
||||
int cmd;
|
||||
struct sockaddr_in *sin;
|
||||
{
|
||||
extern u_char inetctlerrmap[];
|
||||
extern ProtoHook tpin_abort();
|
||||
extern ProtoHook in_rtchange();
|
||||
extern struct in_addr zeroin_addr;
|
||||
void tp_quench __P((struct inpcb *, int));
|
||||
void tpin_abort __P((struct inpcb *, int));
|
||||
|
||||
if (sin->sin_family != AF_INET && sin->sin_family != AF_IMPLINK)
|
||||
return 0;
|
||||
return;
|
||||
if (sin->sin_addr.s_addr == INADDR_ANY)
|
||||
return 0;
|
||||
return;
|
||||
if (cmd < 0 || cmd > PRC_NCMDS)
|
||||
return 0;
|
||||
return;
|
||||
switch (cmd) {
|
||||
|
||||
case PRC_QUENCH:
|
||||
in_pcbnotify(&tp_inpcb, sin, 0,
|
||||
zeroin_addr, 0, cmd, (int (*)())tp_quench);
|
||||
in_pcbnotify(&tp_inpcb, (struct sockaddr *)sin, 0,
|
||||
zeroin_addr, 0, cmd, tp_quench);
|
||||
break;
|
||||
|
||||
case PRC_ROUTEDEAD:
|
||||
@ -692,7 +617,7 @@ tpip_ctlinput(cmd, sin)
|
||||
case PRC_UNREACH_NET:
|
||||
case PRC_IFDOWN:
|
||||
case PRC_HOSTDEAD:
|
||||
in_pcbnotify(&tp_inpcb, sin, 0,
|
||||
in_pcbnotify(&tp_inpcb, (struct sockaddr *)sin, 0,
|
||||
zeroin_addr, 0, cmd, in_rtchange);
|
||||
break;
|
||||
|
||||
@ -712,10 +637,9 @@ tpip_ctlinput(cmd, sin)
|
||||
case PRC_TIMXCEED_REASS:
|
||||
case PRC_PARAMPROB:
|
||||
*/
|
||||
in_pcbnotify(&tp_inpcb, sin, 0, zeroin_addr, 0,
|
||||
cmd, tpin_abort);
|
||||
in_pcbnotify(&tp_inpcb, (struct sockaddr *)sin, 0,
|
||||
zeroin_addr, 0, cmd, tpin_abort);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -737,16 +661,16 @@ tpip_ctlinput(cmd, sin)
|
||||
* NOTES:
|
||||
*/
|
||||
|
||||
ProtoHook
|
||||
tpin_abort(inp)
|
||||
void
|
||||
tpin_abort(inp, n)
|
||||
struct inpcb *inp;
|
||||
int n;
|
||||
{
|
||||
struct tp_event e;
|
||||
|
||||
e.ev_number = ER_TPDU;
|
||||
e.ATTR(ER_TPDU).e_reason = ENETRESET;
|
||||
(void) tp_driver((struct tp_pcb *)inp->inp_ppcb, &e);
|
||||
return 0;
|
||||
tp_driver((struct tp_pcb *)inp->inp_ppcb, &e);
|
||||
}
|
||||
|
||||
#ifdef ARGO_DEBUG
|
||||
@ -755,66 +679,5 @@ dump_inaddr(addr)
|
||||
{
|
||||
printf("INET: port 0x%x; addr 0x%x\n", addr->sin_port, addr->sin_addr);
|
||||
}
|
||||
#endif ARGO_DEBUG
|
||||
|
||||
/*
|
||||
* NAME: tpip_route()
|
||||
*
|
||||
* CALLED FROM: tpip_mtu()
|
||||
*
|
||||
* FUNCTION and ARGUMENTS: given a destination addresss,
|
||||
* find the interface that would be used to send something to this address.
|
||||
*
|
||||
* RETURNS: pointer to an ifnet structure
|
||||
*
|
||||
* SIDE EFFECTS:
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
struct ifnet *
|
||||
tpip_route(dst)
|
||||
struct in_addr *dst;
|
||||
{
|
||||
struct ifnet *ifp = (struct ifnet *)0;
|
||||
struct sockaddr_in insock;
|
||||
struct sockaddr_in *sin = &insock;
|
||||
struct rtentry *rt;
|
||||
struct ifaddr *ia;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tpip_route: dst is x%x\n", *dst);
|
||||
ENDDEBUG
|
||||
|
||||
bzero((caddr_t)sin, sizeof (*sin));
|
||||
sin->sin_family = AF_INET;
|
||||
sin->sin_len = sizeof(*sin);
|
||||
sin->sin_addr = *dst;
|
||||
|
||||
ia = ifa_ifwithdstaddr((struct sockaddr *)sin);
|
||||
if (ia == 0)
|
||||
ia = ifa_ifwithnet((struct sockaddr *)sin);
|
||||
if (ia != 0) {
|
||||
ifp = ia->ifa_ifp;
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tpip_route: ifp from ia:0x%x\n", ia);
|
||||
ENDDEBUG
|
||||
} else {
|
||||
rt = rtalloc1((struct sockaddr *)sin, 0);
|
||||
if (rt != 0) {
|
||||
ifp = rt->rt_ifp;
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tpip_route: ifp from rentry: 0x%x\n", rt);
|
||||
ENDDEBUG
|
||||
rtfree(rt);
|
||||
}
|
||||
}
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tpip_route: returning 0x%x\n", ifp);
|
||||
if (ifp)
|
||||
printf("tpip_route: if name %s unit 0x%x, mtu 0x%x\n",
|
||||
ifp->if_name, ifp->if_unit, ifp->if_mtu);
|
||||
ENDDEBUG
|
||||
return ifp;
|
||||
}
|
||||
|
||||
#endif INET
|
||||
#endif /* ARGO_DEBUG */
|
||||
#endif /* INET */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_input.c 7.19 (Berkeley) 6/27/91
|
||||
* $Id: tp_input.c,v 1.3 1993/12/18 00:43:36 mycroft Exp $
|
||||
* from: @(#)tp_input.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_input.c,v 1.4 1994/05/13 06:09:22 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,13 +61,11 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* tp_input() gets an mbuf chain from ip. Actually, not directly
|
||||
* from ip, because ip calls a net-level routine that strips off
|
||||
* the net header and then calls tp_input(), passing the proper type
|
||||
* of addresses for the address family in use (how it figures out
|
||||
* which AF is not yet determined.
|
||||
* which AF is not yet determined.)
|
||||
*
|
||||
* Decomposing the tpdu is some of the most laughable code. The variable-length
|
||||
* parameters and the problem of non-aligned memory references
|
||||
@ -94,9 +92,6 @@ SOFTWARE.
|
||||
#include <sys/errno.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/kernel.h>
|
||||
#include <sys/types.h>
|
||||
|
||||
#include <net/if.h>
|
||||
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/iso_errno.h>
|
||||
@ -109,6 +104,7 @@ SOFTWARE.
|
||||
#include <netiso/tp_trace.h>
|
||||
#include <netiso/tp_tpdu.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#ifdef TRUE
|
||||
#undef FALSE
|
||||
#undef TRUE
|
||||
@ -137,9 +133,21 @@ tp_inputprep(m)
|
||||
ENDDEBUG
|
||||
|
||||
while( m->m_len < 1 ) {
|
||||
if( (m = m_free(m)) == MNULL ) {
|
||||
return (struct mbuf *)0;
|
||||
}
|
||||
/* The "m_free" logic
|
||||
* if( (m = m_free(m)) == MNULL )
|
||||
* return (struct mbuf *)0;
|
||||
* would cause a system crash if ever executed.
|
||||
* This logic will be executed if the first mbuf
|
||||
* in the chain only contains a CLNP header. The m_free routine
|
||||
* will release the mbuf containing the CLNP header from the
|
||||
* chain and the new head of the chain will not have the
|
||||
* M_PKTHDR bit set. This routine, tp_inputprep, will
|
||||
* eventually call the "sbappendaddr" routine. "sbappendaddr"
|
||||
* calls "panic" if M_PKTHDR is not set. m_pullup is a cheap
|
||||
* way of keeping the head of the chain from being freed.
|
||||
*/
|
||||
if((m = m_pullup(m, 1)) == MNULL)
|
||||
return (MNULL);
|
||||
}
|
||||
if(((int)m->m_data) & 0x3) {
|
||||
/* If we are not 4-byte aligned, we have to be
|
||||
@ -149,7 +157,7 @@ tp_inputprep(m)
|
||||
caddr_t ocp = m->m_data;
|
||||
|
||||
m->m_data = (caddr_t)(((int)m->m_data) & ~0x3);
|
||||
ovbcopy(ocp, m->m_data, (unsigned)m->m_len);
|
||||
bcopy(ocp, m->m_data, (unsigned)m->m_len);
|
||||
}
|
||||
CHANGE_MTYPE(m, TPMT_DATA);
|
||||
|
||||
@ -208,11 +216,9 @@ static u_char tpdu_info[][4] =
|
||||
};
|
||||
|
||||
#define CHECK(Phrase, Erval, Stat, Whattodo, Loc)\
|
||||
if (Phrase) {error = (Erval); errlen = (int)(Loc); IncStat(Stat); tpibrk();\
|
||||
if (Phrase) {error = (Erval); errlen = (int)(Loc); IncStat(Stat);\
|
||||
goto Whattodo; }
|
||||
|
||||
tpibrk() {}
|
||||
|
||||
/*
|
||||
* WHENEVER YOU USE THE FOLLOWING MACRO,
|
||||
* BE SURE THE TPDUTYPE IS A LEGIT VALUE FIRST!
|
||||
@ -255,7 +261,7 @@ static struct socket *
|
||||
tp_newsocket(so, fname, cons_channel, class_to_use, netservice)
|
||||
struct socket *so;
|
||||
struct sockaddr *fname;
|
||||
u_int cons_channel;
|
||||
caddr_t cons_channel;
|
||||
u_char class_to_use;
|
||||
u_int netservice;
|
||||
{
|
||||
@ -306,7 +312,6 @@ tp_newsocket(so, fname, cons_channel, class_to_use, netservice)
|
||||
newtpcb->tp_l_tpdusize = tpcb->tp_l_tpdusize;
|
||||
newtpcb->tp_lsuffixlen = tpcb->tp_lsuffixlen;
|
||||
bcopy( tpcb->tp_lsuffix, newtpcb->tp_lsuffix, newtpcb->tp_lsuffixlen);
|
||||
soreserve(so, (u_long)tpcb->tp_winsize, (u_long)tpcb->tp_winsize);
|
||||
|
||||
if( /* old */ tpcb->tp_ucddata) {
|
||||
/*
|
||||
@ -376,7 +381,7 @@ tpcons_output()
|
||||
{
|
||||
return(0);
|
||||
}
|
||||
#endif !CONS
|
||||
#endif /* !CONS */
|
||||
|
||||
/*
|
||||
* NAME: tp_input()
|
||||
@ -404,41 +409,49 @@ tpcons_output()
|
||||
* mustn't be zero.
|
||||
* 2 seems like a reasonable minimum.
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tp_input(m, faddr, laddr, cons_channel, dgout_routine, ce_bit)
|
||||
register struct mbuf *m;
|
||||
struct sockaddr *faddr, *laddr; /* NSAP addresses */
|
||||
u_int cons_channel;
|
||||
caddr_t cons_channel;
|
||||
int (*dgout_routine)();
|
||||
int ce_bit;
|
||||
|
||||
{
|
||||
register struct tp_pcb *tpcb = (struct tp_pcb *)0;
|
||||
register struct tp_pcb *tpcb;
|
||||
register struct tpdu *hdr;
|
||||
struct socket *so;
|
||||
struct tp_event e;
|
||||
int error = 0;
|
||||
int error;
|
||||
unsigned dutype;
|
||||
u_short dref, sref = 0, acktime = 2, subseq = 0; /*VAX*/
|
||||
u_char preferred_class = 0, class_to_use = 0;
|
||||
u_char opt, dusize = TP_DFL_TPDUSIZE, addlopt = 0, version;
|
||||
u_short dref, sref, acktime, subseq;
|
||||
u_char preferred_class, class_to_use, pdusize;
|
||||
u_char opt, dusize, addlopt, version;
|
||||
#ifdef TP_PERF_MEAS
|
||||
u_char perf_meas;
|
||||
#endif TP_PERF_MEAS
|
||||
u_char fsufxlen = 0, lsufxlen = 0, intercepted = 0;
|
||||
caddr_t fsufxloc = 0, lsufxloc = 0;
|
||||
int tpdu_len = 0;
|
||||
u_int takes_data = FALSE;
|
||||
u_int fcc_present = FALSE;
|
||||
int errlen = 0;
|
||||
#endif /* TP_PERF_MEAS */
|
||||
u_char fsufxlen, lsufxlen;
|
||||
caddr_t fsufxloc, lsufxloc;
|
||||
int tpdu_len;
|
||||
u_int takes_data;
|
||||
u_int fcc_present;
|
||||
int errlen;
|
||||
struct tp_conn_param tpp;
|
||||
int tpcons_output();
|
||||
|
||||
again:
|
||||
hdr = mtod(m, struct tpdu *);
|
||||
tpcb = 0;
|
||||
error = errlen = tpdu_len = 0;
|
||||
takes_data = fcc_present = FALSE;
|
||||
acktime = 2; sref = subseq = 0;
|
||||
fsufxloc = lsufxloc = NULL;
|
||||
fsufxlen = lsufxlen =
|
||||
preferred_class = class_to_use = pdusize = addlopt = 0;
|
||||
dusize = TP_DFL_TPDUSIZE;
|
||||
#ifdef TP_PERF_MEAS
|
||||
GET_CUR_TIME( &e.e_time ); perf_meas = 0;
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
||||
IFDEBUG(D_TPINPUT)
|
||||
printf("tp_input(0x%x, ... 0x%x)\n", m, cons_channel);
|
||||
@ -507,7 +520,7 @@ again:
|
||||
IncStat(ts_inv_dutype);
|
||||
goto discard;
|
||||
}
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
CHECK( (dutype < TP_MIN_TPDUTYPE || dutype > TP_MAX_TPDUTYPE),
|
||||
E_TP_INV_TPDU, ts_inv_dutype, respond,
|
||||
@ -539,6 +552,16 @@ again:
|
||||
if (dusize < TP_MIN_TPDUSIZE || dusize > TP_MAX_TPDUSIZE)
|
||||
dusize = TP_DFL_TPDUSIZE;
|
||||
break;
|
||||
case TPP_ptpdu_size:
|
||||
switch (vbptr(P)->tpv_len) {
|
||||
case 1: pdusize = vbval(P, u_char); break;
|
||||
case 2: pdusize = ntohs(vbval(P, u_short)); break;
|
||||
default: ;
|
||||
IFDEBUG(D_TPINPUT)
|
||||
printf("malformed prefered TPDU option\n");
|
||||
ENDDEBUG
|
||||
}
|
||||
break;
|
||||
case TPP_addl_opt:
|
||||
vb_getval(P, u_char, addlopt);
|
||||
break;
|
||||
@ -579,7 +602,7 @@ again:
|
||||
case TPP_perf_meas:
|
||||
vb_getval(P, u_char, perf_meas);
|
||||
break;
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
||||
case TPP_vers:
|
||||
/* not in class 0; 1 octet; in CR_TPDU only */
|
||||
@ -660,21 +683,27 @@ again:
|
||||
goto respond;
|
||||
} else {
|
||||
register struct tp_pcb *t;
|
||||
|
||||
for (t = tp_intercepts; t ; t = t->tp_nextlisten) {
|
||||
if (laddr->sa_family != t->tp_nlproto->nlp_afamily)
|
||||
continue;
|
||||
if ((*t->tp_nlproto->nlp_cmpnetaddr)(
|
||||
t->tp_npcb, laddr, TP_LOCAL)) {
|
||||
intercepted = 1;
|
||||
goto check_duplicate_cr;
|
||||
}
|
||||
}
|
||||
/*
|
||||
* The intention here is to trap all CR requests
|
||||
* to a given nsap, for constructing transport
|
||||
* service bridges at user level; so these
|
||||
* intercepts should precede the normal listens.
|
||||
* Phrasing the logic in this way also allows for
|
||||
* mop-up listeners, which we don't currently implement.
|
||||
* We also wish to have a single socket be able to
|
||||
* listen over any network service provider,
|
||||
* (cons or clns or ip).
|
||||
*/
|
||||
for (t = tp_listeners; t ; t = t->tp_nextlisten)
|
||||
if (lsufxlen == t->tp_lsuffixlen &&
|
||||
bcmp(lsufxloc, t->tp_lsuffix, lsufxlen) == 0 &&
|
||||
laddr->sa_family == t->tp_nlproto->nlp_afamily)
|
||||
break;
|
||||
if ((t->tp_lsuffixlen == 0 ||
|
||||
(lsufxlen == t->tp_lsuffixlen &&
|
||||
bcmp(lsufxloc, t->tp_lsuffix, lsufxlen) == 0)) &&
|
||||
((t->tp_flags & TPF_GENERAL_ADDR) ||
|
||||
(laddr->sa_family == t->tp_domain &&
|
||||
(*t->tp_nlproto->nlp_cmpnetaddr)
|
||||
(t->tp_npcb, laddr, TP_LOCAL))))
|
||||
break;
|
||||
|
||||
CHECK(t == 0, E_TP_NO_SESSION, ts_inv_sufx, respond,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpduf - (caddr_t)hdr))
|
||||
/* _tpduf is the fixed part; add 2 to get the dref bits of
|
||||
@ -683,7 +712,6 @@ again:
|
||||
IFDEBUG(D_TPINPUT)
|
||||
printf("checking if dup CR\n");
|
||||
ENDDEBUG
|
||||
check_duplicate_cr:
|
||||
tpcb = t;
|
||||
for (t = tpcb->tp_next; t != tpcb; t = t->tp_next) {
|
||||
if (sref != t->tp_fref)
|
||||
@ -728,6 +756,7 @@ again:
|
||||
tpp = tpcb->_tp_param;
|
||||
tpp.p_class = class_to_use;
|
||||
tpp.p_tpdusize = dusize;
|
||||
tpp.p_ptpdusize = pdusize;
|
||||
tpp.p_xtd_format = (opt & TPO_XTD_FMT) == TPO_XTD_FMT;
|
||||
tpp.p_xpd_service = (addlopt & TPAO_USE_TXPD) == TPAO_USE_TXPD;
|
||||
tpp.p_use_checksum = (tpp.p_class == TP_CLASS_0)?0:
|
||||
@ -737,11 +766,11 @@ again:
|
||||
tpp.p_use_efc = (opt & TPO_USE_EFC) == TPO_USE_EFC;
|
||||
tpp.p_use_nxpd = (addlopt & TPAO_USE_NXPD) == TPAO_USE_NXPD;
|
||||
tpp.p_use_rcc = (addlopt & TPAO_USE_RCC) == TPAO_USE_RCC;
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
|
||||
CHECK(
|
||||
tp_consistency(tpcb, 0 /* not force or strict */, &tpp) != 0,
|
||||
E_TP_NEGOT_FAILED, ts_negotfailed, respond,
|
||||
E_TP_NEGOT_FAILED, ts_negotfailed, clear_parent_tcb,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpdufr.CRCC - (caddr_t)hdr)
|
||||
/* ^ more or less the location of class */
|
||||
)
|
||||
@ -755,7 +784,7 @@ again:
|
||||
ENDTRACE
|
||||
CHECK(
|
||||
((class_to_use == TP_CLASS_0)&&(dgout_routine != tpcons_output)),
|
||||
E_TP_NEGOT_FAILED, ts_negotfailed, respond,
|
||||
E_TP_NEGOT_FAILED, ts_negotfailed, clear_parent_tcb,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpdufr.CRCC - (caddr_t)hdr)
|
||||
/* ^ more or less the location of class */
|
||||
)
|
||||
@ -792,6 +821,9 @@ again:
|
||||
printf("tp_newsocket returns 0\n");
|
||||
ENDDEBUG
|
||||
goto discard;
|
||||
clear_parent_tcb:
|
||||
tpcb = 0;
|
||||
goto respond;
|
||||
}
|
||||
tpcb = sototpcb(so);
|
||||
insque(tpcb, parent_tpcb);
|
||||
@ -801,18 +833,20 @@ again:
|
||||
* kind of like a pcbconnect() but don't need
|
||||
* or want all those checks.
|
||||
*/
|
||||
(tpcb->tp_nlproto->nlp_putnetaddr)(so->so_pcb, faddr, TP_FOREIGN);
|
||||
(tpcb->tp_nlproto->nlp_putnetaddr)(so->so_pcb, laddr, TP_LOCAL);
|
||||
(tpcb->tp_nlproto->nlp_putnetaddr)(tpcb->tp_npcb, faddr, TP_FOREIGN);
|
||||
(tpcb->tp_nlproto->nlp_putnetaddr)(tpcb->tp_npcb, laddr, TP_LOCAL);
|
||||
|
||||
/* stash the f suffix in the new tpcb */
|
||||
bcopy(fsufxloc, tpcb->tp_fsuffix, fsufxlen);
|
||||
/* l suffix is already there, unless this is an intercept case */
|
||||
if (intercepted)
|
||||
bcopy(lsufxloc, tpcb->tp_lsuffix, lsufxlen);
|
||||
if (tpcb->tp_fsuffixlen = fsufxlen) {
|
||||
bcopy(fsufxloc, tpcb->tp_fsuffix, fsufxlen);
|
||||
(tpcb->tp_nlproto->nlp_putsufx)
|
||||
(tpcb->tp_npcb, fsufxloc, fsufxlen, TP_FOREIGN);
|
||||
}
|
||||
/* stash the l suffix in the new tpcb */
|
||||
tpcb->tp_lsuffixlen = lsufxlen;
|
||||
bcopy(lsufxloc, tpcb->tp_lsuffix, lsufxlen);
|
||||
(tpcb->tp_nlproto->nlp_putsufx)
|
||||
(so->so_pcb, fsufxloc, fsufxlen, TP_FOREIGN);
|
||||
(tpcb->tp_nlproto->nlp_putsufx)
|
||||
(so->so_pcb, lsufxloc, lsufxlen, TP_LOCAL);
|
||||
(tpcb->tp_npcb, lsufxloc, lsufxlen, TP_LOCAL);
|
||||
#ifdef TP_PERF_MEAS
|
||||
if( tpcb->tp_perf_on = perf_meas ) { /* assignment */
|
||||
/* ok, let's create an mbuf for stashing the
|
||||
@ -820,7 +854,7 @@ again:
|
||||
*/
|
||||
(void) tp_setup_perf(tpcb);
|
||||
}
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
tpcb->tp_fref = sref;
|
||||
|
||||
/* We've already checked for consistency with the options
|
||||
@ -837,12 +871,6 @@ again:
|
||||
if(tpcb->tp_xtd_format)
|
||||
IncStat(ts_xtd_fmt);
|
||||
|
||||
/*
|
||||
* Get the maximum transmission unit from the lower layer(s)
|
||||
* so we can negotiate a reasonable max TPDU size.
|
||||
*/
|
||||
(tpcb->tp_nlproto->nlp_mtu)(so, so->so_pcb,
|
||||
&tpcb->tp_l_tpdusize, &tpcb->tp_tpdusize, 0);
|
||||
tpcb->tp_peer_acktime = acktime;
|
||||
|
||||
/*
|
||||
@ -854,15 +882,14 @@ again:
|
||||
/*tpcb->tp_fref = 0;*/
|
||||
ENDDEBUG
|
||||
}
|
||||
LOCAL_CREDIT(tpcb);
|
||||
IncStat(ts_CR_rcvd);
|
||||
if (!tpcb->tp_cebit_off) {
|
||||
tpcb->tp_win_recv = tp_start_win << 8;
|
||||
tpcb->tp_cong_sample.cs_size = 0;
|
||||
LOCAL_CREDIT(tpcb);
|
||||
CONG_INIT_SAMPLE(tpcb);
|
||||
CONG_UPDATE_SAMPLE(tpcb, ce_bit);
|
||||
}
|
||||
tpcb->tp_ackrcvd = 0;
|
||||
} else if ( dutype == ER_TPDU_type ) {
|
||||
/*
|
||||
* ER TPDUs have to be recognized separately
|
||||
@ -877,10 +904,10 @@ again:
|
||||
IncStat(ts_ER_rcvd);
|
||||
e.ev_number = ER_TPDU;
|
||||
e.ATTR(ER_TPDU).e_reason = (u_char)hdr->tpdu_ERreason;
|
||||
CHECK (((int)dref <= 0 || dref >= N_TPREF ||
|
||||
CHECK (((int)dref <= 0 || dref >= tp_refinfo.tpr_size ||
|
||||
(tpcb = tp_ref[dref].tpr_pcb ) == (struct tp_pcb *) 0 ||
|
||||
tpcb->tp_refp->tpr_state == REF_FREE ||
|
||||
tpcb->tp_refp->tpr_state == REF_FROZEN),
|
||||
tpcb->tp_refstate == REF_FREE ||
|
||||
tpcb->tp_refstate == REF_FROZEN),
|
||||
E_TP_MISM_REFS, ts_inv_dref, discard, 0)
|
||||
|
||||
} else {
|
||||
@ -890,44 +917,35 @@ again:
|
||||
* _tpduf is the fixed part; add 2 to get the dref bits of
|
||||
* the fixed part (can't take the address of a bit field)
|
||||
*/
|
||||
#ifdef old_history
|
||||
if(cons_channel) {
|
||||
#ifdef NARGOXTWENTYFIVE
|
||||
extern struct tp_pcb *cons_chan_to_tpcb();
|
||||
#ifdef TPCONS
|
||||
if (cons_channel && dutype == DT_TPDU_type) {
|
||||
struct isopcb *isop = ((struct isopcb *)
|
||||
((struct pklcd *)cons_channel)->lcd_upnext);
|
||||
if (isop && isop->isop_refcnt == 1 && isop->isop_socket &&
|
||||
(tpcb = sototpcb(isop->isop_socket)) &&
|
||||
(tpcb->tp_class == TP_CLASS_0/* || == CLASS_1 */)) {
|
||||
IFDEBUG(D_TPINPUT)
|
||||
printf("tpinput_dt: class 0 short circuit\n");
|
||||
ENDDEBUG
|
||||
dref = tpcb->tp_lref;
|
||||
sref = tpcb->tp_fref;
|
||||
CHECK( (tpcb->tp_refstate == REF_FREE),
|
||||
E_TP_MISM_REFS,ts_inv_dref, nonx_dref,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpduf - (caddr_t)hdr))
|
||||
goto tp0_data;
|
||||
}
|
||||
|
||||
tpcb = cons_chan_to_tpcb( cons_channel );
|
||||
/* Problem: We may have a legit
|
||||
* error situation yet we may or may not have
|
||||
* a correspondence between the tpcb and the vc,
|
||||
* e.g., TP4cr--> <no dice, respond w/ DR on vc>
|
||||
* <--- DR
|
||||
* Now it's up to TP to look at the tpdu and do one of:
|
||||
* confirm(dgm)(cr), confirm(circuit)(cr), reject(cr), or
|
||||
* nothing, if the circuit is already open (any other tpdu).
|
||||
* Sigh.
|
||||
*/
|
||||
|
||||
/* I don't know about this error value */
|
||||
CHECK( (tpcb == (struct tp_pcb *)0) ,
|
||||
E_TP_NO_CR_ON_NC, ts_inv_dref, respond,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpduf - (caddr_t)hdr))
|
||||
#else
|
||||
printf("tp_input(): X25 NOT CONFIGURED!!\n");
|
||||
}
|
||||
#endif
|
||||
} else
|
||||
/* we've now made the error reporting thing check for
|
||||
multiple channels and not close out if more than
|
||||
one in use */
|
||||
#endif old_history
|
||||
{
|
||||
|
||||
CHECK( ((int)dref <= 0 || dref >= N_TPREF) ,
|
||||
CHECK( ((int)dref <= 0 || dref >= tp_refinfo.tpr_size) ,
|
||||
E_TP_MISM_REFS,ts_inv_dref, nonx_dref,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpduf - (caddr_t)hdr))
|
||||
CHECK( ((tpcb = tp_ref[dref].tpr_pcb ) == (struct tp_pcb *) 0 ),
|
||||
E_TP_MISM_REFS,ts_inv_dref, nonx_dref,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpduf - (caddr_t)hdr))
|
||||
CHECK( (tpcb->tp_refp->tpr_state == REF_FREE),
|
||||
CHECK( (tpcb->tp_refstate == REF_FREE),
|
||||
E_TP_MISM_REFS,ts_inv_dref, nonx_dref,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpduf - (caddr_t)hdr))
|
||||
}
|
||||
@ -937,7 +955,7 @@ again:
|
||||
ENDDEBUG
|
||||
|
||||
/* causes a DR to be sent for CC; ER for all else */
|
||||
CHECK( (tpcb->tp_refp->tpr_state == REF_FROZEN),
|
||||
CHECK( (tpcb->tp_refstate == REF_FROZEN),
|
||||
(dutype == CC_TPDU_type?E_TP_NO_SESSION:E_TP_MISM_REFS),
|
||||
ts_inv_dref, respond,
|
||||
(1 + 2 + (caddr_t)&hdr->_tpduf - (caddr_t)hdr))
|
||||
@ -958,6 +976,7 @@ again:
|
||||
CONG_UPDATE_SAMPLE(tpcb, ce_bit);
|
||||
|
||||
dusize = tpcb->tp_tpdusize;
|
||||
pdusize = tpcb->tp_ptpdusize;
|
||||
|
||||
dutype = hdr->tpdu_type << 8; /* for the switch below */
|
||||
|
||||
@ -983,6 +1002,23 @@ again:
|
||||
ENDDEBUG
|
||||
}
|
||||
break;
|
||||
caseof( CC_TPDU_type, TPP_ptpdu_size ):
|
||||
{
|
||||
u_short opdusize = pdusize;
|
||||
switch (vbptr(P)->tpv_len) {
|
||||
case 1: pdusize = vbval(P, u_char); break;
|
||||
case 2: pdusize = ntohs(vbval(P, u_short)); break;
|
||||
default: ;
|
||||
IFDEBUG(D_TPINPUT)
|
||||
printf("malformed prefered TPDU option\n");
|
||||
ENDDEBUG
|
||||
}
|
||||
CHECK( (pdusize == 0 ||
|
||||
(opdusize && (pdusize > opdusize))),
|
||||
E_TP_INV_PVAL, ts_inv_pval, respond,
|
||||
(1 + (caddr_t)&vbptr(P)->tpv_val - (caddr_t)hdr) )
|
||||
}
|
||||
break;
|
||||
caseof( CC_TPDU_type, TPP_calling_sufx):
|
||||
IFDEBUG(D_TPINPUT)
|
||||
printf("CC calling (local) sufxlen 0x%x\n", lsufxlen);
|
||||
@ -1034,14 +1070,14 @@ again:
|
||||
* to pass this info to the user anyway
|
||||
*/
|
||||
break;
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
|
||||
caseof( AK_TPDU_type, TPP_subseq ):
|
||||
/* used after reduction of window */
|
||||
vb_getval(P, u_short, subseq);
|
||||
subseq = ntohs(subseq);
|
||||
IFDEBUG(D_ACKRECV)
|
||||
printf("AK Subsequence # 0x%x\n", subseq);
|
||||
printf("AK dref 0x%x Subseq 0x%x\n", dref, subseq);
|
||||
ENDDEBUG
|
||||
break;
|
||||
|
||||
@ -1058,8 +1094,8 @@ again:
|
||||
ysubseq = ntohs(ysubseq);
|
||||
ycredit = ntohs(ycredit);
|
||||
IFDEBUG(D_ACKRECV)
|
||||
printf("AK FCC lwe 0x%x, subseq 0x%x, cdt 0x%x\n",
|
||||
ylwe, ysubseq, ycredit);
|
||||
printf("%s%x, subseq 0x%x, cdt 0x%x dref 0x%x\n",
|
||||
"AK FCC lwe 0x", ylwe, ysubseq, ycredit, dref);
|
||||
ENDDEBUG
|
||||
}
|
||||
break;
|
||||
@ -1093,6 +1129,7 @@ again:
|
||||
tpp = tpcb->_tp_param;
|
||||
tpp.p_class = (1<<hdr->tpdu_CCclass);
|
||||
tpp.p_tpdusize = dusize;
|
||||
tpp.p_ptpdusize = pdusize;
|
||||
tpp.p_dont_change_params = 0;
|
||||
tpp.p_xtd_format = (opt & TPO_XTD_FMT) == TPO_XTD_FMT;
|
||||
tpp.p_xpd_service = (addlopt & TPAO_USE_TXPD) == TPAO_USE_TXPD;
|
||||
@ -1101,7 +1138,7 @@ again:
|
||||
tpp.p_use_efc = (opt & TPO_USE_EFC) == TPO_USE_EFC;
|
||||
tpp.p_use_nxpd = (addlopt & TPAO_USE_NXPD) == TPAO_USE_NXPD;
|
||||
tpp.p_use_rcc = (addlopt & TPAO_USE_RCC) == TPAO_USE_RCC;
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
|
||||
CHECK(
|
||||
tp_consistency(tpcb, TP_FORCE, &tpp) != 0,
|
||||
@ -1144,16 +1181,6 @@ again:
|
||||
hdr->tpdu_CCclass);
|
||||
ENDTRACE
|
||||
|
||||
/*
|
||||
* Get the maximum transmission unit from the lower layer(s)
|
||||
* so we can decide how large a TPDU size to negotiate.
|
||||
* It would be nice if the arguments to this
|
||||
* were more reasonable.
|
||||
*/
|
||||
(tpcb->tp_nlproto->nlp_mtu)(tpcb->tp_sock, tpcb->tp_sock->so_pcb,
|
||||
&tpcb->tp_l_tpdusize, &tpcb->tp_tpdusize, 0);
|
||||
|
||||
|
||||
/* if called or calling suffices appeared on the CC,
|
||||
* they'd better jive with what's in the pcb
|
||||
*/
|
||||
@ -1235,7 +1262,7 @@ again:
|
||||
#else
|
||||
e.ATTR(AK_TPDU).e_cdt = hdr->tpdu_AKcdtX;
|
||||
e.ATTR(AK_TPDU).e_seq = hdr->tpdu_AKseqX;
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else {
|
||||
e.ATTR(AK_TPDU).e_cdt = hdr->tpdu_AKcdt;
|
||||
e.ATTR(AK_TPDU).e_seq = hdr->tpdu_AKseq;
|
||||
@ -1260,7 +1287,7 @@ again:
|
||||
e.ATTR(XAK_TPDU).e_seq = seqeotX.s_seq;
|
||||
#else
|
||||
e.ATTR(XAK_TPDU).e_seq = hdr->tpdu_XAKseqX;
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else {
|
||||
e.ATTR(XAK_TPDU).e_seq = hdr->tpdu_XAKseq;
|
||||
}
|
||||
@ -1278,7 +1305,7 @@ again:
|
||||
e.ATTR(XPD_TPDU).e_seq = seqeotX.s_seq;
|
||||
#else
|
||||
e.ATTR(XPD_TPDU).e_seq = hdr->tpdu_XPDseqX;
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else {
|
||||
e.ATTR(XPD_TPDU).e_seq = hdr->tpdu_XPDseq;
|
||||
}
|
||||
@ -1301,6 +1328,7 @@ again:
|
||||
ENDDEBUG
|
||||
}
|
||||
if (tpcb->tp_class == TP_CLASS_0) {
|
||||
tp0_data:
|
||||
e.ATTR(DT_TPDU).e_seq = 0; /* actually don't care */
|
||||
e.ATTR(DT_TPDU).e_eot = (((struct tp0du *)hdr)->tp0du_eot);
|
||||
} else if (tpcb->tp_xtd_format) {
|
||||
@ -1313,7 +1341,7 @@ again:
|
||||
#else
|
||||
e.ATTR(DT_TPDU).e_seq = hdr->tpdu_DTseqX;
|
||||
e.ATTR(DT_TPDU).e_eot = hdr->tpdu_DTeotX;
|
||||
#endif BYTE_ORDER
|
||||
#endif /* BYTE_ORDER */
|
||||
} else {
|
||||
e.ATTR(DT_TPDU).e_seq = hdr->tpdu_DTseq;
|
||||
e.ATTR(DT_TPDU).e_eot = hdr->tpdu_DTeot;
|
||||
@ -1489,7 +1517,7 @@ separate:
|
||||
printf("tp_input : after m_freem 0x%x\n", m);
|
||||
ENDDEBUG
|
||||
}
|
||||
return (ProtoHook) tpcb;
|
||||
return;
|
||||
|
||||
discard:
|
||||
/* class 4: drop the tpdu */
|
||||
@ -1504,7 +1532,7 @@ discard:
|
||||
ENDTRACE
|
||||
m_freem(m);
|
||||
IncStat(ts_recv_drop);
|
||||
return (ProtoHook)0;
|
||||
return;
|
||||
|
||||
nonx_dref:
|
||||
switch (dutype) {
|
||||
@ -1527,16 +1555,15 @@ respond:
|
||||
goto discard;
|
||||
(void) tp_error_emit(error, (u_long)sref, (struct sockaddr_iso *)faddr,
|
||||
(struct sockaddr_iso *)laddr, m, errlen, tpcb,
|
||||
(int)cons_channel, dgout_routine);
|
||||
cons_channel, dgout_routine);
|
||||
IFDEBUG(D_ERROR_EMIT)
|
||||
printf("tp_input after error_emit\n");
|
||||
ENDDEBUG
|
||||
|
||||
#ifdef lint
|
||||
printf("",sref,opt);
|
||||
#endif lint
|
||||
#endif /* lint */
|
||||
IncStat(ts_recv_drop);
|
||||
return (ProtoHook)0;
|
||||
}
|
||||
|
||||
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_ip.h 7.3 (Berkeley) 5/6/91
|
||||
* $Id: tp_ip.h,v 1.3 1993/05/20 05:27:42 cgd Exp $
|
||||
* from: @(#)tp_ip.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_ip.h,v 1.4 1994/05/13 06:09:24 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_IP_H_
|
||||
#define _NETISO_TP_IP_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,25 +61,25 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* internet IP-dependent structures and include files
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef SOCK_STREAM
|
||||
#include "socket.h"
|
||||
#endif SOCK_STREAM
|
||||
#ifndef _NETISO_TP_IP_H_
|
||||
#define _NETISO_TP_IP_H_
|
||||
|
||||
#include "../netinet/in.h"
|
||||
#include "../netinet/in_systm.h"
|
||||
#include "../netinet/ip.h"
|
||||
#include "../net/route.h"
|
||||
#include "../netinet/in_pcb.h"
|
||||
#include "../netinet/ip_var.h"
|
||||
#ifndef SOCK_STREAM
|
||||
#include <sys/socket.h>
|
||||
#endif
|
||||
|
||||
#include <netinet/in.h>
|
||||
#include <netinet/in_systm.h>
|
||||
#include <netinet/ip.h>
|
||||
#include <net/route.h>
|
||||
#include <netinet/in_pcb.h>
|
||||
#include <netinet/ip_var.h>
|
||||
|
||||
|
||||
struct inpcb tp_inpcb;
|
||||
/* queue of active inpcbs for tp ; for tp with dod ip */
|
||||
|
||||
#endif /* !_NETISO_TP_IP_H_ */
|
||||
#endif /* _NETISO_TP_IP_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_iso.c 7.11 (Berkeley) 5/6/91
|
||||
* $Id: tp_iso.c,v 1.3 1993/12/18 00:43:38 mycroft Exp $
|
||||
* from: @(#)tp_iso.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_iso.c,v 1.4 1994/05/13 06:09:25 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* Here is where you find the iso-dependent code. We've tried
|
||||
* keep all net-level and (primarily) address-family-dependent stuff
|
||||
* out of the tp source, and everthing here is reached indirectly
|
||||
@ -108,6 +106,8 @@ SOFTWARE.
|
||||
#include <netiso/tp_clnp.h>
|
||||
#include <netiso/cltp_var.h>
|
||||
|
||||
void tpclnp_ctlinput();
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* pr_usrreq() on PRU_BIND, PRU_CONNECT, PRU_ACCEPT, and PRU_PEERADDR
|
||||
@ -312,103 +312,41 @@ iso_getnetaddr( isop, name, which)
|
||||
else
|
||||
name->m_len = 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tp_input() on incoming CR, CC, and pr_usrreq() for PRU_CONNECT
|
||||
* FUNCTION, ARGUMENTS, SIDE EFFECTS and RETURN VALUE:
|
||||
* Determine the proper maximum transmission unit, i.e., MTU, to use, given
|
||||
* a) the header size for the network protocol and the max transmission
|
||||
* unit on the subnet interface, determined from the information in (isop),
|
||||
* b) the max size negotiated so far (negot)
|
||||
* c) the window size used by the tp connection (found in so),
|
||||
* NAME: tpclnp_mtu()
|
||||
*
|
||||
* The result is put in the integer *size in its integer form and in
|
||||
* *negot in its logarithmic form.
|
||||
* CALLED FROM:
|
||||
* tp_route_to() on incoming CR, CC, and pr_usrreq() for PRU_CONNECT
|
||||
*
|
||||
* FUNCTION, ARGUMENTS, and RETURN VALUE:
|
||||
*
|
||||
* Perform subnetwork dependent part of determining MTU information.
|
||||
* It appears that setting a double pointer to the rtentry associated with
|
||||
* the destination, and returning the header size for the network protocol
|
||||
* suffices.
|
||||
*
|
||||
* The rules are:
|
||||
* a) can only negotiate down from the value found in *negot.
|
||||
* b) the MTU must be < the windowsize,
|
||||
* c) If src and dest are on the same net,
|
||||
* we will negotiate the closest size larger than MTU but really USE
|
||||
* the actual device mtu - ll hdr sizes.
|
||||
* otherwise we negotiate the closest size smaller than MTU - ll hdr sizes.
|
||||
* SIDE EFFECTS:
|
||||
* Sets tp_routep pointer in pcb.
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
|
||||
void
|
||||
tpclnp_mtu(so, isop, size, negot )
|
||||
struct socket *so;
|
||||
struct isopcb *isop;
|
||||
int *size;
|
||||
u_char *negot;
|
||||
tpclnp_mtu(tpcb)
|
||||
register struct tp_pcb *tpcb;
|
||||
{
|
||||
struct ifnet *ifp = 0;
|
||||
struct iso_ifaddr *ia = 0;
|
||||
register int i;
|
||||
int windowsize = so->so_rcv.sb_hiwat;
|
||||
int clnp_size, mtu;
|
||||
int sizeismtu = 0;
|
||||
register struct rtentry *rt = isop->isop_route.ro_rt;
|
||||
struct isopcb *isop = (struct isopcb *)tpcb->tp_npcb;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tpclnp_mtu(0x%x,0x%x,0x%x,0x%x)\n", so, isop, size, negot);
|
||||
printf("tpclnp_mtu(tpcb)\n", tpcb);
|
||||
ENDDEBUG
|
||||
IFTRACE(D_CONN)
|
||||
tptrace(TPPTmisc, "ENTER GET MTU: size negot \n",*size, *negot, 0, 0);
|
||||
ENDTRACE
|
||||
tpcb->tp_routep = &(isop->isop_route.ro_rt);
|
||||
if (tpcb->tp_netservice == ISO_CONS)
|
||||
return 0;
|
||||
else
|
||||
return (sizeof(struct clnp_fixed) + sizeof(struct clnp_segment) +
|
||||
2 * sizeof(struct iso_addr));
|
||||
|
||||
*size = 1 << *negot;
|
||||
|
||||
if( *size > windowsize ) {
|
||||
*size = windowsize;
|
||||
}
|
||||
|
||||
if (rt == 0 || (rt->rt_flags & RTF_UP == 0) ||
|
||||
(ia = (struct iso_ifaddr *)rt->rt_ifa) == 0 ||
|
||||
(ifp = ia->ia_ifp) == 0) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tpclnp_mtu routing abort rt=0x%x ia=0x%x ifp=0x%x\n",
|
||||
rt, ia, ifp)
|
||||
ENDDEBUG
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/* TODO - make this indirect off the socket structure to the
|
||||
* network layer to get headersize
|
||||
*/
|
||||
clnp_size = sizeof(struct clnp_fixed) + sizeof(struct clnp_segment) +
|
||||
2 * sizeof(struct iso_addr);
|
||||
mtu = SN_MTU(ifp, rt) - clnp_size;
|
||||
if(*size > mtu) {
|
||||
*size = mtu;
|
||||
sizeismtu = 1;
|
||||
}
|
||||
/* have to transform size to the log2 of size */
|
||||
for(i=TP_MIN_TPDUSIZE; (i<=TP_MAX_TPDUSIZE && ((1<<i) <= *size)) ; i++)
|
||||
;
|
||||
i--;
|
||||
|
||||
IFTRACE(D_CONN)
|
||||
tptrace(TPPTmisc, "GET MTU MID: tpcb size negot i \n",
|
||||
*size, *negot, i, 0);
|
||||
ENDTRACE
|
||||
|
||||
*size = 1<<i;
|
||||
*negot = i;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("GET MTU RETURNS: ifp %s size 0x%x negot 0x%x\n",
|
||||
ifp->if_name, *size, *negot);
|
||||
ENDDEBUG
|
||||
IFTRACE(D_CONN)
|
||||
tptrace(TPPTmisc, "EXIT GET MTU: tpcb size negot \n",
|
||||
*size, *negot, 0, 0);
|
||||
ENDTRACE
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tp_emit()
|
||||
@ -416,7 +354,7 @@ tpclnp_mtu(so, isop, size, negot )
|
||||
* Take a packet(m0) from tp and package it so that clnp will accept it.
|
||||
* This means prepending space for the clnp header and filling in a few
|
||||
* of the fields.
|
||||
* inp is the isopcb structure; datalen is the length of the data in the
|
||||
* isop is the isopcb structure; datalen is the length of the data in the
|
||||
* mbuf string m0.
|
||||
* RETURN VALUE:
|
||||
* whatever (E*) is returned form the net layer output routine.
|
||||
@ -520,15 +458,14 @@ tpclnp_output_dg(laddr, faddr, m0, datalen, ro, nochksum)
|
||||
* Take a packet (m) from clnp, strip off the clnp header and give it to tp
|
||||
* No return value.
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tpclnp_input(m, src, dst, clnp_len, ce_bit)
|
||||
register struct mbuf *m;
|
||||
struct sockaddr_iso *src, *dst;
|
||||
int clnp_len, ce_bit;
|
||||
{
|
||||
int s = splnet();
|
||||
struct mbuf *tp_inputprep();
|
||||
int tp_input(), cltp_input(), (*input)() = tp_input;
|
||||
void tp_input(), cltp_input(), (*input)() = tp_input;
|
||||
|
||||
IncStat(ts_pkt_rcvd);
|
||||
|
||||
@ -542,13 +479,27 @@ tpclnp_input(m, src, dst, clnp_len, ce_bit)
|
||||
* First, strip off the Clnp header. leave the mbuf there for the
|
||||
* pullup that follows.
|
||||
*/
|
||||
|
||||
m->m_len -= clnp_len;
|
||||
m->m_data += clnp_len;
|
||||
|
||||
m->m_pkthdr.len -= clnp_len;
|
||||
/* XXXX: should probably be in clnp_input */
|
||||
switch (dst->siso_data[dst->siso_nlen - 1]) {
|
||||
#ifdef TUBA
|
||||
case ISOPROTO_TCP:
|
||||
tuba_tcpinput(m, src, dst);
|
||||
return;
|
||||
#endif
|
||||
case 0:
|
||||
if (m->m_len == 0 && (m = m_pullup(m, 1)) == 0)
|
||||
return;
|
||||
if (*(mtod(m, u_char *)) == ISO10747_IDRP) {
|
||||
idrp_input(m, src, dst);
|
||||
return;
|
||||
}
|
||||
}
|
||||
m = tp_inputprep(m);
|
||||
if (m == 0)
|
||||
return 0;
|
||||
return;
|
||||
if (mtod(m, u_char *)[1] == UD_TPDU_type)
|
||||
input = cltp_input;
|
||||
|
||||
@ -564,31 +515,27 @@ tpclnp_input(m, src, dst, clnp_len, ce_bit)
|
||||
dump_isoaddr(dst);
|
||||
ENDDEBUG
|
||||
|
||||
(void) (*input)(m, (struct sockaddr *)src, (struct sockaddr *)dst,
|
||||
0, tpclnp_output_dg, ce_bit);
|
||||
(*input)(m, (struct sockaddr *)src, (struct sockaddr *)dst, 0,
|
||||
tpclnp_output_dg, ce_bit);
|
||||
|
||||
IFDEBUG(D_QUENCH)
|
||||
{
|
||||
if(time.tv_usec & 0x4 && time.tv_usec & 0x40) {
|
||||
printf("tpclnp_input: FAKING %s\n",
|
||||
tp_stat.ts_pkt_rcvd & 0x1?"QUENCH":"QUENCH2");
|
||||
if(tp_stat.ts_pkt_rcvd & 0x1) {
|
||||
if (tp_stat.ts_pkt_rcvd & 0x1)
|
||||
tpclnp_ctlinput(PRC_QUENCH, &src);
|
||||
} else {
|
||||
else
|
||||
tpclnp_ctlinput(PRC_QUENCH2, &src);
|
||||
}
|
||||
}
|
||||
}
|
||||
ENDDEBUG
|
||||
|
||||
splx(s);
|
||||
return 0;
|
||||
}
|
||||
|
||||
ProtoHook
|
||||
void
|
||||
iso_rtchange()
|
||||
{
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
@ -601,7 +548,7 @@ void
|
||||
tpiso_decbit(isop)
|
||||
struct isopcb *isop;
|
||||
{
|
||||
tp_quench((struct tp_pcb *)isop->isop_socket->so_tpcb, PRC_QUENCH2);
|
||||
tp_quench((struct tp_pcb *)isop->isop_socket->so_pcb, PRC_QUENCH2);
|
||||
}
|
||||
/*
|
||||
* CALLED FROM:
|
||||
@ -613,7 +560,7 @@ void
|
||||
tpiso_quench(isop)
|
||||
struct isopcb *isop;
|
||||
{
|
||||
tp_quench((struct tp_pcb *)isop->isop_socket->so_tpcb, PRC_QUENCH);
|
||||
tp_quench((struct tp_pcb *)isop->isop_socket->so_pcb, PRC_QUENCH);
|
||||
}
|
||||
|
||||
/*
|
||||
@ -627,16 +574,13 @@ tpiso_quench(isop)
|
||||
* (cmd) is the type of ICMP error.
|
||||
* (siso) is the address of the guy who sent the ER CLNPDU
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tpclnp_ctlinput(cmd, siso)
|
||||
int cmd;
|
||||
struct sockaddr_iso *siso;
|
||||
{
|
||||
extern u_char inetctlerrmap[];
|
||||
extern ProtoHook tpiso_abort();
|
||||
extern ProtoHook iso_rtchange();
|
||||
extern ProtoHook tpiso_reset();
|
||||
void iso_pcbnotify();
|
||||
void tpiso_abort(), iso_rtchange(), tpiso_reset(), iso_pcbnotify();
|
||||
|
||||
IFDEBUG(D_TPINPUT)
|
||||
printf("tpclnp_ctlinput1: cmd 0x%x addr: \n", cmd);
|
||||
@ -644,9 +588,9 @@ tpclnp_ctlinput(cmd, siso)
|
||||
ENDDEBUG
|
||||
|
||||
if (cmd < 0 || cmd > PRC_NCMDS)
|
||||
return 0;
|
||||
return;
|
||||
if (siso->siso_family != AF_ISO)
|
||||
return 0;
|
||||
return;
|
||||
switch (cmd) {
|
||||
|
||||
case PRC_QUENCH2:
|
||||
@ -688,7 +632,6 @@ tpclnp_ctlinput(cmd, siso)
|
||||
iso_pcbnotify(&tp_isopcb, siso, (int)inetctlerrmap[cmd], tpiso_abort);
|
||||
break;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
/*
|
||||
* XXX - Variant which is called by clnp_er.c with an isoaddr rather
|
||||
@ -717,7 +660,7 @@ tpclnp_ctlinput1(cmd, isoa)
|
||||
* abort always aborts the TP connection.
|
||||
* reset may or may not, depending on the TP class that's in use.
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tpiso_abort(isop)
|
||||
struct isopcb *isop;
|
||||
{
|
||||
@ -728,18 +671,18 @@ tpiso_abort(isop)
|
||||
ENDDEBUG
|
||||
e.ev_number = ER_TPDU;
|
||||
e.ATTR(ER_TPDU).e_reason = ECONNABORTED;
|
||||
return tp_driver((struct tp_pcb *)isop->isop_socket->so_tpcb, &e);
|
||||
tp_driver((struct tp_pcb *)isop->isop_socket->so_pcb, &e);
|
||||
}
|
||||
|
||||
ProtoHook
|
||||
void
|
||||
tpiso_reset(isop)
|
||||
struct isopcb *isop;
|
||||
{
|
||||
struct tp_event e;
|
||||
|
||||
e.ev_number = T_NETRESET;
|
||||
return tp_driver((struct tp_pcb *)isop->isop_socket->so_tpcb, &e);
|
||||
tp_driver((struct tp_pcb *)isop->isop_socket->so_pcb, &e);
|
||||
|
||||
}
|
||||
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_meas.c 7.4 (Berkeley) 5/6/91
|
||||
* $Id: tp_meas.c,v 1.4 1993/12/18 00:43:40 mycroft Exp $
|
||||
* from: @(#)tp_meas.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_meas.c,v 1.5 1994/05/13 06:09:26 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -66,7 +66,6 @@ SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/cdefs.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
@ -123,4 +122,4 @@ Tpmeas(ref, kind, timev, seq, win, size)
|
||||
tpm->tpm_size = size;
|
||||
}
|
||||
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_meas.h 7.5 (Berkeley) 5/6/91
|
||||
* $Id: tp_meas.h,v 1.3 1993/05/20 05:27:46 cgd Exp $
|
||||
* from: @(#)tp_meas.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_meas.h,v 1.4 1994/05/13 06:09:28 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_MEAS_H_
|
||||
#define _NETISO_TP_MEAS_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -95,6 +92,4 @@ extern struct tp_Meas tp_Meas[];
|
||||
#define TPtime_open_X 0x28 /* xtd format */
|
||||
#define TPtime_close 0x09
|
||||
|
||||
#endif TP_PERF_MEAS
|
||||
|
||||
#endif /* !_NETISO_TP_MEAS_H_ */
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_output.c 7.10 (Berkeley) 6/27/91
|
||||
* $Id: tp_output.c,v 1.4 1993/12/18 00:43:44 mycroft Exp $
|
||||
* from: @(#)tp_output.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_output.c,v 1.5 1994/05/13 06:09:30 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* In here is tp_ctloutput(), the guy called by [sg]etsockopt(),
|
||||
*/
|
||||
|
||||
@ -86,8 +84,6 @@ SOFTWARE.
|
||||
#include <netiso/tp_pcb.h>
|
||||
#include <netiso/tp_trace.h>
|
||||
|
||||
#define USERFLAGSMASK_G 0x0f00643b
|
||||
#define USERFLAGSMASK_S 0x0f000432
|
||||
#define TPDUSIZESHIFT 24
|
||||
#define CLASSHIFT 16
|
||||
|
||||
@ -162,7 +158,7 @@ tp_consistency( tpcb, cmd, param )
|
||||
printf("p_class 0x%x, class_to_use 0x%x\n", param->p_class,
|
||||
class_to_use);
|
||||
ENDDEBUG
|
||||
if( param->p_netservice > TP_MAX_NETSERVICES) {
|
||||
if((param->p_netservice < 0) || (param->p_netservice > TP_MAX_NETSERVICES)){
|
||||
error = EINVAL; goto done;
|
||||
}
|
||||
if( (param->p_class & TP_CLASSES_IMPLEMENTED) == 0 ) {
|
||||
@ -176,18 +172,6 @@ tp_consistency( tpcb, cmd, param )
|
||||
/* bad for any class because negot has to be done a la class 4 */
|
||||
error = EINVAL; goto done;
|
||||
}
|
||||
IFDEBUG(D_SETPARAMS)
|
||||
printf("winsize 0x%x\n", param->p_winsize );
|
||||
ENDDEBUG
|
||||
if( (param->p_winsize < 128 ) ||
|
||||
(param->p_winsize < param->p_tpdusize ) ||
|
||||
(param->p_winsize > ((1+SB_MAX)>>2 /* 1/4 of the max */)) ) {
|
||||
error = EINVAL; goto done;
|
||||
} else {
|
||||
if( tpcb->tp_state == TP_CLOSED )
|
||||
soreserve(tpcb->tp_sock, (u_long)param->p_winsize,
|
||||
(u_long)param->p_winsize);
|
||||
}
|
||||
IFDEBUG(D_SETPARAMS)
|
||||
printf("use_csum 0x%x\n", param->p_use_checksum );
|
||||
printf("xtd_format 0x%x\n", param->p_xtd_format );
|
||||
@ -300,9 +284,8 @@ tp_consistency( tpcb, cmd, param )
|
||||
}
|
||||
|
||||
if ((error==0) && (cmd & TP_FORCE)) {
|
||||
long dusize = ((long)param->p_ptpdusize) << 7;
|
||||
/* Enforce Negotation rules below */
|
||||
if (tpcb->tp_tpdusize > param->p_tpdusize)
|
||||
tpcb->tp_tpdusize = param->p_tpdusize;
|
||||
tpcb->tp_class = param->p_class;
|
||||
if (tpcb->tp_use_checksum || param->p_use_checksum)
|
||||
tpcb->tp_use_checksum = 1;
|
||||
@ -310,8 +293,19 @@ tp_consistency( tpcb, cmd, param )
|
||||
tpcb->tp_xpd_service = 0;
|
||||
if (!tpcb->tp_xtd_format || !param->p_xtd_format)
|
||||
tpcb->tp_xtd_format = 0;
|
||||
if (dusize) {
|
||||
if (tpcb->tp_l_tpdusize > dusize)
|
||||
tpcb->tp_l_tpdusize = dusize;
|
||||
if (tpcb->tp_ptpdusize == 0 ||
|
||||
tpcb->tp_ptpdusize > param->p_ptpdusize)
|
||||
tpcb->tp_ptpdusize = param->p_ptpdusize;
|
||||
} else {
|
||||
if (param->p_tpdusize != 0 &&
|
||||
tpcb->tp_tpdusize > param->p_tpdusize)
|
||||
tpcb->tp_tpdusize = param->p_tpdusize;
|
||||
tpcb->tp_l_tpdusize = 1 << tpcb->tp_tpdusize;
|
||||
}
|
||||
}
|
||||
|
||||
done:
|
||||
|
||||
IFTRACE(D_CONN)
|
||||
@ -362,7 +356,7 @@ done:
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
ProtoHook
|
||||
int
|
||||
tp_ctloutput(cmd, so, level, optname, mp)
|
||||
int cmd, level, optname;
|
||||
struct socket *so;
|
||||
@ -408,8 +402,20 @@ tp_ctloutput(cmd, so, level, optname, mp)
|
||||
else if (tpcb->tp_nlproto->nlp_ctloutput == NULL)
|
||||
error = EOPNOTSUPP;
|
||||
else
|
||||
error = (tpcb->tp_nlproto->nlp_ctloutput)(cmd, optname,
|
||||
tpcb->tp_npcb, *mp);
|
||||
return ((tpcb->tp_nlproto->nlp_ctloutput)(cmd, optname,
|
||||
tpcb->tp_npcb, *mp));
|
||||
goto done;
|
||||
} else if ( level == SOL_SOCKET) {
|
||||
if (optname == SO_RCVBUF && cmd == PRCO_SETOPT) {
|
||||
u_long old_credit = tpcb->tp_maxlcredit;
|
||||
tp_rsyset(tpcb);
|
||||
if (tpcb->tp_rhiwat != so->so_rcv.sb_hiwat &&
|
||||
tpcb->tp_state == TP_OPEN &&
|
||||
(old_credit < tpcb->tp_maxlcredit))
|
||||
tp_emit(AK_TPDU_type, tpcb,
|
||||
tpcb->tp_rcvnxt, 0, MNULL);
|
||||
tpcb->tp_rhiwat = so->so_rcv.sb_hiwat;
|
||||
}
|
||||
goto done;
|
||||
} else if ( level != SOL_TRANSPORT ) {
|
||||
error = EOPNOTSUPP; goto done;
|
||||
@ -439,7 +445,7 @@ tp_ctloutput(cmd, so, level, optname, mp)
|
||||
* the tpcb is gone
|
||||
*/
|
||||
if ((so->so_state & (SS_ISCONNECTED | SS_ISCONFIRMING)) == 0) {
|
||||
if ( so->so_tpcb == (caddr_t)0 ) {
|
||||
if ( so->so_pcb == (caddr_t)0 ) {
|
||||
error = ENOTCONN; goto done;
|
||||
}
|
||||
if ( (tpcb->tp_state == TP_REFWAIT || tpcb->tp_state == TP_CLOSING) &&
|
||||
@ -456,48 +462,46 @@ tp_ctloutput(cmd, so, level, optname, mp)
|
||||
switch (optname) {
|
||||
|
||||
case TPOPT_INTERCEPT:
|
||||
#define INA(t) (((struct inpcb *)(t->tp_npcb))->inp_laddr.s_addr)
|
||||
#define ISOA(t) (((struct isopcb *)(t->tp_npcb))->isop_laddr->siso_addr)
|
||||
|
||||
if ((so->so_state & SS_PRIV) == 0) {
|
||||
error = EPERM;
|
||||
break;
|
||||
} else if (cmd != PRCO_SETOPT || tpcb->tp_state != TP_LISTENING)
|
||||
} else if (cmd != PRCO_SETOPT || tpcb->tp_state != TP_CLOSED ||
|
||||
(tpcb->tp_flags & TPF_GENERAL_ADDR) ||
|
||||
tpcb->tp_next == 0)
|
||||
error = EINVAL;
|
||||
else {
|
||||
register struct tp_pcb *t = 0;
|
||||
struct mbuf *m = m_getclr(M_WAIT, MT_SONAME);
|
||||
struct sockaddr *sa = mtod(m, struct sockaddr *);
|
||||
(*tpcb->tp_nlproto->nlp_getnetaddr)(tpcb->tp_npcb, m, TP_LOCAL);
|
||||
switch (sa->sa_family) {
|
||||
case AF_ISO:
|
||||
if (((struct sockaddr_iso *)sa)->siso_nlen == 0)
|
||||
default: error = EINVAL;
|
||||
break;
|
||||
case AF_INET:
|
||||
if (((struct sockaddr_in *)sa)->sin_addr.s_addr == 0)
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
for (t = tp_intercepts; t; t = t->tp_nextlisten) {
|
||||
if (t->tp_nlproto->nlp_afamily != tpcb->tp_nlproto->nlp_afamily)
|
||||
continue;
|
||||
if ((*t->tp_nlproto->nlp_cmpnetaddr)(t->tp_npcb, sa, TP_LOCAL))
|
||||
error = EADDRINUSE;
|
||||
}
|
||||
m_freem(m);
|
||||
if (error)
|
||||
break;
|
||||
register struct tp_pcb *t;
|
||||
error = EADDRINUSE;
|
||||
for (t = tp_listeners; t; t = t->tp_nextlisten)
|
||||
if ((t->tp_flags & TPF_GENERAL_ADDR) == 0 &&
|
||||
t->tp_domain == tpcb->tp_domain)
|
||||
switch (tpcb->tp_domain) {
|
||||
default:
|
||||
goto done;
|
||||
#ifdef INET
|
||||
case AF_INET:
|
||||
if (INA(t) == INA(tpcb))
|
||||
goto done;
|
||||
continue;
|
||||
#endif
|
||||
#ifdef ISO
|
||||
case AF_ISO:
|
||||
if (bcmp(ISOA(t).isoa_genaddr, ISOA(tpcb).isoa_genaddr,
|
||||
ISOA(t).isoa_len) == 0)
|
||||
goto done;
|
||||
continue;
|
||||
#endif
|
||||
}
|
||||
tpcb->tp_lsuffixlen = 0;
|
||||
tpcb->tp_state = TP_LISTENING;
|
||||
error = 0;
|
||||
remque(tpcb);
|
||||
tpcb->tp_next = tpcb->tp_prev = tpcb;
|
||||
tpcb->tp_nextlisten = tp_listeners;
|
||||
tp_listeners = tpcb;
|
||||
}
|
||||
{
|
||||
register struct tp_pcb **tt;
|
||||
for (tt = &tp_listeners; *tt; tt = &((*tt)->tp_nextlisten))
|
||||
if (*tt == tpcb)
|
||||
break;
|
||||
if (*tt)
|
||||
*tt = tpcb->tp_nextlisten;
|
||||
else
|
||||
{error = EHOSTUNREACH; goto done; }
|
||||
}
|
||||
tpcb->tp_nextlisten = tp_intercepts;
|
||||
tp_intercepts = tpcb;
|
||||
break;
|
||||
|
||||
case TPOPT_MY_TSEL:
|
||||
@ -603,7 +607,7 @@ tp_ctloutput(cmd, so, level, optname, mp)
|
||||
#else
|
||||
error = EOPNOTSUPP;
|
||||
goto done;
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
||||
case TPOPT_CDDATA_CLEAR:
|
||||
if (cmd == PRCO_GETOPT) {
|
||||
@ -649,7 +653,7 @@ tp_ctloutput(cmd, so, level, optname, mp)
|
||||
tptrace(TPPTmisc,"C/D DATA: flags snd.sbcc val_len",
|
||||
tpcb->tp_flags, so->so_snd.sb_cc,val_len,0);
|
||||
ENDTRACE
|
||||
*mp = MNULL; /* prevent sosetopt from freeing it! */
|
||||
*mp = MNULL;
|
||||
if (optname == TPOPT_CFRM_DATA && (so->so_state & SS_ISCONFIRMING))
|
||||
(void) tp_confirm(tpcb);
|
||||
}
|
||||
@ -668,9 +672,9 @@ tp_ctloutput(cmd, so, level, optname, mp)
|
||||
}
|
||||
if( tpcb->tp_perf_on )
|
||||
error = tp_setup_perf(tpcb);
|
||||
#else TP_PERF_MEAS
|
||||
#else /* TP_PERF_MEAS */
|
||||
error = EOPNOTSUPP;
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
break;
|
||||
|
||||
default:
|
||||
@ -686,15 +690,19 @@ done:
|
||||
* sigh: getsockopt looks only at m_len : all output data must
|
||||
* reside in the first mbuf
|
||||
*/
|
||||
if ( error && (*mp) != MNULL )
|
||||
(*mp)->m_len = 0;
|
||||
if( (*mp) != MNULL ) {
|
||||
ASSERT ( m_compress(*mp, mp) <= MLEN );
|
||||
IFDEBUG(D_REQUEST)
|
||||
dump_mbuf(*mp, "tp_ctloutput *mp after compress");
|
||||
ENDDEBUG
|
||||
if (*mp) {
|
||||
if (cmd == PRCO_SETOPT) {
|
||||
m_freem(*mp);
|
||||
*mp = MNULL;
|
||||
} else {
|
||||
ASSERT ( m_compress(*mp, mp) <= MLEN );
|
||||
if (error)
|
||||
(*mp)->m_len = 0;
|
||||
IFDEBUG(D_REQUEST)
|
||||
dump_mbuf(*mp, "tp_ctloutput *mp after compress");
|
||||
ENDDEBUG
|
||||
}
|
||||
}
|
||||
|
||||
splx(s);
|
||||
return error;
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_param.h 7.8 (Berkeley) 6/27/91
|
||||
* $Id: tp_param.h,v 1.3 1993/05/20 05:27:48 cgd Exp $
|
||||
* from: @(#)tp_param.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_param.h,v 1.4 1994/05/13 06:09:32 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_PARAM_H_
|
||||
#define _NETISO_TP_PARAM_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,6 +61,9 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_PARAM_H_
|
||||
#define _NETISO_TP_PARAM_H_
|
||||
|
||||
/******************************************************
|
||||
* compile time parameters that can be changed
|
||||
*****************************************************/
|
||||
@ -89,15 +89,19 @@ extern int N_TPREF;
|
||||
* wraparound in checksumming
|
||||
* (No mtu is likely to be larger than 4K anyway...)
|
||||
*/
|
||||
#define TP_NRETRANS 5 /* was 1; cray uses 6 */
|
||||
#define TP_NRETRANS 12 /* TCP_MAXRXTSHIFT + 1 */
|
||||
#define TP_MAXRXTSHIFT 6 /* factor of 64 */
|
||||
#define TP_MAXPORT 0xefff
|
||||
|
||||
#define TP_RTT_NUM 0x7
|
||||
/* ALPHA: to be used in the context: gain= 1/(2**alpha), or
|
||||
* put another way, gaintimes(x) (x)>>alpha (forgetting the case alpha==0)
|
||||
*/
|
||||
#define TP_RTT_ALPHA 3
|
||||
#define TP_RTV_ALPHA 2
|
||||
#define TP_REXMTVAL(tpcb)\
|
||||
((tp_rttadd + (tpcb)->tp_rtt + ((tpcb)->tp_rtv) << 2) / tp_rttdiv)
|
||||
#define TP_RANGESET(tv, value, min, max) \
|
||||
((tv = value) > (max) ? (tv = max) : (tv < min ? tv = min : tv))
|
||||
|
||||
/*
|
||||
* not sure how to treat data on disconnect
|
||||
@ -194,24 +198,27 @@ extern int N_TPREF;
|
||||
#define TPP_addl_opt 0xc6
|
||||
#define TPP_alt_class 0xc7
|
||||
#define TPP_perf_meas 0xc8 /* local item : perf meas on, svp */
|
||||
#define TPP_ptpdu_size 0xf0 /* preferred TPDU size */
|
||||
#define TPP_inact_time 0xf2 /* inactivity time exchanged */
|
||||
|
||||
|
||||
/******************************************************
|
||||
* Some fundamental data types
|
||||
*****************************************************/
|
||||
#ifndef TRUE
|
||||
#define TRUE 1
|
||||
#endif TRUE
|
||||
#endif /* TRUE */
|
||||
|
||||
#ifndef FALSE
|
||||
#define FALSE 0
|
||||
#endif FALSE
|
||||
#endif /* FALSE */
|
||||
|
||||
#define TP_LOCAL 22
|
||||
#define TP_FOREIGN 33
|
||||
|
||||
#ifndef EOK
|
||||
#define EOK 0
|
||||
#endif EOK
|
||||
#endif /* EOK */
|
||||
|
||||
#define TP_CLASS_0 (1<<0)
|
||||
#define TP_CLASS_1 (1<<1)
|
||||
@ -224,7 +231,7 @@ extern int N_TPREF;
|
||||
|
||||
#ifndef MNULL
|
||||
#define MNULL (struct mbuf *)0
|
||||
#endif MNULL
|
||||
#endif /* MNULL */
|
||||
/* if ../sys/mbuf.h gets MT_types up to 0x40, these will
|
||||
* have to be changed:
|
||||
*/
|
||||
@ -235,16 +242,6 @@ extern int N_TPREF;
|
||||
|
||||
typedef unsigned int SeqNum;
|
||||
typedef unsigned short RefNum;
|
||||
typedef int ProtoHook;
|
||||
|
||||
|
||||
/******************************************************
|
||||
* Some fundamental constants
|
||||
*****************************************************/
|
||||
|
||||
#define TP_MIN_WIN 2048
|
||||
#define TP_MAX_WIN 16384
|
||||
#define TP_MAX_WIN_UNPRIV 8192
|
||||
|
||||
/******************************************************
|
||||
* Macro used all over, for driver
|
||||
@ -327,36 +324,36 @@ bcopy((caddr_t)&(((struct tp_vbp *)(src))->tpv_val),(caddr_t)&(dst),sizeof(type)
|
||||
#if defined(ARGO_DEBUG)&&!defined(LOCAL_CREDIT_EXPAND)
|
||||
#define LOCAL_CREDIT(tpcb) tp_local_credit(tpcb)
|
||||
#else
|
||||
#define LOCAL_CREDIT( tpcb ) {\
|
||||
#define LOCAL_CREDIT(tpcb) { if (tpcb->tp_rsycnt == 0) {\
|
||||
register struct sockbuf *xxsb = &((tpcb)->tp_sock->so_rcv);\
|
||||
register int xxi = ((xxsb)->sb_hiwat-(xxsb)->sb_cc);\
|
||||
register int maxcredit = ((tpcb)->tp_xtd_format?0xffff:0xf);\
|
||||
xxi = (xxi<0) ? 0 : ((xxi)>>(tpcb)->tp_tpdusize);\
|
||||
xxi = MIN(xxi, maxcredit); \
|
||||
register int xxi = sbspace(xxsb);\
|
||||
xxi = (xxi<0) ? 0 : ((xxi) / (tpcb)->tp_l_tpdusize);\
|
||||
xxi = min(xxi, (tpcb)->tp_maxlcredit); \
|
||||
if (!(tpcb->tp_cebit_off)) { \
|
||||
(tpcb)->tp_lcredit = ROUND((tpcb)->tp_win_recv); \
|
||||
if (xxi < (tpcb)->tp_lcredit) { \
|
||||
(tpcb)->tp_lcredit = xxi; \
|
||||
} \
|
||||
} \
|
||||
else { \
|
||||
} else \
|
||||
(tpcb)->tp_lcredit = xxi; \
|
||||
} \
|
||||
}
|
||||
#endif ARGO_DEBUG
|
||||
} }
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
#ifdef KERNEL
|
||||
extern int tp_rttadd, tp_rttdiv;
|
||||
#include <sys/syslog.h>
|
||||
#define printf logpri(LOG_DEBUG),addlog
|
||||
|
||||
#ifndef tp_NSTATES
|
||||
|
||||
#include "tp_states.h"
|
||||
#include "tp_events.h"
|
||||
#include <netiso/tp_states.h>
|
||||
#include <netiso/tp_events.h>
|
||||
#if defined(__STDC__) || defined(__cplusplus)
|
||||
#undef ATTR
|
||||
#define ATTR(X) ev_union.EV_ ## X
|
||||
#endif /* defined(__STDC__) || defined(__cplusplus) */
|
||||
|
||||
#endif tp_NSTATES
|
||||
#endif KERNEL
|
||||
#endif /* tp_NSTATES */
|
||||
#endif /* KERNEL */
|
||||
|
||||
#endif /* !_NETISO_TP_PARAM_H_ */
|
||||
#endif /* _NETISO_TP_PARAM_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_pcb.c 7.11 (Berkeley) 5/6/91
|
||||
* $Id: tp_pcb.c,v 1.3 1993/12/18 00:43:53 mycroft Exp $
|
||||
* from: @(#)tp_pcb.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_pcb.c,v 1.4 1994/05/13 06:09:34 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* This is the initialization and cleanup stuff -
|
||||
* for the tp machine in general as well as for the individual pcbs.
|
||||
* tp_init() is called at system startup. tp_attach() and tp_getref() are
|
||||
@ -72,14 +70,14 @@ SOFTWARE.
|
||||
* tp_soisdisconnecting() and tp_soisdisconnected() are tp-specific
|
||||
* versions of soisconnect*
|
||||
* and are called (obviously) during the closing phase.
|
||||
*
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/domain.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/errno.h>
|
||||
#include <sys/time.h>
|
||||
@ -96,10 +94,6 @@ SOFTWARE.
|
||||
#include <netiso/tp_seq.h>
|
||||
#include <netiso/tp_clnp.h>
|
||||
|
||||
struct tp_param tp_param = {
|
||||
1, /* configured */
|
||||
};
|
||||
|
||||
/* ticks are in units of:
|
||||
* 500 nano-fortnights ;-) or
|
||||
* 500 ms or
|
||||
@ -267,7 +261,7 @@ int in_pcballoc();
|
||||
int tpip_output();
|
||||
int tpip_output_dg();
|
||||
struct inpcb tp_inpcb;
|
||||
#endif INET
|
||||
#endif /* INET */
|
||||
#ifdef ISO
|
||||
int iso_putnetaddr();
|
||||
int iso_getnetaddr();
|
||||
@ -285,7 +279,7 @@ int tpclnp_output();
|
||||
int tpclnp_output_dg();
|
||||
int iso_nlctloutput();
|
||||
struct isopcb tp_isopcb;
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
#ifdef TPCONS
|
||||
int iso_putnetaddr();
|
||||
int iso_getnetaddr();
|
||||
@ -301,7 +295,7 @@ int iso_pcbdetach();
|
||||
int iso_pcballoc();
|
||||
int tpcons_output();
|
||||
struct isopcb tp_isopcb;
|
||||
#endif TPCONS
|
||||
#endif /* TPCONS */
|
||||
|
||||
|
||||
struct nl_protosw nl_protosw[] = {
|
||||
@ -318,7 +312,7 @@ struct nl_protosw nl_protosw[] = {
|
||||
},
|
||||
#else
|
||||
{ 0 },
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
/* IN_CLNS */
|
||||
#ifdef INET
|
||||
{ AF_INET, in_putnetaddr, in_getnetaddr, in_cmpnetaddr,
|
||||
@ -332,7 +326,7 @@ struct nl_protosw nl_protosw[] = {
|
||||
},
|
||||
#else
|
||||
{ 0 },
|
||||
#endif INET
|
||||
#endif /* INET */
|
||||
/* ISO_CONS */
|
||||
#if defined(ISO) && defined(TPCONS)
|
||||
{ AF_ISO, iso_putnetaddr, iso_getnetaddr, iso_cmpnetaddr,
|
||||
@ -346,11 +340,14 @@ struct nl_protosw nl_protosw[] = {
|
||||
},
|
||||
#else
|
||||
{ 0 },
|
||||
#endif ISO_CONS
|
||||
#endif /* ISO_CONS */
|
||||
/* End of protosw marker */
|
||||
{ 0 }
|
||||
};
|
||||
|
||||
u_long tp_sendspace = 1024 * 4;
|
||||
u_long tp_recvspace = 1024 * 4;
|
||||
|
||||
/*
|
||||
* NAME: tp_init()
|
||||
*
|
||||
@ -366,15 +363,14 @@ struct nl_protosw nl_protosw[] = {
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
int
|
||||
void
|
||||
tp_init()
|
||||
{
|
||||
static int init_done=0;
|
||||
void tp_timerinit();
|
||||
|
||||
if (init_done++)
|
||||
return 0;
|
||||
|
||||
return;
|
||||
|
||||
/* FOR INET */
|
||||
tp_inpcb.inp_next = tp_inpcb.inp_prev = &tp_inpcb;
|
||||
@ -385,7 +381,6 @@ tp_init()
|
||||
|
||||
tp_timerinit();
|
||||
bzero((caddr_t)&tp_stat, sizeof(struct tp_stat));
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -458,7 +453,7 @@ tp_soisdisconnected(tpcb)
|
||||
|
||||
soisdisconnecting(so);
|
||||
so->so_state &= ~SS_CANTSENDMORE;
|
||||
IFPERF(sototpcb(so))
|
||||
IFPERF(tpcb)
|
||||
register struct tp_pcb *ttpcb = sototpcb(so);
|
||||
u_int fsufx, lsufx;
|
||||
|
||||
@ -471,13 +466,11 @@ tp_soisdisconnected(tpcb)
|
||||
tpcb->tp_perf_on = 0; /* turn perf off */
|
||||
ENDPERF
|
||||
|
||||
tpcb->tp_refp->tpr_state = REF_FROZEN;
|
||||
tp_recycle_tsuffix( tpcb );
|
||||
tp_etimeout(tpcb->tp_refp, TM_reference, 0,0,0, (int)tpcb->tp_refer_ticks);
|
||||
tpcb->tp_refstate = REF_FROZEN;
|
||||
tp_recycle_tsuffix(tpcb);
|
||||
tp_etimeout(tpcb, TM_reference, (int)tpcb->tp_refer_ticks);
|
||||
}
|
||||
|
||||
int tp_maxrefopen; /* highest reference # of the set of open tp connections */
|
||||
|
||||
/*
|
||||
* NAME: tp_freeref()
|
||||
*
|
||||
@ -497,33 +490,37 @@ int tp_maxrefopen; /* highest reference # of the set of open tp connections */
|
||||
* NOTES: better be called at clock priority !!!!!
|
||||
*/
|
||||
void
|
||||
tp_freeref(r)
|
||||
register struct tp_ref *r;
|
||||
tp_freeref(n)
|
||||
RefNum n;
|
||||
{
|
||||
register struct tp_ref *r = tp_ref + n;
|
||||
register struct tp_pcb *tpcb;
|
||||
|
||||
tpcb = r->tpr_pcb;
|
||||
IFDEBUG(D_TIMER)
|
||||
printf("tp_freeref called for ref %d maxrefopen %d\n",
|
||||
r - tp_ref, tp_maxrefopen);
|
||||
printf("tp_freeref called for ref %d pcb %x maxrefopen %d\n",
|
||||
n, tpcb, tp_refinfo.tpr_maxopen);
|
||||
ENDDEBUG
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTmisc, "tp_freeref ref tp_maxrefopen",
|
||||
r - tp_ref, tp_maxrefopen, 0, 0);
|
||||
tptrace(TPPTmisc, "tp_freeref ref maxrefopen pcb",
|
||||
n, tp_refinfo.tpr_maxopen, tpcb, 0);
|
||||
ENDTRACE
|
||||
r->tpr_state = REF_FREE;
|
||||
if (tpcb == 0)
|
||||
return;
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tp_freeref: CLEARING tpr_pcb 0x%x\n", r->tpr_pcb);
|
||||
printf("tp_freeref: CLEARING tpr_pcb 0x%x\n", tpcb);
|
||||
ENDDEBUG
|
||||
r->tpr_pcb = (struct tp_pcb *)0;
|
||||
tpcb->tp_refstate = REF_FREE;
|
||||
|
||||
r = &tp_ref[tp_maxrefopen];
|
||||
|
||||
while( tp_maxrefopen > 0 ) {
|
||||
if(r->tpr_state )
|
||||
for (r = tp_ref + tp_refinfo.tpr_maxopen; r > tp_ref; r--)
|
||||
if (r->tpr_pcb)
|
||||
break;
|
||||
tp_maxrefopen--;
|
||||
r--;
|
||||
}
|
||||
tp_refinfo.tpr_maxopen = r - tp_ref;
|
||||
tp_refinfo.tpr_numopen--;
|
||||
|
||||
IFDEBUG(D_TIMER)
|
||||
printf("tp_freeref ends w/ maxrefopen %d\n", tp_maxrefopen);
|
||||
printf("tp_freeref ends w/ maxrefopen %d\n", tp_refinfo.tpr_maxopen);
|
||||
ENDDEBUG
|
||||
}
|
||||
|
||||
@ -545,27 +542,72 @@ tp_freeref(r)
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
static RefNum
|
||||
u_long
|
||||
tp_getref(tpcb)
|
||||
register struct tp_pcb *tpcb;
|
||||
{
|
||||
register struct tp_ref *r = tp_ref; /* tp_ref[0] is never used */
|
||||
register int i=1;
|
||||
register struct tp_ref *r, *rlim;
|
||||
register int i;
|
||||
caddr_t obase;
|
||||
unsigned size;
|
||||
|
||||
if (++tp_refinfo.tpr_numopen < tp_refinfo.tpr_size)
|
||||
for (r = tp_refinfo.tpr_base, rlim = r + tp_refinfo.tpr_size;
|
||||
++r < rlim; ) /* tp_ref[0] is never used */
|
||||
if (r->tpr_pcb == 0)
|
||||
goto got_one;
|
||||
/* else have to allocate more space */
|
||||
|
||||
while ((++r)->tpr_state != REF_FREE) {
|
||||
if (++i == N_TPREF)
|
||||
return TP_ENOREF;
|
||||
}
|
||||
r->tpr_state = REF_OPENING;
|
||||
if (tp_maxrefopen < i)
|
||||
tp_maxrefopen = i;
|
||||
obase = (caddr_t)tp_refinfo.tpr_base;
|
||||
size = tp_refinfo.tpr_size * sizeof(struct tp_ref);
|
||||
r = (struct tp_ref *) malloc(size + size, M_PCB, M_NOWAIT);
|
||||
if (r == 0)
|
||||
return (--tp_refinfo.tpr_numopen, TP_ENOREF);
|
||||
tp_refinfo.tpr_base = tp_ref = r;
|
||||
tp_refinfo.tpr_size *= 2;
|
||||
bcopy(obase, (caddr_t)r, size);
|
||||
free(obase, M_PCB);
|
||||
r = (struct tp_ref *)(size + (caddr_t)r);
|
||||
bzero((caddr_t)r, size);
|
||||
|
||||
got_one:
|
||||
r->tpr_pcb = tpcb;
|
||||
tpcb->tp_refp = r;
|
||||
|
||||
return i;
|
||||
tpcb->tp_refstate = REF_OPENING;
|
||||
i = r - tp_refinfo.tpr_base;
|
||||
if (tp_refinfo.tpr_maxopen < i)
|
||||
tp_refinfo.tpr_maxopen = i;
|
||||
return (u_long)i;
|
||||
}
|
||||
|
||||
/*
|
||||
* NAME: tp_set_npcb()
|
||||
*
|
||||
* CALLED FROM:
|
||||
* tp_attach(), tp_route_to()
|
||||
*
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* given a tpcb, allocate an appropriate lower-lever npcb, freeing
|
||||
* any old ones that might need re-assigning.
|
||||
*/
|
||||
tp_set_npcb(tpcb)
|
||||
register struct tp_pcb *tpcb;
|
||||
{
|
||||
register struct socket *so = tpcb->tp_sock;
|
||||
int error;
|
||||
|
||||
if (tpcb->tp_nlproto && tpcb->tp_npcb) {
|
||||
short so_state = so->so_state;
|
||||
so->so_state &= ~SS_NOFDREF;
|
||||
tpcb->tp_nlproto->nlp_pcbdetach(tpcb->tp_npcb);
|
||||
so->so_state = so_state;
|
||||
}
|
||||
tpcb->tp_nlproto = &nl_protosw[tpcb->tp_netservice];
|
||||
/* xx_pcballoc sets so_pcb */
|
||||
error = tpcb->tp_nlproto->nlp_pcballoc(so, tpcb->tp_nlproto->nlp_pcblist);
|
||||
tpcb->tp_npcb = so->so_pcb;
|
||||
so->so_pcb = (caddr_t)tpcb;
|
||||
return (error);
|
||||
}
|
||||
/*
|
||||
* NAME: tp_attach()
|
||||
*
|
||||
@ -591,13 +633,14 @@ tp_getref(tpcb)
|
||||
*
|
||||
* NOTES:
|
||||
*/
|
||||
tp_attach(so, dom)
|
||||
struct socket *so;
|
||||
int dom;
|
||||
tp_attach(so, protocol)
|
||||
struct socket *so;
|
||||
int protocol;
|
||||
{
|
||||
register struct tp_pcb *tpcb;
|
||||
int error;
|
||||
int protocol = so->so_proto->pr_protocol;
|
||||
int error = 0;
|
||||
int dom = so->so_proto->pr_domain->dom_family;
|
||||
u_long lref;
|
||||
extern struct tp_conn_param tp_conn_param[];
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
@ -606,16 +649,13 @@ tp_attach(so, dom)
|
||||
IFTRACE(D_CONN)
|
||||
tptrace(TPPTmisc, "tp_attach:dom so", dom, so, 0, 0);
|
||||
ENDTRACE
|
||||
if ( ! tp_param.tpp_configed ) {
|
||||
error = ENOPROTOOPT; /* protocol not available */
|
||||
goto bad2;
|
||||
}
|
||||
|
||||
if (so->so_pcb != NULL) {
|
||||
return EISCONN; /* socket already part of a connection*/
|
||||
}
|
||||
|
||||
error = soreserve(so, TP_SOCKBUFSIZE, TP_SOCKBUFSIZE);
|
||||
if (so->so_snd.sb_hiwat == 0 || so->so_rcv.sb_hiwat == 0)
|
||||
error = soreserve(so, tp_sendspace, tp_recvspace);
|
||||
/* later an ioctl will allow reallocation IF still in closed state */
|
||||
|
||||
if (error)
|
||||
@ -628,13 +668,16 @@ tp_attach(so, dom)
|
||||
}
|
||||
bzero( (caddr_t)tpcb, sizeof (struct tp_pcb) );
|
||||
|
||||
if ( ((tpcb->tp_lref = tp_getref(tpcb)) & TP_ENOREF) != 0 ) {
|
||||
if ( ((lref = tp_getref(tpcb)) & TP_ENOREF) != 0 ) {
|
||||
error = ETOOMANYREFS;
|
||||
goto bad3;
|
||||
}
|
||||
tpcb->tp_lref = lref;
|
||||
tpcb->tp_sock = so;
|
||||
tpcb->tp_domain = dom;
|
||||
if (protocol<ISOPROTO_TP4) {
|
||||
tpcb->tp_rhiwat = so->so_rcv.sb_hiwat;
|
||||
/* tpcb->tp_proto = protocol; someday maybe? */
|
||||
if (protocol && protocol<ISOPROTO_TP4) {
|
||||
tpcb->tp_netservice = ISO_CONS;
|
||||
tpcb->tp_snduna = (SeqNum) -1;/* kludge so the pseudo-ack from the CR/CC
|
||||
* will generate correct fake-ack values
|
||||
@ -645,9 +688,9 @@ tp_attach(so, dom)
|
||||
}
|
||||
tpcb->_tp_param = tp_conn_param[tpcb->tp_netservice];
|
||||
|
||||
tpcb->tp_cong_win = 1;
|
||||
tpcb->tp_state = TP_CLOSED;
|
||||
tpcb->tp_vers = TP_VERSION;
|
||||
tpcb->tp_notdetached = 1;
|
||||
|
||||
/* Spec says default is 128 octets,
|
||||
* that is, if the tpdusize argument never appears, use 128.
|
||||
@ -658,46 +701,21 @@ tp_attach(so, dom)
|
||||
* we'll respond w/ this.
|
||||
* Our maximum is 4096. See tp_chksum.c comments.
|
||||
*/
|
||||
tpcb->tp_l_tpdusize = 1 << tpcb->tp_tpdusize;
|
||||
tpcb->tp_cong_win =
|
||||
tpcb->tp_l_tpdusize = 1 << tpcb->tp_tpdusize;
|
||||
|
||||
tpcb->tp_seqmask = TP_NML_FMT_MASK;
|
||||
tpcb->tp_seqbit = TP_NML_FMT_BIT;
|
||||
tpcb->tp_seqhalf = tpcb->tp_seqbit >> 1;
|
||||
tpcb->tp_sndhiwat = (SeqNum) - 1; /* a kludge but it works */
|
||||
tpcb->tp_s_subseq = 0;
|
||||
|
||||
/* attach to a network-layer protoswitch */
|
||||
/* new way */
|
||||
tpcb->tp_nlproto = & nl_protosw[tpcb->tp_netservice];
|
||||
ASSERT( tpcb->tp_nlproto->nlp_afamily == tpcb->tp_domain);
|
||||
#ifdef notdef
|
||||
/* OLD WAY */
|
||||
/* TODO: properly, this search would be on the basis of
|
||||
* domain,netservice or just netservice only (if you have
|
||||
* IN_CLNS, ISO_CLNS, and ISO_CONS)
|
||||
*/
|
||||
tpcb->tp_nlproto = nl_protosw;
|
||||
while(tpcb->tp_nlproto->nlp_afamily != tpcb->tp_domain ) {
|
||||
if( tpcb->tp_nlproto->nlp_afamily == 0 ) {
|
||||
error = EAFNOSUPPORT;
|
||||
goto bad4;
|
||||
}
|
||||
tpcb->tp_nlproto ++;
|
||||
}
|
||||
#endif notdef
|
||||
|
||||
/* xx_pcballoc sets so_pcb */
|
||||
if ( error = (tpcb->tp_nlproto->nlp_pcballoc) (
|
||||
so, tpcb->tp_nlproto->nlp_pcblist ) ) {
|
||||
if ( error = tp_set_npcb(tpcb))
|
||||
goto bad4;
|
||||
}
|
||||
ASSERT( tpcb->tp_nlproto->nlp_afamily == tpcb->tp_domain);
|
||||
|
||||
/* nothing to do for iso case */
|
||||
if( dom == AF_INET )
|
||||
sotoinpcb(so)->inp_ppcb = (caddr_t) tpcb;
|
||||
/* nothing to do for iso case */
|
||||
|
||||
tpcb->tp_npcb = (caddr_t) so->so_pcb;
|
||||
so->so_tpcb = (caddr_t) tpcb;
|
||||
|
||||
return 0;
|
||||
|
||||
@ -705,7 +723,7 @@ bad4:
|
||||
IFDEBUG(D_CONN)
|
||||
printf("BAD4 in tp_attach, so 0x%x\n", so);
|
||||
ENDDEBUG
|
||||
tp_freeref(tpcb->tp_refp);
|
||||
tp_freeref(tpcb->tp_lref);
|
||||
|
||||
bad3:
|
||||
IFDEBUG(D_CONN)
|
||||
@ -719,7 +737,6 @@ bad2:
|
||||
printf("BAD2 in tp_attach, so 0x%x\n", so);
|
||||
ENDDEBUG
|
||||
so->so_pcb = 0;
|
||||
so->so_tpcb = 0;
|
||||
|
||||
/*bad:*/
|
||||
IFDEBUG(D_CONN)
|
||||
@ -755,7 +772,7 @@ void
|
||||
tp_detach(tpcb)
|
||||
register struct tp_pcb *tpcb;
|
||||
{
|
||||
void tp_freeref();
|
||||
void tp_freeref(), tp_rsyflush();
|
||||
register struct socket *so = tpcb->tp_sock;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
@ -767,33 +784,6 @@ tp_detach(tpcb)
|
||||
tpcb, so, *(u_short *)(tpcb->tp_lsuffix), 0);
|
||||
ENDTRACE
|
||||
|
||||
if (so->so_head) {
|
||||
if (!soqremque(so, 0) && !soqremque(so, 1))
|
||||
panic("sofree dq");
|
||||
so->so_head = 0;
|
||||
}
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tp_detach(freeing RTC list snduna 0x%x rcvnxt 0x%x)\n",
|
||||
tpcb->tp_snduna_rtc,
|
||||
tpcb->tp_rcvnxt_rtc);
|
||||
ENDDEBUG
|
||||
|
||||
#define FREE_RTC_LIST(XXX)\
|
||||
{ register struct tp_rtc *xxr = XXX, *xxs; while (xxr) {\
|
||||
xxs = xxr->tprt_next;\
|
||||
m_freem( xxr->tprt_data );\
|
||||
m_free( dtom(xxr) ); xxr = xxs; }\
|
||||
XXX = (struct tp_rtc *)0;\
|
||||
}
|
||||
|
||||
FREE_RTC_LIST( tpcb->tp_snduna_rtc );
|
||||
tpcb->tp_sndhiwat_rtc = (struct tp_rtc *)0;
|
||||
|
||||
FREE_RTC_LIST( tpcb->tp_rcvnxt_rtc );
|
||||
|
||||
#undef FREE_RTC_LIST
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("so_snd at 0x%x so_rcv at 0x%x\n", &so->so_snd, &so->so_rcv);
|
||||
dump_mbuf(so->so_snd.sb_mb, "so_snd at detach ");
|
||||
@ -801,45 +791,60 @@ tp_detach(tpcb)
|
||||
tpcb->tp_nlproto, tpcb->tp_nlproto->nlp_pcbdetach);
|
||||
ENDDEBUG
|
||||
|
||||
if (so->so_snd.sb_cc != 0)
|
||||
sbflush(&so->so_snd);
|
||||
if (tpcb->tp_Xrcv.sb_cc != 0)
|
||||
sbdrop(&tpcb->tp_Xrcv, (int)tpcb->tp_Xrcv.sb_cc);
|
||||
if (tpcb->tp_Xsnd.sb_mb) {
|
||||
printf("Unsent Xdata on detach; would panic");
|
||||
sbflush(&tpcb->tp_Xsnd);
|
||||
}
|
||||
if (tpcb->tp_ucddata)
|
||||
m_freem(tpcb->tp_ucddata);
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("reassembly info cnt %d rsyq 0x%x\n",
|
||||
tpcb->tp_rsycnt, tpcb->tp_rsyq);
|
||||
ENDDEBUG
|
||||
if (tpcb->tp_rsyq)
|
||||
tp_rsyflush(tpcb);
|
||||
|
||||
if (tpcb->tp_next) {
|
||||
remque(tpcb);
|
||||
tpcb->tp_next = tpcb->tp_prev = 0;
|
||||
}
|
||||
tpcb->tp_notdetached = 0;
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("calling (...nlproto->...)(0x%x, so 0x%x)\n",
|
||||
so->so_pcb, so);
|
||||
tpcb->tp_npcb, so);
|
||||
printf("so 0x%x so_head 0x%x, qlen %d q0len %d qlimit %d\n",
|
||||
so, so->so_head,
|
||||
so->so_q0len, so->so_qlen, so->so_qlimit);
|
||||
ENDDEBUG
|
||||
|
||||
|
||||
(tpcb->tp_nlproto->nlp_pcbdetach)(so->so_pcb);
|
||||
/* does an sofree(so) */
|
||||
(tpcb->tp_nlproto->nlp_pcbdetach)(tpcb->tp_npcb);
|
||||
/* does an so->so_pcb = 0; sofree(so) */
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("after xxx_pcbdetach\n");
|
||||
ENDDEBUG
|
||||
|
||||
if( tpcb->tp_refp->tpr_state == REF_OPENING ) {
|
||||
if (tpcb->tp_state == TP_LISTENING) {
|
||||
register struct tp_pcb **tt;
|
||||
for (tt = &tp_listeners; *tt; tt = &((*tt)->tp_nextlisten))
|
||||
if (*tt == tpcb)
|
||||
break;
|
||||
if (*tt)
|
||||
*tt = tpcb->tp_nextlisten;
|
||||
else
|
||||
printf("tp_detach from listen: should panic\n");
|
||||
}
|
||||
if (tpcb->tp_refstate == REF_OPENING ) {
|
||||
/* no connection existed here so no reference timer will be called */
|
||||
IFDEBUG(D_CONN)
|
||||
printf("SETTING ref %d, 0x%x to REF_FREE\n", tpcb->tp_lref,
|
||||
tpcb->tp_refp - &tp_ref[0]);
|
||||
printf("SETTING ref %d to REF_FREE\n", tpcb->tp_lref);
|
||||
ENDDEBUG
|
||||
|
||||
tp_freeref(tpcb->tp_refp);
|
||||
tp_freeref(tpcb->tp_lref);
|
||||
}
|
||||
|
||||
if (tpcb->tp_Xsnd.sb_mb) {
|
||||
printf("Unsent Xdata on detach; would panic");
|
||||
sbflush(&tpcb->tp_Xsnd);
|
||||
}
|
||||
so->so_tpcb = (caddr_t)0;
|
||||
|
||||
#ifdef TP_PERF_MEAS
|
||||
/*
|
||||
* Get rid of the cluster mbuf allocated for performance measurements, if
|
||||
* there is one. Note that tpcb->tp_perf_on says nothing about whether or
|
||||
@ -847,7 +852,6 @@ tp_detach(tpcb)
|
||||
* to one (that is, we need the TP_PERF_MEASs around the following section
|
||||
* of code, not the IFPERFs)
|
||||
*/
|
||||
#ifdef TP_PERF_MEAS
|
||||
if (tpcb->tp_p_mbuf) {
|
||||
register struct mbuf *m = tpcb->tp_p_mbuf;
|
||||
struct mbuf *n;
|
||||
@ -861,10 +865,127 @@ tp_detach(tpcb)
|
||||
tpcb->tp_p_meas = 0;
|
||||
tpcb->tp_p_mbuf = 0;
|
||||
}
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf( "end of detach, NOT single, tpcb 0x%x\n", tpcb);
|
||||
ENDDEBUG
|
||||
/* free((caddr_t)tpcb, M_PCB); WHere to put this ? */
|
||||
}
|
||||
|
||||
struct que {
|
||||
struct tp_pcb *next;
|
||||
struct tp_pcb *prev;
|
||||
} tp_bound_pcbs =
|
||||
{(struct tp_pcb *)&tp_bound_pcbs, (struct tp_pcb *)&tp_bound_pcbs};
|
||||
|
||||
u_short tp_unique;
|
||||
|
||||
tp_tselinuse(tlen, tsel, siso, reuseaddr)
|
||||
caddr_t tsel;
|
||||
register struct sockaddr_iso *siso;
|
||||
{
|
||||
struct tp_pcb *b = tp_bound_pcbs.next, *l = tp_listeners;
|
||||
register struct tp_pcb *t;
|
||||
|
||||
for (;;) {
|
||||
if (b != (struct tp_pcb *)&tp_bound_pcbs) {
|
||||
t = b; b = t->tp_next;
|
||||
} else if (l) {
|
||||
t = l; l = t->tp_nextlisten;
|
||||
} else
|
||||
break;
|
||||
if (tlen == t->tp_lsuffixlen && bcmp(tsel, t->tp_lsuffix, tlen) == 0) {
|
||||
if (t->tp_flags & TPF_GENERAL_ADDR) {
|
||||
if (siso == 0 || reuseaddr == 0)
|
||||
return 1;
|
||||
} else if (siso) {
|
||||
if (siso->siso_family == t->tp_domain &&
|
||||
t->tp_nlproto->nlp_cmpnetaddr(t->tp_npcb, siso, TP_LOCAL))
|
||||
return 1;
|
||||
} else if (reuseaddr == 0)
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
|
||||
tp_pcbbind(tpcb, nam)
|
||||
register struct tp_pcb *tpcb;
|
||||
register struct mbuf *nam;
|
||||
{
|
||||
register struct sockaddr_iso *siso = 0;
|
||||
int tlen = 0, wrapped = 0;
|
||||
caddr_t tsel;
|
||||
u_short tutil;
|
||||
|
||||
if (tpcb->tp_state != TP_CLOSED)
|
||||
return (EINVAL);
|
||||
if (nam) {
|
||||
siso = mtod(nam, struct sockaddr_iso *);
|
||||
switch (siso->siso_family) {
|
||||
default:
|
||||
return (EAFNOSUPPORT);
|
||||
#ifdef ISO
|
||||
case AF_ISO:
|
||||
tlen = siso->siso_tlen;
|
||||
tsel = TSEL(siso);
|
||||
if (siso->siso_nlen == 0)
|
||||
siso = 0;
|
||||
break;
|
||||
#endif
|
||||
#ifdef INET
|
||||
case AF_INET:
|
||||
tsel = (caddr_t)&tutil;
|
||||
if (tutil = ((struct sockaddr_in *)siso)->sin_port) {
|
||||
tlen = 2;
|
||||
}
|
||||
if (((struct sockaddr_in *)siso)->sin_addr.s_addr == 0)
|
||||
siso = 0;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
if (tpcb->tp_lsuffixlen == 0) {
|
||||
if (tlen) {
|
||||
if (tp_tselinuse(tlen, tsel, siso,
|
||||
tpcb->tp_sock->so_options & SO_REUSEADDR))
|
||||
return (EINVAL);
|
||||
} else {
|
||||
for (tsel = (caddr_t)&tutil, tlen = 2;;){
|
||||
if (tp_unique++ < ISO_PORT_RESERVED ||
|
||||
tp_unique > ISO_PORT_USERRESERVED) {
|
||||
if (wrapped++)
|
||||
return ESRCH;
|
||||
tp_unique = ISO_PORT_RESERVED;
|
||||
}
|
||||
tutil = htons(tp_unique);
|
||||
if (tp_tselinuse(tlen, tsel, siso, 0) == 0)
|
||||
break;
|
||||
}
|
||||
if (siso) switch (siso->siso_family) {
|
||||
#ifdef ISO
|
||||
case AF_ISO:
|
||||
bcopy(tsel, TSEL(siso), tlen);
|
||||
siso->siso_tlen = tlen;
|
||||
break;
|
||||
#endif
|
||||
#ifdef INET
|
||||
case AF_INET:
|
||||
((struct sockaddr_in *)siso)->sin_port = tutil;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
bcopy(tsel, tpcb->tp_lsuffix, (tpcb->tp_lsuffixlen = tlen));
|
||||
insque(tpcb, &tp_bound_pcbs);
|
||||
} else {
|
||||
if (tlen || siso == 0)
|
||||
return (EINVAL);
|
||||
}
|
||||
if (siso == 0) {
|
||||
tpcb->tp_flags |= TPF_GENERAL_ADDR;
|
||||
return (0);
|
||||
}
|
||||
return tpcb->tp_nlproto->nlp_pcbbind(tpcb->tp_npcb, nam);
|
||||
}
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_pcb.h 7.9 (Berkeley) 5/6/91
|
||||
* $Id: tp_pcb.h,v 1.3 1993/05/20 05:27:51 cgd Exp $
|
||||
* from: @(#)tp_pcb.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_pcb.h,v 1.4 1994/05/13 06:09:37 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_PCB_H_
|
||||
#define _NETISO_TP_PCB_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,18 +61,19 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* This file defines the transport protocol control block (tpcb).
|
||||
* and a bunch of #define values that are used in the tpcb.
|
||||
*/
|
||||
|
||||
#include "../netiso/tp_param.h"
|
||||
#include "../netiso/tp_timer.h"
|
||||
#include "../netiso/tp_user.h"
|
||||
#ifndef _NETISO_TP_PCB_H_
|
||||
#define _NETISO_TP_PCB_H_
|
||||
|
||||
#include <netiso/tp_param.h>
|
||||
#include <netiso/tp_timer.h>
|
||||
#include <netiso/tp_user.h>
|
||||
#ifndef sblock
|
||||
#include "socketvar.h"
|
||||
#endif sblock
|
||||
#include <sys/socketvar.h>
|
||||
#endif /* sblock */
|
||||
|
||||
/* NOTE: the code depends on REF_CLOSED > REF_OPEN > the rest, and
|
||||
* on REF_FREE being zero
|
||||
@ -106,31 +104,18 @@ SOFTWARE.
|
||||
#define REF_OPENING 1 /* in use (has a pcb) but no timers */
|
||||
#define REF_FREE 0 /* free to reallocate */
|
||||
|
||||
#define N_CTIMERS 4
|
||||
#define N_ETIMERS 2
|
||||
#define TM_NTIMERS 6
|
||||
|
||||
struct tp_ref {
|
||||
u_char tpr_state; /* values REF_FROZEN, etc. above */
|
||||
struct Ccallout tpr_callout[N_CTIMERS]; /* C timers */
|
||||
struct Ecallout tpr_calltodo; /* list of active E timers */
|
||||
struct tp_pcb *tpr_pcb; /* back ptr to PCB */
|
||||
};
|
||||
|
||||
struct tp_param {
|
||||
/* PER system stuff (one static structure instead of a bunch of names) */
|
||||
unsigned tpp_configed:1; /* Has TP been initialized? */
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* retransmission control and performance measurement
|
||||
*/
|
||||
struct tp_rtc {
|
||||
struct tp_rtc *tprt_next; /* ptr to next rtc structure in the list */
|
||||
SeqNum tprt_seq; /* seq # of this TPDU */
|
||||
int tprt_eot; /* Will this TPDU have the eot bit set? */
|
||||
int tprt_octets;/* # octets in this TPDU */
|
||||
struct mbuf *tprt_data; /* ptr to the octets of data */
|
||||
/* PER system stuff (one static structure instead of a bunch of names) */
|
||||
struct tp_refinfo {
|
||||
struct tp_ref *tpr_base;
|
||||
int tpr_size;
|
||||
int tpr_maxopen;
|
||||
int tpr_numopen;
|
||||
};
|
||||
|
||||
struct nl_protosw {
|
||||
@ -158,12 +143,12 @@ struct tp_pcb {
|
||||
struct tp_pcb *tp_next;
|
||||
struct tp_pcb *tp_prev;
|
||||
struct tp_pcb *tp_nextlisten; /* chain all listeners */
|
||||
struct socket *tp_sock; /* back ptr */
|
||||
u_short tp_state; /* state of fsm */
|
||||
short tp_retrans; /* # times can still retrans */
|
||||
struct tp_ref *tp_refp; /* rest of pcb */
|
||||
caddr_t tp_npcb; /* to lower layer pcb */
|
||||
struct nl_protosw *tp_nlproto; /* lower-layer dependent routines */
|
||||
struct socket *tp_sock; /* back ptr */
|
||||
struct rtentry **tp_routep; /* obtain mtu; inside npcb */
|
||||
|
||||
|
||||
RefNum tp_lref; /* local reference */
|
||||
@ -173,38 +158,37 @@ struct tp_pcb {
|
||||
u_int tp_seqbit; /* bit for seq number wraparound */
|
||||
u_int tp_seqhalf; /* half the seq space */
|
||||
|
||||
/* credit & sequencing info for SENDING */
|
||||
u_short tp_fcredit; /* current remote credit in # packets */
|
||||
|
||||
u_short tp_cong_win; /* congestion window : set to 1 on
|
||||
* source quench
|
||||
* Minimizes the amount of retrans-
|
||||
* missions (independently of the
|
||||
* retrans strategy). Increased
|
||||
* by one for each good ack received.
|
||||
* Minimizes the amount sent in a
|
||||
* regular tp_send() also.
|
||||
*/
|
||||
u_int tp_ackrcvd; /* ACKs received since the send window was updated */
|
||||
SeqNum tp_last_retrans;
|
||||
SeqNum tp_retrans_hiwat;
|
||||
SeqNum tp_snduna; /* seq # of lowest unacked DT */
|
||||
struct tp_rtc *tp_snduna_rtc; /* lowest unacked stuff sent so far */
|
||||
SeqNum tp_sndhiwat; /* highest seq # sent so far */
|
||||
|
||||
struct tp_rtc *tp_sndhiwat_rtc; /* last stuff sent so far */
|
||||
int tp_Nwindow; /* for perf. measurement */
|
||||
struct mbuf *tp_ucddata; /* user connect/disconnect data */
|
||||
|
||||
/* credit & sequencing info for SENDING */
|
||||
u_short tp_fcredit; /* current remote credit in # packets */
|
||||
u_short tp_maxfcredit; /* max remote credit in # packets */
|
||||
u_short tp_dupacks; /* intuit packet loss before rxt timo */
|
||||
u_long tp_cong_win; /* congestion window in bytes.
|
||||
* see profuse comments in TCP code
|
||||
*/
|
||||
u_long tp_ssthresh; /* cong_win threshold for slow start
|
||||
* exponential to linear switch
|
||||
*/
|
||||
SeqNum tp_snduna; /* seq # of lowest unacked DT */
|
||||
SeqNum tp_sndnew; /* seq # of lowest unsent DT */
|
||||
SeqNum tp_sndnum; /* next seq # to be assigned */
|
||||
SeqNum tp_sndnxt; /* what to do next; poss. rxt */
|
||||
struct mbuf *tp_sndnxt_m; /* packet corres. to sndnxt*/
|
||||
int tp_Nwindow; /* for perf. measurement */
|
||||
|
||||
/* credit & sequencing info for RECEIVING */
|
||||
SeqNum tp_rcvnxt; /* next DT seq # expect to recv */
|
||||
SeqNum tp_sent_lcdt; /* cdt according to last ack sent */
|
||||
SeqNum tp_sent_uwe; /* uwe according to last ack sent */
|
||||
SeqNum tp_sent_rcvnxt; /* rcvnxt according to last ack sent
|
||||
* needed for perf measurements only
|
||||
*/
|
||||
u_short tp_lcredit; /* current local credit in # packets */
|
||||
SeqNum tp_rcvnxt; /* next DT seq # expect to recv */
|
||||
struct tp_rtc *tp_rcvnxt_rtc; /* unacked stuff recvd out of order */
|
||||
u_short tp_maxlcredit; /* needed for reassembly queue */
|
||||
struct mbuf **tp_rsyq; /* unacked stuff recvd out of order */
|
||||
int tp_rsycnt; /* number of packets "" "" "" "" */
|
||||
u_long tp_rhiwat; /* remember original RCVBUF size */
|
||||
|
||||
/* receiver congestion state stuff ... */
|
||||
u_int tp_win_recv;
|
||||
@ -246,45 +230,47 @@ struct tp_pcb {
|
||||
#define tp_dont_change_params _tp_param.p_dont_change_params
|
||||
#define tp_netservice _tp_param.p_netservice
|
||||
#define tp_version _tp_param.p_version
|
||||
#define tp_ptpdusize _tp_param.p_ptpdusize
|
||||
|
||||
int tp_l_tpdusize;
|
||||
int tp_l_tpdusize;
|
||||
/* whereas tp_tpdusize is log2(the negotiated max size)
|
||||
* l_tpdusize is the size we'll use when sending, in # chars
|
||||
*/
|
||||
|
||||
struct timeval tp_rtv; /* max round-trip time variance */
|
||||
struct timeval tp_rtt; /* smoothed round-trip time */
|
||||
struct timeval tp_rttemit[ TP_RTT_NUM + 1 ];
|
||||
/* times that the last TP_RTT_NUM DT_TPDUs were emitted */
|
||||
int tp_rtv; /* max round-trip time variance */
|
||||
int tp_rtt; /* smoothed round-trip time */
|
||||
SeqNum tp_rttseq; /* packet being timed */
|
||||
int tp_rttemit; /* when emitted, in ticks */
|
||||
int tp_idle; /* last activity, in ticks */
|
||||
short tp_rxtcur; /* current retransmit value */
|
||||
short tp_rxtshift; /* log(2) of rexmt exp. backoff */
|
||||
u_char tp_cebit_off; /* real DEC bit algorithms not in use */
|
||||
u_char tp_oktonagle; /* Last unsent pckt may be append to */
|
||||
u_char tp_flags; /* values: */
|
||||
#define TPF_NLQOS_PDN TPFLAG_NLQOS_PDN
|
||||
#define TPF_PEER_ON_SAMENET TPFLAG_PEER_ON_SAMENET
|
||||
#define TPF_GENERAL_ADDR TPFLAG_GENERAL_ADDR
|
||||
#define TPF_DELACK 0x8
|
||||
#define TPF_ACKNOW 0x10
|
||||
|
||||
#define PEER_IS_LOCAL(t) (((t)->tp_flags & TPF_PEER_ON_SAME_NET) != 0)
|
||||
#define USES_PDN(t) (((t)->tp_flags & TPF_NLQOS_PDN) != 0)
|
||||
|
||||
|
||||
unsigned
|
||||
tp_sendfcc:1, /* shall next ack include FCC parameter? */
|
||||
tp_trace:1, /* is this pcb being traced? (not used yet) */
|
||||
tp_perf_on:1, /* 0/1 -> performance measuring on */
|
||||
tp_reneged:1, /* have we reneged on cdt since last ack? */
|
||||
tp_decbit:3, /* dec bit was set, we're in reneg mode */
|
||||
tp_cebit_off:1, /* the real DEC bit algorithms not in use */
|
||||
tp_flags:8, /* values: */
|
||||
#define TPF_CONN_DATA_OUT TPFLAG_CONN_DATA_OUT
|
||||
#define TPF_CONN_DATA_IN TPFLAG_CONN_DATA_IN
|
||||
#define TPF_DISC_DATA_IN TPFLAG_DISC_DATA_IN
|
||||
#define TPF_DISC_DATA_OUT TPFLAG_DISC_DATA_OUT
|
||||
#define TPF_XPD_PRESENT TPFLAG_XPD_PRESENT
|
||||
#define TPF_NLQOS_PDN TPFLAG_NLQOS_PDN
|
||||
#define TPF_PEER_ON_SAMENET TPFLAG_PEER_ON_SAMENET
|
||||
|
||||
#define PEER_IS_LOCAL(t) \
|
||||
(((t)->tp_flags & TPF_PEER_ON_SAME_NET)==TPF_PEER_ON_SAME_NET)
|
||||
#define USES_PDN(t) \
|
||||
(((t)->tp_flags & TPF_NLQOS_PDN)==TPF_NLQOS_PDN)
|
||||
|
||||
tp_unused:16;
|
||||
|
||||
tp_notdetached:1; /* Call tp_detach before freeing XXXXXXX */
|
||||
|
||||
#ifdef TP_PERF_MEAS
|
||||
/* performance stats - see tp_stat.h */
|
||||
struct tp_pmeas *tp_p_meas;
|
||||
struct mbuf *tp_p_mbuf;
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
||||
/* addressing */
|
||||
u_short tp_domain; /* domain (INET, ISO) */
|
||||
/* for compatibility with the *old* way and with INET, be sure that
|
||||
@ -298,8 +284,12 @@ struct tp_pcb {
|
||||
#define SHORT_LSUFXP(tpcb) ((short *)((tpcb)->tp_lsuffix))
|
||||
#define SHORT_FSUFXP(tpcb) ((short *)((tpcb)->tp_fsuffix))
|
||||
|
||||
u_char tp_vers; /* protocol version */
|
||||
u_char tp_peer_acktime; /* used to compute DT retrans time */
|
||||
/* Timer stuff */
|
||||
u_char tp_vers; /* protocol version */
|
||||
u_char tp_peer_acktime; /* used for DT retrans time */
|
||||
u_char tp_refstate; /* values REF_FROZEN, etc. above */
|
||||
struct tp_pcb *tp_fasttimeo; /* limit pcbs to examine */
|
||||
u_int tp_timer[TM_NTIMERS]; /* C timers */
|
||||
|
||||
struct sockbuf tp_Xsnd; /* for expedited data */
|
||||
/* struct sockbuf tp_Xrcv; /* for expedited data */
|
||||
@ -323,7 +313,7 @@ u_int tp_start_win;
|
||||
#define CONG_INIT_SAMPLE(pcb) \
|
||||
pcb->tp_cong_sample.cs_received = \
|
||||
pcb->tp_cong_sample.cs_ce_set = 0; \
|
||||
pcb->tp_cong_sample.cs_size = MAX(pcb->tp_lcredit, 1) << 1;
|
||||
pcb->tp_cong_sample.cs_size = max(pcb->tp_lcredit, 1) << 1;
|
||||
|
||||
#define CONG_UPDATE_SAMPLE(pcb, ce_bit) \
|
||||
pcb->tp_cong_sample.cs_received++; \
|
||||
@ -334,7 +324,7 @@ u_int tp_start_win;
|
||||
if ((pcb->tp_cong_sample.cs_ce_set << 1) >= \
|
||||
pcb->tp_cong_sample.cs_size ) { \
|
||||
pcb->tp_win_recv -= pcb->tp_win_recv >> 3; /* multiply by .875 */ \
|
||||
pcb->tp_win_recv = MAX(1 << 8, pcb->tp_win_recv); \
|
||||
pcb->tp_win_recv = max(1 << 8, pcb->tp_win_recv); \
|
||||
} \
|
||||
else { \
|
||||
pcb->tp_win_recv += (1 << 8); /* add one to the scaled int */ \
|
||||
@ -343,29 +333,19 @@ u_int tp_start_win;
|
||||
CONG_INIT_SAMPLE(pcb); \
|
||||
}
|
||||
|
||||
#define CONG_ACK(pcb, seq) \
|
||||
{ int newacks = SEQ_SUB(pcb, seq, pcb->tp_snduna); \
|
||||
if (newacks > 0) { \
|
||||
pcb->tp_ackrcvd += newacks; \
|
||||
if (pcb->tp_ackrcvd >= MIN(pcb->tp_fcredit, pcb->tp_cong_win)) { \
|
||||
++pcb->tp_cong_win; \
|
||||
pcb->tp_ackrcvd = 0; \
|
||||
} \
|
||||
} \
|
||||
}
|
||||
|
||||
#ifdef KERNEL
|
||||
extern struct tp_refinfo tp_refinfo;
|
||||
extern struct timeval time;
|
||||
extern struct tp_ref *tp_ref;
|
||||
extern struct tp_ref *tp_ref;
|
||||
extern struct tp_param tp_param;
|
||||
extern struct nl_protosw nl_protosw[];
|
||||
extern struct tp_pcb *tp_listeners;
|
||||
extern struct tp_pcb *tp_intercepts;
|
||||
extern struct tp_pcb *tp_ftimeolist;
|
||||
#endif
|
||||
|
||||
#define sototpcb(so) ((struct tp_pcb *)(so->so_tpcb))
|
||||
#define sototpref(so) ((struct tp_ref *)((so)->so_tpcb->tp_ref))
|
||||
#define sototpcb(so) ((struct tp_pcb *)(so->so_pcb))
|
||||
#define sototpref(so) ((sototpcb(so)->tp_ref))
|
||||
#define tpcbtoso(tp) ((struct socket *)((tp)->tp_sock))
|
||||
#define tpcbtoref(tp) ((struct tp_ref *)((tp)->tp_ref))
|
||||
|
||||
#endif /* !_NETISO_TP_PCB_H_ */
|
||||
#endif /* _NETISO_TP_PCB_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_seq.h 7.5 (Berkeley) 5/6/91
|
||||
* $Id: tp_seq.h,v 1.3 1993/05/20 05:27:52 cgd Exp $
|
||||
* from: @(#)tp_seq.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_seq.h,v 1.4 1994/05/13 06:09:39 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_SEQ_H_
|
||||
#define _NETISO_TP_SEQ_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* These macros perform sequence number arithmetic modulo (2**7 or 2**31).
|
||||
* The relevant fields in the tpcb are:
|
||||
* tp_seqmask : the mask of bits that define the sequence space.
|
||||
@ -74,6 +69,9 @@ SOFTWARE.
|
||||
* Not exactly fast, but at least it's maintainable.
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_SEQ_H_
|
||||
#define _NETISO_TP_SEQ_H_
|
||||
|
||||
#define SEQ(tpcb,x) \
|
||||
((x) & (tpcb)->tp_seqmask)
|
||||
|
||||
@ -119,4 +117,4 @@ SOFTWARE.
|
||||
#define IN_SWINDOW(tpcb, seq, lwe, uwe)\
|
||||
( SEQ_GT(tpcb, seq, lwe) && SEQ_LEQ(tpcb, seq, uwe) )
|
||||
|
||||
#endif /* !_NETISO_TP_SEQ_H_ */
|
||||
#endif /* _NETISO_TP_SEQ_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_stat.h 7.5 (Berkeley) 6/27/91
|
||||
* $Id: tp_stat.h,v 1.3 1993/05/20 05:27:53 cgd Exp $
|
||||
* from: @(#)tp_stat.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_stat.h,v 1.4 1994/05/13 06:09:41 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_STAT_H_
|
||||
#define _NETISO_TP_STAT_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,12 +61,13 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* Here are the data structures in which the global
|
||||
* statistics(counters) are gathered.
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_STAT_H_
|
||||
#define _NETISO_TP_STAT_H_
|
||||
|
||||
struct tp_stat {
|
||||
u_long ts_param_ignored;
|
||||
u_long ts_unused3;
|
||||
@ -144,6 +142,8 @@ struct tp_stat {
|
||||
u_long ts_Cset;
|
||||
u_long ts_Ccan_act;
|
||||
u_long ts_Ccan_inact;
|
||||
u_long ts_Fdelack;
|
||||
u_long ts_Fpruned;
|
||||
|
||||
u_long ts_concat_rcvd;
|
||||
|
||||
@ -174,8 +174,8 @@ struct tp_stat {
|
||||
* 2 --> tp_flags: TPF_PEER_ON_SAMENET | ~TPF_NL_PDN
|
||||
* 3 --> tp_flags: TPF_PEER_ON_SAMENET | TPF_NL_PDN
|
||||
*/
|
||||
struct timeval ts_rtt[NRTT_CATEGORIES];
|
||||
struct timeval ts_rtv[NRTT_CATEGORIES];
|
||||
int ts_rtt[NRTT_CATEGORIES];
|
||||
int ts_rtv[NRTT_CATEGORIES];
|
||||
|
||||
u_long ts_ackreason[_ACK_NUM_REASONS_];
|
||||
/* ACK_DONT 0 / ACK_STRAT_EACH 0x1 / ACK_STRAT_FULLWIN 0x4
|
||||
@ -217,7 +217,7 @@ struct tp_pmeas {
|
||||
* Each window size, we keep the running average of the time
|
||||
* taken by tp_sbsend() for each window size.
|
||||
*/
|
||||
struct timeval tps_sendtime[TP_PM_MAX+1];
|
||||
int tps_sendtime[TP_PM_MAX+1];
|
||||
/*
|
||||
* n_TMsendack: # times ack sent because timer went off
|
||||
* n_ack_cuz_eot: # times ack sent due to EOTSDU on incoming packet
|
||||
@ -274,6 +274,6 @@ int PStat_Junk;
|
||||
#define IFPERF(x) if (0) {
|
||||
#define ENDPERF }
|
||||
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
||||
#endif /* !_NETISO_TP_STAT_H_ */
|
||||
#endif /* _NETISO_TP_STAT_H_ */
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $Id: tp_states.h,v 1.2 1993/05/20 05:27:55 cgd Exp $ */
|
||||
/* $Id: tp_states.h,v 1.3 1994/05/13 06:09:42 mycroft Exp $ */
|
||||
|
||||
#define ST_ERROR 0x0
|
||||
#define TP_CLOSED 0x1
|
||||
|
@ -1,4 +1,4 @@
|
||||
/* $Id: tp_states.init,v 1.2 1993/05/20 05:27:56 cgd Exp $ */
|
||||
/* $Id: tp_states.init,v 1.3 1994/05/13 06:09:43 mycroft Exp $ */
|
||||
|
||||
{0x3,0x0},
|
||||
{0x6,0x1},
|
||||
|
File diff suppressed because it is too large
Load Diff
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_subr2.c 7.10 (Berkeley) 6/27/91
|
||||
* $Id: tp_subr2.c,v 1.4 1993/12/18 00:43:59 mycroft Exp $
|
||||
* from: @(#)tp_subr2.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_subr2.c,v 1.5 1994/05/13 06:09:48 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* Some auxiliary routines:
|
||||
* tp_protocol_error: required by xebec- called when a combo of state,
|
||||
* event, predicate isn't covered for by the transition file.
|
||||
@ -84,13 +82,10 @@ SOFTWARE.
|
||||
#include <sys/domain.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/errno.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/kernel.h>
|
||||
|
||||
#undef MNULL
|
||||
|
||||
#include <net/if.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/tp_param.h>
|
||||
#include <netiso/tp_ip.h>
|
||||
@ -106,6 +101,8 @@ SOFTWARE.
|
||||
#include <netiso/tp_user.h>
|
||||
#include <netiso/cons.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#include <net/if_types.h>
|
||||
#ifdef TRUE
|
||||
#undef FALSE
|
||||
#undef TRUE
|
||||
@ -114,10 +111,7 @@ SOFTWARE.
|
||||
#include <netccitt/pk.h>
|
||||
#include <netccitt/pk_var.h>
|
||||
|
||||
#ifndef TPCONS
|
||||
static void
|
||||
pk_flowcontrol() {}
|
||||
#endif
|
||||
void tp_rsyset();
|
||||
|
||||
/*
|
||||
* NAME: tp_local_credit()
|
||||
@ -146,7 +140,7 @@ tp_local_credit(tpcb)
|
||||
LOCAL_CREDIT(tpcb);
|
||||
IFDEBUG(D_CREDIT)
|
||||
printf("ref 0x%x lcdt 0x%x l_tpdusize 0x%x decbit 0x%x\n",
|
||||
tpcb->tp_refp - tp_ref,
|
||||
tpcb->tp_lref,
|
||||
tpcb->tp_lcredit,
|
||||
tpcb->tp_l_tpdusize,
|
||||
tpcb->tp_decbit,
|
||||
@ -193,10 +187,10 @@ tp_protocol_error(e,tpcb)
|
||||
|
||||
|
||||
/* Not used at the moment */
|
||||
ProtoHook
|
||||
void
|
||||
tp_drain()
|
||||
{
|
||||
return 0;
|
||||
|
||||
}
|
||||
|
||||
|
||||
@ -265,7 +259,8 @@ tp_indicate(ind, tpcb, error)
|
||||
so->so_error = error;
|
||||
|
||||
if (ind == T_DISCONNECT) {
|
||||
so->so_error = ENOTCONN;
|
||||
if (error == 0)
|
||||
so->so_error = ENOTCONN;
|
||||
if ( tpcb->tp_no_disc_indications )
|
||||
return;
|
||||
}
|
||||
@ -302,8 +297,9 @@ struct tp_pcb *tpcb;
|
||||
tpcb->tp_xtd_format ? TP_XTD_FMT_BIT : TP_NML_FMT_BIT ;
|
||||
tpcb->tp_seqhalf = tpcb->tp_seqbit >> 1;
|
||||
tpcb->tp_dt_ticks =
|
||||
MAX(tpcb->tp_dt_ticks, (tpcb->tp_peer_acktime + 2));
|
||||
|
||||
max(tpcb->tp_dt_ticks, (tpcb->tp_peer_acktime + 2));
|
||||
tp_rsyset(tpcb);
|
||||
|
||||
}
|
||||
|
||||
/*
|
||||
@ -372,11 +368,11 @@ tp_quench( tpcb, cmd )
|
||||
ENDDEBUG
|
||||
switch(cmd) {
|
||||
case PRC_QUENCH:
|
||||
tpcb->tp_cong_win = 1;
|
||||
tpcb->tp_cong_win = tpcb->tp_l_tpdusize;
|
||||
IncStat(ts_quench);
|
||||
break;
|
||||
case PRC_QUENCH2:
|
||||
tpcb->tp_cong_win = 1; /* might as well quench source also */
|
||||
tpcb->tp_cong_win = tpcb->tp_l_tpdusize; /* might as well quench source also */
|
||||
tpcb->tp_decbit = TP_DECBIT_CLEAR_COUNT;
|
||||
IncStat(ts_rcvdecbit);
|
||||
break;
|
||||
@ -413,17 +409,24 @@ tp_netcmd( tpcb, cmd )
|
||||
|
||||
case CONN_CLOSE:
|
||||
case CONN_REFUSE:
|
||||
if (isop->isop_refcnt == 1)
|
||||
if (isop->isop_refcnt == 1) {
|
||||
/* This is really superfluous, since it would happen
|
||||
anyway in iso_pcbdetach, although it is a courtesy
|
||||
to free up the x.25 channel before the refwait timer
|
||||
expires. */
|
||||
lcp->lcd_upper = 0;
|
||||
lcp->lcd_upnext = 0;
|
||||
pk_disconnect(lcp);
|
||||
isop->isop_chan = 0;
|
||||
isop->isop_refcnt = 0;
|
||||
isop->isop_chan = 0;
|
||||
isop->isop_refcnt = 0;
|
||||
}
|
||||
break;
|
||||
|
||||
default:
|
||||
printf("tp_netcmd(0x%x, 0x%x) NOT IMPLEMENTED\n", tpcb, cmd);
|
||||
break;
|
||||
}
|
||||
#else TPCONS
|
||||
#else /* TPCONS */
|
||||
printf("tp_netcmd(): X25 NOT CONFIGURED!!\n");
|
||||
#endif
|
||||
}
|
||||
@ -471,31 +474,140 @@ copyQOSparms(src, dst)
|
||||
dst->p_rx_strat = src->p_rx_strat;
|
||||
#undef COPYSIZE
|
||||
}
|
||||
/*
|
||||
* Determine a reasonable value for maxseg size.
|
||||
* If the route is known, check route for mtu.
|
||||
* We also initialize the congestion/slow start
|
||||
* window to be a single segment if the destination isn't local.
|
||||
* While looking at the routing entry, we also initialize other path-dependent
|
||||
* parameters from pre-set or cached values in the routing entry.
|
||||
*/
|
||||
void
|
||||
tp_mss(tpcb, nhdr_size)
|
||||
register struct tp_pcb *tpcb;
|
||||
int nhdr_size;
|
||||
{
|
||||
register struct rtentry *rt;
|
||||
struct ifnet *ifp;
|
||||
register int rtt, mss;
|
||||
u_long bufsize;
|
||||
int i, ssthresh = 0, rt_mss;
|
||||
struct socket *so;
|
||||
|
||||
if (tpcb->tp_ptpdusize)
|
||||
mss = tpcb->tp_ptpdusize << 7;
|
||||
else
|
||||
mss = 1 << tpcb->tp_tpdusize;
|
||||
so = tpcb->tp_sock;
|
||||
if ((rt = *(tpcb->tp_routep)) == 0) {
|
||||
bufsize = so->so_rcv.sb_hiwat;
|
||||
goto punt_route;
|
||||
}
|
||||
ifp = rt->rt_ifp;
|
||||
|
||||
#ifdef RTV_MTU /* if route characteristics exist ... */
|
||||
/*
|
||||
* While we're here, check if there's an initial rtt
|
||||
* or rttvar. Convert from the route-table units
|
||||
* to hz ticks for the smoothed timers and slow-timeout units
|
||||
* for other inital variables.
|
||||
*/
|
||||
if (tpcb->tp_rtt == 0 && (rtt = rt->rt_rmx.rmx_rtt)) {
|
||||
tpcb->tp_rtt = rtt * hz / RTM_RTTUNIT;
|
||||
if (rt->rt_rmx.rmx_rttvar)
|
||||
tpcb->tp_rtv = rt->rt_rmx.rmx_rttvar
|
||||
* hz / RTM_RTTUNIT;
|
||||
else
|
||||
tpcb->tp_rtv = tpcb->tp_rtt;
|
||||
}
|
||||
/*
|
||||
* if there's an mtu associated with the route, use it
|
||||
*/
|
||||
if (rt->rt_rmx.rmx_mtu)
|
||||
rt_mss = rt->rt_rmx.rmx_mtu - nhdr_size;
|
||||
else
|
||||
#endif /* RTV_MTU */
|
||||
rt_mss = (ifp->if_mtu - nhdr_size);
|
||||
if (tpcb->tp_ptpdusize == 0 || /* assume application doesn't care */
|
||||
mss > rt_mss /* network won't support what was asked for */)
|
||||
mss = rt_mss;
|
||||
/* can propose mtu which are multiples of 128 */
|
||||
mss &= ~0x7f;
|
||||
/*
|
||||
* If there's a pipesize, change the socket buffer
|
||||
* to that size.
|
||||
*/
|
||||
#ifdef RTV_SPIPE
|
||||
if ((bufsize = rt->rt_rmx.rmx_sendpipe) > 0) {
|
||||
#endif
|
||||
bufsize = min(bufsize, so->so_snd.sb_hiwat);
|
||||
(void) sbreserve(&so->so_snd, bufsize);
|
||||
}
|
||||
#ifdef RTV_SPIPE
|
||||
if ((bufsize = rt->rt_rmx.rmx_recvpipe) > 0) {
|
||||
#endif
|
||||
bufsize = min(bufsize, so->so_rcv.sb_hiwat);
|
||||
(void) sbreserve(&so->so_rcv, bufsize);
|
||||
} else
|
||||
bufsize = so->so_rcv.sb_hiwat;
|
||||
#ifdef RTV_SSTHRESH
|
||||
/*
|
||||
* There's some sort of gateway or interface
|
||||
* buffer limit on the path. Use this to set
|
||||
* the slow start threshhold, but set the
|
||||
* threshold to no less than 2*mss.
|
||||
*/
|
||||
ssthresh = rt->rt_rmx.rmx_ssthresh;
|
||||
punt_route:
|
||||
/*
|
||||
* The current mss is initialized to the default value.
|
||||
* If we compute a smaller value, reduce the current mss.
|
||||
* If we compute a larger value, return it for use in sending
|
||||
* a max seg size option.
|
||||
* If we received an offer, don't exceed it.
|
||||
* However, do not accept offers under 128 bytes.
|
||||
*/
|
||||
if (tpcb->tp_l_tpdusize)
|
||||
mss = min(mss, tpcb->tp_l_tpdusize);
|
||||
/*
|
||||
* We want a minimum recv window of 4 packets to
|
||||
* signal packet loss by duplicate acks.
|
||||
*/
|
||||
mss = min(mss, bufsize >> 2) & ~0x7f;
|
||||
mss = max(mss, 128); /* sanity */
|
||||
tpcb->tp_cong_win =
|
||||
(rt == 0 || (rt->rt_flags & RTF_GATEWAY)) ? mss : bufsize;
|
||||
tpcb->tp_l_tpdusize = mss;
|
||||
tp_rsyset(tpcb);
|
||||
tpcb->tp_ssthresh = max(2 * mss, ssthresh);
|
||||
/* Calculate log2 of mss */
|
||||
for (i = TP_MIN_TPDUSIZE + 1; i <= TP_MAX_TPDUSIZE; i++)
|
||||
if ((1 << i) > mss)
|
||||
break;
|
||||
i--;
|
||||
tpcb->tp_tpdusize = i;
|
||||
#endif /* RTV_MTU */
|
||||
}
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tp_usrreq on PRU_CONNECT and tp_input on receipt of CR
|
||||
*
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* route directly to x.25 if the address is type 37 - GROT.
|
||||
* furthermore, let TP0 handle only type-37 addresses
|
||||
* -- An mbuf containing the peer's network address.
|
||||
* -- Our control block, which will be modified
|
||||
* -- In the case of cons, a control block for that layer.
|
||||
*
|
||||
* Since this assumes that its address argument is in a mbuf, the
|
||||
* parameter was changed to reflect this assumtion. This also
|
||||
* implies that an mbuf must be allocated when this is
|
||||
* called from tp_input
|
||||
*
|
||||
* RETURNS:
|
||||
* errno value :
|
||||
* EAFNOSUPPORT if can't find an nl_protosw for x.25 (really could panic)
|
||||
* ECONNREFUSED if trying to run TP0 with non-type 37 address
|
||||
* possibly other E* returned from cons_netcmd()
|
||||
* NOTE:
|
||||
* Would like to eliminate as much of this as possible --
|
||||
* only one set of defaults (let the user set the parms according
|
||||
* to parameters provided in the directory service).
|
||||
* Left here for now 'cause we don't yet have a clean way to handle
|
||||
* it on the passive end.
|
||||
*
|
||||
* SIDE EFFECTS:
|
||||
* Determines recommended tpdusize, buffering and intial delays
|
||||
* based on information cached on the route.
|
||||
*/
|
||||
int
|
||||
tp_route_to( m, tpcb, channel)
|
||||
@ -505,8 +617,9 @@ tp_route_to( m, tpcb, channel)
|
||||
{
|
||||
register struct sockaddr_iso *siso; /* NOTE: this may be a sockaddr_in */
|
||||
extern struct tp_conn_param tp_conn_param[];
|
||||
struct pklcd *lcp = (struct pklcd *)channel;
|
||||
int error = 0;
|
||||
int error = 0, save_netservice = tpcb->tp_netservice;
|
||||
register struct rtentry *rt = 0;
|
||||
int nhdr_size, mtu, bufsize;
|
||||
|
||||
siso = mtod(m, struct sockaddr_iso *);
|
||||
IFTRACE(D_CONN)
|
||||
@ -521,115 +634,68 @@ tp_route_to( m, tpcb, channel)
|
||||
printf("m->mlen x%x, m->m_data:\n", m->m_len);
|
||||
dump_buf(mtod(m, caddr_t), m->m_len);
|
||||
ENDDEBUG
|
||||
if (siso->siso_family != tpcb->tp_domain) {
|
||||
error = EAFNOSUPPORT;
|
||||
goto done;
|
||||
}
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tp_route_to calling nlp_pcbconn, netserv %d\n",
|
||||
tpcb->tp_netservice);
|
||||
ENDDEBUG
|
||||
if (channel) {
|
||||
#ifdef TPCONS
|
||||
if (lcp) {
|
||||
struct pklcd *lcp = (struct pklcd *)channel;
|
||||
struct isopcb *isop = (struct isopcb *)lcp->lcd_upnext,
|
||||
*isop_new = (struct isopcb *)tpcb->tp_sock->so_pcb;
|
||||
*isop_new = (struct isopcb *)tpcb->tp_npcb;
|
||||
/* The next 2 lines believe that you haven't
|
||||
set any network level options or done a pcbconnect
|
||||
and XXXXXXX'edly apply to both inpcb's and isopcb's */
|
||||
remque(isop_new);
|
||||
free(isop_new, M_PCB);
|
||||
tpcb->tp_sock->so_pcb = (caddr_t)isop;
|
||||
if (isop->isop_refcnt == 0) {
|
||||
extern struct isopcb tp_isopcb;
|
||||
remque(isop);
|
||||
insque(isop, &tp_isopcb);
|
||||
isop->isop_head = &tp_isopcb;
|
||||
tpcb->tp_npcb = (caddr_t)isop;
|
||||
tpcb->tp_netservice = ISO_CONS;
|
||||
tpcb->tp_nlproto = nl_protosw + ISO_CONS;
|
||||
if (isop->isop_refcnt++ == 0) {
|
||||
iso_putsufx(isop, tpcb->tp_lsuffix, tpcb->tp_lsuffixlen, TP_LOCAL);
|
||||
}
|
||||
/* else there are already connections sharing this */
|
||||
isop->isop_refcnt++;
|
||||
} else
|
||||
isop->isop_socket = tpcb->tp_sock;
|
||||
} else
|
||||
/* there are already connections sharing this */;
|
||||
#endif
|
||||
error = (tpcb->tp_nlproto->nlp_pcbconn)(tpcb->tp_sock->so_pcb, m);
|
||||
if( error )
|
||||
goto done;
|
||||
|
||||
{
|
||||
register int save_netservice = tpcb->tp_netservice;
|
||||
|
||||
switch(tpcb->tp_netservice) {
|
||||
case ISO_COSNS:
|
||||
case ISO_CLNS:
|
||||
/* This is a kludge but seems necessary so the passive end
|
||||
* can get long enough timers. sigh.
|
||||
if( siso->siso_addr.osinet_idi[1] == (u_char)IDI_OSINET )
|
||||
*/
|
||||
#define IDI_OSINET 0x0004 /* bcd of "0004" */
|
||||
if( siso->siso_addr.isoa_genaddr[2] == (char)IDI_OSINET ) {
|
||||
if( tpcb->tp_dont_change_params == 0) {
|
||||
copyQOSparms( &tp_conn_param[ISO_COSNS],
|
||||
&tpcb->_tp_param);
|
||||
}
|
||||
tpcb->tp_flags |= TPF_NLQOS_PDN;
|
||||
}
|
||||
/* drop through to IN_CLNS*/
|
||||
case IN_CLNS:
|
||||
if (iso_localifa(siso))
|
||||
tpcb->tp_flags |= TPF_PEER_ON_SAMENET;
|
||||
if( (tpcb->tp_class & TP_CLASS_4)==0 ) {
|
||||
error = EPROTOTYPE;
|
||||
break;
|
||||
}
|
||||
tpcb->tp_class = TP_CLASS_4; /* IGNORE dont_change_parms */
|
||||
break;
|
||||
|
||||
case ISO_CONS:
|
||||
#ifdef TPCONS
|
||||
tpcb->tp_flags |= TPF_NLQOS_PDN;
|
||||
if( tpcb->tp_dont_change_params == 0 ) {
|
||||
copyQOSparms( &tp_conn_param[ISO_CONS],
|
||||
&tpcb->_tp_param);
|
||||
}
|
||||
/*
|
||||
* for use over x.25 really need a small receive window,
|
||||
* need to start slowly, need small max negotiable tpdu size,
|
||||
* and need to use the congestion window to the max
|
||||
* IGNORES tp_dont_change_params for these!
|
||||
*/
|
||||
if( tpcb->tp_sock->so_snd.sb_hiwat > 512 ) {
|
||||
(void) soreserve(tpcb->tp_sock, 512, 512 );/* GAG */
|
||||
}
|
||||
tpcb->tp_rx_strat = TPRX_USE_CW;
|
||||
|
||||
if( (tpcb->tp_nlproto != &nl_protosw[ISO_CONS]) ) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf(
|
||||
"tp_route_to( CHANGING nlproto old 0x%x new 0x%x)\n",
|
||||
tpcb->tp_nlproto , &nl_protosw[ISO_CONS]);
|
||||
ENDDEBUG
|
||||
tpcb->tp_nlproto = &nl_protosw[ISO_CONS];
|
||||
}
|
||||
/* class 4 doesn't need to open a vc now - may use one already
|
||||
* opened or may open one only when it sends a pkt.
|
||||
*/
|
||||
#else TPCONS
|
||||
error = ECONNREFUSED;
|
||||
#endif TPCONS
|
||||
break;
|
||||
} else {
|
||||
switch (siso->siso_family) {
|
||||
default:
|
||||
error = EPROTOTYPE;
|
||||
error = EAFNOSUPPORT;
|
||||
goto done;
|
||||
#ifdef ISO
|
||||
case AF_ISO:
|
||||
{
|
||||
struct isopcb *isop = (struct isopcb *)tpcb->tp_npcb;
|
||||
int flags = tpcb->tp_sock->so_options & SO_DONTROUTE;
|
||||
tpcb->tp_netservice = ISO_CLNS;
|
||||
if (clnp_route(&siso->siso_addr, &isop->isop_route,
|
||||
flags, (void **)0, (void **)0) == 0) {
|
||||
rt = isop->isop_route.ro_rt;
|
||||
if (rt && rt->rt_flags & RTF_PROTO1)
|
||||
tpcb->tp_netservice = ISO_CONS;
|
||||
}
|
||||
} break;
|
||||
#endif
|
||||
#ifdef INET
|
||||
case AF_INET:
|
||||
tpcb->tp_netservice = IN_CLNS;
|
||||
#endif
|
||||
}
|
||||
|
||||
ASSERT( save_netservice == tpcb->tp_netservice);
|
||||
if (tpcb->tp_nlproto->nlp_afamily != siso->siso_family) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tp_route_to( CHANGING nlproto old 0x%x new 0x%x)\n",
|
||||
save_netservice, tpcb->tp_netservice);
|
||||
ENDDEBUG
|
||||
if (error = tp_set_npcb(tpcb))
|
||||
goto done;
|
||||
}
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tp_route_to calling nlp_pcbconn, netserv %d\n",
|
||||
tpcb->tp_netservice);
|
||||
ENDDEBUG
|
||||
tpcb->tp_nlproto = nl_protosw + tpcb->tp_netservice;
|
||||
error = (tpcb->tp_nlproto->nlp_pcbconn)(tpcb->tp_npcb, m);
|
||||
}
|
||||
if (error) {
|
||||
tp_netcmd( tpcb, CONN_CLOSE);
|
||||
if (error)
|
||||
goto done;
|
||||
}
|
||||
{ /* start with the global rtt, rtv stats */
|
||||
register int i =
|
||||
(int) tpcb->tp_flags & (TPF_PEER_ON_SAMENET | TPF_NLQOS_PDN);
|
||||
|
||||
tpcb->tp_rtt = tp_stat.ts_rtt[i];
|
||||
tpcb->tp_rtv = tp_stat.ts_rtv[i];
|
||||
}
|
||||
nhdr_size = tpcb->tp_nlproto->nlp_mtu(tpcb); /* only gets common info */
|
||||
tp_mss(tpcb, nhdr_size);
|
||||
done:
|
||||
IFDEBUG(D_CONN)
|
||||
printf("tp_route_to returns 0x%x\n", error);
|
||||
@ -641,6 +707,10 @@ done:
|
||||
return error;
|
||||
}
|
||||
|
||||
#ifndef TPCONS
|
||||
static
|
||||
pk_flowcontrol() {}
|
||||
#endif
|
||||
|
||||
/* class zero version */
|
||||
void
|
||||
@ -650,9 +720,9 @@ tp0_stash( tpcb, e )
|
||||
{
|
||||
#ifndef lint
|
||||
#define E e->ATTR(DT_TPDU)
|
||||
#else lint
|
||||
#else /* lint */
|
||||
#define E e->ev_union.EV_DT_TPDU
|
||||
#endif lint
|
||||
#endif /* lint */
|
||||
|
||||
register struct sockbuf *sb = &tpcb->tp_sock->so_rcv;
|
||||
register struct isopcb *isop = (struct isopcb *)tpcb->tp_npcb;
|
||||
@ -746,7 +816,7 @@ tp_setup_perf(tpcb)
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
#endif TP_PERF_MEAS
|
||||
#endif /* TP_PERF_MEAS */
|
||||
|
||||
#ifdef ARGO_DEBUG
|
||||
dump_addr (addr)
|
||||
@ -760,7 +830,7 @@ dump_addr (addr)
|
||||
case AF_ISO:
|
||||
dump_isoaddr((struct sockaddr_iso *)addr);
|
||||
break;
|
||||
#endif ISO
|
||||
#endif /* ISO */
|
||||
default:
|
||||
printf("BAD AF: 0x%x\n", addr->sa_family);
|
||||
break;
|
||||
@ -803,7 +873,4 @@ int len;
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#endif ARGO_DEBUG
|
||||
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_timer.c 7.5 (Berkeley) 5/6/91
|
||||
* $Id: tp_timer.c,v 1.3 1993/12/18 00:44:00 mycroft Exp $
|
||||
* from: @(#)tp_timer.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_timer.c,v 1.4 1994/05/13 06:09:50 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -60,47 +60,28 @@ SOFTWARE.
|
||||
/*
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* Contains all the timer code.
|
||||
* There are two sources of calls to these routines:
|
||||
* the clock, and tp.trans. (ok, and tp_pcb.c calls it at init time)
|
||||
*
|
||||
* Timers come in two flavors - those that generally get
|
||||
* cancelled (tp_ctimeout, tp_cuntimeout)
|
||||
* and those that either usually expire (tp_etimeout,
|
||||
* tp_euntimeout, tp_slowtimo) or may require more than one instance
|
||||
* of the timer active at a time.
|
||||
*
|
||||
* The C timers are stored in the tp_ref structure. Their "going off"
|
||||
* is manifested by a driver event of the TM_xxx form.
|
||||
*
|
||||
* The E timers are handled like the generic kernel callouts.
|
||||
* Their "going off" is manifested by a function call w/ 3 arguments.
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/malloc.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/kernel.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/tp_param.h>
|
||||
#include <netiso/tp_timer.h>
|
||||
#include <netiso/tp_stat.h>
|
||||
#include <netiso/tp_pcb.h>
|
||||
#include <netiso/tp_tpdu.h>
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/tp_trace.h>
|
||||
#include <netiso/tp_seq.h>
|
||||
|
||||
struct Ecallout *TP_callfree;
|
||||
struct Ecallout *TP_callout;
|
||||
struct tp_ref *tp_ref;
|
||||
int N_TPREF = 100;
|
||||
|
||||
extern int tp_maxrefopen; /* highest ref # of an open tp connection */
|
||||
int tp_rttdiv, tp_rttadd, N_TPREF = 127;
|
||||
struct tp_refinfo tp_refinfo;
|
||||
struct tp_pcb *tp_ftimeolist = (struct tp_pcb *)&tp_ftimeolist;
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
@ -112,150 +93,53 @@ extern int tp_maxrefopen; /* highest ref # of an open tp connection */
|
||||
void
|
||||
tp_timerinit()
|
||||
{
|
||||
register struct Ecallout *e;
|
||||
register int s;
|
||||
#define GETME(x, t, n) {s = (n)*sizeof(*x); x = (t) malloc(s, M_PCB, M_NOWAIT);\
|
||||
if (x == 0) panic("tp_timerinit"); bzero((caddr_t)x, s);}
|
||||
/*
|
||||
* Initialize storage
|
||||
*/
|
||||
GETME(TP_callout, struct Ecallout *, 2 * N_TPREF);
|
||||
GETME(tp_ref, struct tp_ref *, 1 + N_TPREF);
|
||||
|
||||
TP_callfree = TP_callout + ((2 * N_TPREF) - 1);
|
||||
for (e = TP_callfree; e > TP_callout; e--)
|
||||
e->c_next = e - 1;
|
||||
|
||||
/* hate to do this but we really don't want zero to be a legit ref */
|
||||
tp_maxrefopen = 1;
|
||||
tp_ref[0].tpr_state = REF_FROZEN; /* white lie -- no ref timer, don't
|
||||
* want this one to be allocated- ever
|
||||
* unless, of course, you make refs and address instead of an
|
||||
* index - then 0 can be allocated
|
||||
*/
|
||||
#undef GETME
|
||||
if (tp_refinfo.tpr_base)
|
||||
return;
|
||||
tp_refinfo.tpr_size = N_TPREF + 1; /* Need to start somewhere */
|
||||
s = sizeof(*tp_ref) * tp_refinfo.tpr_size;
|
||||
if ((tp_ref = (struct tp_ref *) malloc(s, M_PCB, M_NOWAIT)) == 0)
|
||||
panic("tp_timerinit");
|
||||
bzero((caddr_t)tp_ref, (unsigned) s);
|
||||
tp_refinfo.tpr_base = tp_ref;
|
||||
tp_rttdiv = hz / PR_SLOWHZ;
|
||||
tp_rttadd = (2 * tp_rttdiv) - 1;
|
||||
}
|
||||
|
||||
#ifdef TP_DEBUG_TIMERS
|
||||
/********************** e timers *************************/
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tp_slowtimo() every 1/2 second, for each open reference
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* (refp) indicates a reference structure that is in use.
|
||||
* This ref structure may contain active E-type timers.
|
||||
* Update the timers and if any expire, create an event and
|
||||
* call the driver.
|
||||
*/
|
||||
static void
|
||||
tp_Eclock(refp)
|
||||
struct tp_ref *refp; /* the reference structure */
|
||||
{
|
||||
register struct Ecallout *p1; /* to drift through the list of callouts */
|
||||
struct tp_event E; /* event to pass to tp_driver() */
|
||||
int tp_driver(); /* drives the FSM */
|
||||
|
||||
/*
|
||||
* Update real-time timeout queue.
|
||||
* At front of queue are some number of events which are ``due''.
|
||||
* The time to these is <= 0 and if negative represents the
|
||||
* number of ticks which have passed since it was supposed to happen.
|
||||
* The rest of the q elements (times > 0) are events yet to happen,
|
||||
* where the time for each is given as a delta from the previous.
|
||||
* Decrementing just the first of these serves to decrement the time
|
||||
* to all events.
|
||||
*
|
||||
* This version, which calls the driver directly, doesn't pass
|
||||
* along the ticks - may want to add the ticks if there's any use
|
||||
* for them.
|
||||
*/
|
||||
IncStat(ts_Eticks);
|
||||
p1 = refp->tpr_calltodo.c_next;
|
||||
while (p1) {
|
||||
if (--p1->c_time > 0)
|
||||
break;
|
||||
if (p1->c_time == 0)
|
||||
break;
|
||||
p1 = p1->c_next;
|
||||
}
|
||||
|
||||
for (;;) {
|
||||
struct tp_pcb *tpcb;
|
||||
if ((p1 = refp->tpr_calltodo.c_next) == 0 || p1->c_time > 0) {
|
||||
break;
|
||||
}
|
||||
refp->tpr_calltodo.c_next = p1->c_next;
|
||||
p1->c_next = TP_callfree;
|
||||
|
||||
#ifndef lint
|
||||
E.ev_number = p1->c_func;
|
||||
E.ATTR(TM_data_retrans).e_low = (SeqNum) p1->c_arg1;
|
||||
E.ATTR(TM_data_retrans).e_high = (SeqNum) p1->c_arg2;
|
||||
E.ATTR(TM_data_retrans).e_retrans = p1->c_arg3;
|
||||
#endif lint
|
||||
IFDEBUG(D_TIMER)
|
||||
printf("E expired! event 0x%x (0x%x,0x%x), pcb 0x%x ref %d\n",
|
||||
p1->c_func, p1->c_arg1, p1->c_arg2, refp->tpr_pcb,
|
||||
refp-tp_ref);
|
||||
ENDDEBUG
|
||||
|
||||
TP_callfree = p1;
|
||||
IncStat(ts_Eexpired);
|
||||
(void) tp_driver( tpcb = refp->tpr_pcb, &E);
|
||||
if (p1->c_func == TM_reference && tpcb->tp_state == TP_CLOSED)
|
||||
free((caddr_t)tpcb, M_PCB); /* XXX wart; where else to do it? */
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tp.trans all over
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* Set an E type timer. (refp) is the ref structure.
|
||||
* Causes fun(arg1,arg2,arg3) to be called after time t.
|
||||
* Set an E type timer.
|
||||
*/
|
||||
void
|
||||
tp_etimeout(refp, fun, arg1, arg2, arg3, ticks)
|
||||
struct tp_ref *refp;
|
||||
int fun; /* function to be called */
|
||||
u_int arg1, arg2;
|
||||
int arg3;
|
||||
register int ticks;
|
||||
tp_etimeout(tpcb, fun, ticks)
|
||||
register struct tp_pcb *tpcb;
|
||||
int fun; /* function to be called */
|
||||
int ticks;
|
||||
{
|
||||
register struct Ecallout *p1, *p2, *pnew;
|
||||
/* p1 and p2 drift through the list of timeout callout structures,
|
||||
* pnew points to the newly created callout structure
|
||||
*/
|
||||
|
||||
register u_int *callp;
|
||||
IFDEBUG(D_TIMER)
|
||||
printf("etimeout pcb 0x%x state 0x%x\n", refp->tpr_pcb,
|
||||
refp->tpr_pcb->tp_state);
|
||||
printf("etimeout pcb 0x%x state 0x%x\n", tpcb, tpcb->tp_state);
|
||||
ENDDEBUG
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTmisc, "tp_etimeout ref refstate tks Etick", refp-tp_ref,
|
||||
refp->tpr_state, ticks, tp_stat.ts_Eticks);
|
||||
tptrace(TPPTmisc, "tp_etimeout ref refstate tks Etick", tpcb->tp_lref,
|
||||
tpcb->tp_state, ticks, tp_stat.ts_Eticks);
|
||||
ENDTRACE
|
||||
|
||||
if (tpcb == 0)
|
||||
return;
|
||||
IncStat(ts_Eset);
|
||||
if (ticks == 0)
|
||||
ticks = 1;
|
||||
pnew = TP_callfree;
|
||||
if (pnew == (struct Ecallout *)0)
|
||||
panic("tp timeout table overflow");
|
||||
TP_callfree = pnew->c_next;
|
||||
pnew->c_arg1 = arg1;
|
||||
pnew->c_arg2 = arg2;
|
||||
pnew->c_arg3 = arg3;
|
||||
pnew->c_func = fun;
|
||||
for (p1 = &(refp->tpr_calltodo);
|
||||
(p2 = p1->c_next) && p2->c_time < ticks; p1 = p2)
|
||||
if (p2->c_time > 0)
|
||||
ticks -= p2->c_time;
|
||||
p1->c_next = pnew;
|
||||
pnew->c_next = p2;
|
||||
pnew->c_time = ticks;
|
||||
if (p2)
|
||||
p2->c_time -= ticks;
|
||||
callp = tpcb->tp_timer + fun;
|
||||
if (*callp == 0 || *callp > ticks)
|
||||
*callp = ticks;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -265,64 +149,16 @@ tp_etimeout(refp, fun, arg1, arg2, arg3, ticks)
|
||||
* Cancel all occurrences of E-timer function (fun) for reference (refp)
|
||||
*/
|
||||
void
|
||||
tp_euntimeout(refp, fun)
|
||||
struct tp_ref *refp;
|
||||
tp_euntimeout(tpcb, fun)
|
||||
register struct tp_pcb *tpcb;
|
||||
int fun;
|
||||
{
|
||||
register struct Ecallout *p1, *p2; /* ptrs to drift through the list */
|
||||
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTmisc, "tp_euntimeout ref", refp-tp_ref, 0, 0, 0);
|
||||
tptrace(TPPTmisc, "tp_euntimeout ref", tpcb->tp_lref, 0, 0, 0);
|
||||
ENDTRACE
|
||||
|
||||
p1 = &refp->tpr_calltodo;
|
||||
while ( (p2 = p1->c_next) != 0) {
|
||||
if (p2->c_func == fun) {
|
||||
if (p2->c_next && p2->c_time > 0)
|
||||
p2->c_next->c_time += p2->c_time;
|
||||
p1->c_next = p2->c_next;
|
||||
p2->c_next = TP_callfree;
|
||||
TP_callfree = p2;
|
||||
IncStat(ts_Ecan_act);
|
||||
continue;
|
||||
}
|
||||
p1 = p2;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tp.trans, when an incoming ACK causes things to be dropped
|
||||
* from the retransmission queue, and we want their associated
|
||||
* timers to be cancelled.
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* cancel all occurrences of function (fun) where (arg2) < (seq)
|
||||
*/
|
||||
void
|
||||
tp_euntimeout_lss(refp, fun, seq)
|
||||
struct tp_ref *refp;
|
||||
int fun;
|
||||
SeqNum seq;
|
||||
{
|
||||
register struct Ecallout *p1, *p2;
|
||||
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTmisc, "tp_euntimeoutLSS ref", refp-tp_ref, seq, 0, 0);
|
||||
ENDTRACE
|
||||
|
||||
p1 = &refp->tpr_calltodo;
|
||||
while ( (p2 = p1->c_next) != 0) {
|
||||
if ((p2->c_func == fun) && SEQ_LT(refp->tpr_pcb, p2->c_arg2, seq)) {
|
||||
if (p2->c_next && p2->c_time > 0)
|
||||
p2->c_next->c_time += p2->c_time;
|
||||
p1->c_next = p2->c_next;
|
||||
p2->c_next = TP_callfree;
|
||||
TP_callfree = p2;
|
||||
IncStat(ts_Ecan_act);
|
||||
continue;
|
||||
}
|
||||
p1 = p2;
|
||||
}
|
||||
if (tpcb)
|
||||
tpcb->tp_timer[fun] = 0;
|
||||
}
|
||||
|
||||
/**************** c timers **********************
|
||||
@ -332,7 +168,7 @@ tp_euntimeout_lss(refp, fun, seq)
|
||||
* are typically cancelled so it's faster not to
|
||||
* mess with the chains
|
||||
*/
|
||||
|
||||
#endif
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* the clock, every 500 ms
|
||||
@ -340,47 +176,122 @@ tp_euntimeout_lss(refp, fun, seq)
|
||||
* Look for open references with active timers.
|
||||
* If they exist, call the appropriate timer routines to update
|
||||
* the timers and possibly generate events.
|
||||
* (The E timers are done in other procedures; the C timers are
|
||||
* updated here, and events for them are generated here.)
|
||||
*/
|
||||
ProtoHook
|
||||
void
|
||||
tp_slowtimo()
|
||||
{
|
||||
register int r,t;
|
||||
struct Ccallout *cp;
|
||||
struct tp_ref *rp = tp_ref;
|
||||
register u_int *cp;
|
||||
register struct tp_ref *rp;
|
||||
struct tp_pcb *tpcb;
|
||||
struct tp_event E;
|
||||
int s = splnet();
|
||||
int s = splnet(), t;
|
||||
|
||||
/* check only open reference structures */
|
||||
IncStat(ts_Cticks);
|
||||
rp++; /* tp_ref[0] is never used */
|
||||
for( r=1 ; (r <= tp_maxrefopen) ; r++,rp++ ) {
|
||||
if (rp->tpr_state < REF_OPEN)
|
||||
/* tp_ref[0] is never used */
|
||||
for (rp = tp_ref + tp_refinfo.tpr_maxopen; rp > tp_ref; rp--) {
|
||||
if ((tpcb = rp->tpr_pcb) == 0 || tpcb->tp_refstate < REF_OPEN)
|
||||
continue;
|
||||
|
||||
/* check the C-type timers */
|
||||
cp = rp->tpr_callout;
|
||||
for (t=0 ; t < N_CTIMERS; t++,cp++) {
|
||||
if( cp->c_active ) {
|
||||
if( --cp->c_time <= 0 ) {
|
||||
cp->c_active = FALSE;
|
||||
E.ev_number = t;
|
||||
IFDEBUG(D_TIMER)
|
||||
printf("C expired! type 0x%x\n", t);
|
||||
ENDDEBUG
|
||||
IncStat(ts_Cexpired);
|
||||
tp_driver( rp->tpr_pcb, &E);
|
||||
/* check the timers */
|
||||
for (t = 0; t < TM_NTIMERS; t++) {
|
||||
cp = tpcb->tp_timer + t;
|
||||
if (*cp && --(*cp) <= 0 ) {
|
||||
*cp = 0;
|
||||
E.ev_number = t;
|
||||
IFDEBUG(D_TIMER)
|
||||
printf("tp_slowtimo: pcb 0x%x t %d\n",
|
||||
tpcb, t);
|
||||
ENDDEBUG
|
||||
IncStat(ts_Cexpired);
|
||||
tp_driver(tpcb, &E);
|
||||
if (t == TM_reference && tpcb->tp_state == TP_CLOSED) {
|
||||
if (tpcb->tp_notdetached) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf("PRU_DETACH: not detached\n");
|
||||
ENDDEBUG
|
||||
tp_detach(tpcb);
|
||||
}
|
||||
/* XXX wart; where else to do it? */
|
||||
free((caddr_t)tpcb, M_PCB);
|
||||
}
|
||||
}
|
||||
}
|
||||
/* now update the list */
|
||||
tp_Eclock(rp);
|
||||
}
|
||||
splx(s);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* Called From: tp.trans from tp_slowtimo() -- retransmission timer went off.
|
||||
*/
|
||||
tp_data_retrans(tpcb)
|
||||
register struct tp_pcb *tpcb;
|
||||
{
|
||||
int rexmt, win;
|
||||
tpcb->tp_rttemit = 0; /* cancel current round trip time */
|
||||
tpcb->tp_dupacks = 0;
|
||||
tpcb->tp_sndnxt = tpcb->tp_snduna;
|
||||
if (tpcb->tp_fcredit == 0) {
|
||||
/*
|
||||
* We transmitted new data, started timing it and the window
|
||||
* got shrunk under us. This can only happen if all data
|
||||
* that they wanted us to send got acked, so don't
|
||||
* bother shrinking the congestion windows, et. al.
|
||||
* The retransmission timer should have been reset in goodack()
|
||||
*/
|
||||
IFDEBUG(D_ACKRECV)
|
||||
printf("tp_data_retrans: 0 window tpcb 0x%x una 0x%x\n",
|
||||
tpcb, tpcb->tp_snduna);
|
||||
ENDDEBUG
|
||||
tpcb->tp_rxtshift = 0;
|
||||
tpcb->tp_timer[TM_data_retrans] = 0;
|
||||
tpcb->tp_timer[TM_sendack] = tpcb->tp_dt_ticks;
|
||||
return;
|
||||
}
|
||||
rexmt = tpcb->tp_dt_ticks << min(tpcb->tp_rxtshift, TP_MAXRXTSHIFT);
|
||||
win = min(tpcb->tp_fcredit, (tpcb->tp_cong_win / tpcb->tp_l_tpdusize / 2));
|
||||
win = max(win, 2);
|
||||
tpcb->tp_cong_win = tpcb->tp_l_tpdusize; /* slow start again. */
|
||||
tpcb->tp_ssthresh = win * tpcb->tp_l_tpdusize;
|
||||
/* We're losing; our srtt estimate is probably bogus.
|
||||
* Clobber it so we'll take the next rtt measurement as our srtt;
|
||||
* Maintain current rxt times until then.
|
||||
*/
|
||||
if (++tpcb->tp_rxtshift > TP_NRETRANS / 4) {
|
||||
/* tpcb->tp_nlprotosw->nlp_losing(tpcb->tp_npcb) someday */
|
||||
tpcb->tp_rtt = 0;
|
||||
}
|
||||
TP_RANGESET(tpcb->tp_rxtcur, rexmt, tpcb->tp_peer_acktime, 128);
|
||||
tpcb->tp_timer[TM_data_retrans] = tpcb->tp_rxtcur;
|
||||
tp_send(tpcb);
|
||||
}
|
||||
|
||||
void
|
||||
tp_fasttimo()
|
||||
{
|
||||
register struct tp_pcb *t;
|
||||
int s = splnet();
|
||||
struct tp_event E;
|
||||
|
||||
E.ev_number = TM_sendack;
|
||||
while ((t = tp_ftimeolist) != (struct tp_pcb *)&tp_ftimeolist) {
|
||||
if (t == 0) {
|
||||
printf("tp_fasttimeo: should panic");
|
||||
tp_ftimeolist = (struct tp_pcb *)&tp_ftimeolist;
|
||||
} else {
|
||||
if (t->tp_flags & TPF_DELACK) {
|
||||
IncStat(ts_Fdelack);
|
||||
tp_driver(t, &E);
|
||||
t->tp_flags &= ~TPF_DELACK;
|
||||
} else
|
||||
IncStat(ts_Fpruned);
|
||||
tp_ftimeolist = t->tp_fasttimeo;
|
||||
t->tp_fasttimeo = 0;
|
||||
}
|
||||
}
|
||||
splx(s);
|
||||
}
|
||||
|
||||
#ifdef TP_DEBUG_TIMERS
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* tp.trans, tp_emit()
|
||||
@ -388,21 +299,21 @@ tp_slowtimo()
|
||||
* Set a C type timer of type (which) to go off after (ticks) time.
|
||||
*/
|
||||
void
|
||||
tp_ctimeout(refp, which, ticks)
|
||||
register struct tp_ref *refp;
|
||||
tp_ctimeout(tpcb, which, ticks)
|
||||
register struct tp_pcb *tpcb;
|
||||
int which, ticks;
|
||||
{
|
||||
register struct Ccallout *cp = &(refp->tpr_callout[which]);
|
||||
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTmisc, "tp_ctimeout ref which tpcb active",
|
||||
(int)(refp - tp_ref), which, refp->tpr_pcb, cp->c_active);
|
||||
tpcb->tp_lref, which, tpcb, tpcb->tp_timer[which]);
|
||||
ENDTRACE
|
||||
if(cp->c_active)
|
||||
if(tpcb->tp_timer[which])
|
||||
IncStat(ts_Ccan_act);
|
||||
IncStat(ts_Cset);
|
||||
cp->c_time = ticks;
|
||||
cp->c_active = TRUE;
|
||||
if (ticks <= 0)
|
||||
ticks = 1;
|
||||
tpcb->tp_timer[which] = ticks;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -413,25 +324,20 @@ tp_ctimeout(refp, which, ticks)
|
||||
* parameter (ticks) is > the current value of the timer.
|
||||
*/
|
||||
void
|
||||
tp_ctimeout_MIN(refp, which, ticks)
|
||||
register struct tp_ref *refp;
|
||||
tp_ctimeout_MIN(tpcb, which, ticks)
|
||||
register struct tp_pcb *tpcb;
|
||||
int which, ticks;
|
||||
{
|
||||
register struct Ccallout *cp = &(refp->tpr_callout[which]);
|
||||
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTmisc, "tp_ctimeout_MIN ref which tpcb active",
|
||||
(int)(refp - tp_ref), which, refp->tpr_pcb, cp->c_active);
|
||||
tpcb->tp_lref, which, tpcb, tpcb->tp_timer[which]);
|
||||
ENDTRACE
|
||||
if(cp->c_active)
|
||||
IncStat(ts_Ccan_act);
|
||||
IncStat(ts_Cset);
|
||||
if( cp->c_active )
|
||||
cp->c_time = MIN(ticks, cp->c_time);
|
||||
else {
|
||||
cp->c_time = ticks;
|
||||
cp->c_active = TRUE;
|
||||
}
|
||||
if (tpcb->tp_timer[which]) {
|
||||
tpcb->tp_timer[which] = min(ticks, tpcb->tp_timer[which]);
|
||||
IncStat(ts_Ccan_act);
|
||||
} else
|
||||
tpcb->tp_timer[which] = ticks;
|
||||
}
|
||||
|
||||
/*
|
||||
@ -441,26 +347,24 @@ tp_ctimeout_MIN(refp, which, ticks)
|
||||
* Cancel the (which) timer in the ref structure indicated by (refp).
|
||||
*/
|
||||
void
|
||||
tp_cuntimeout(refp, which)
|
||||
tp_cuntimeout(tpcb, which)
|
||||
register struct tp_pcb *tpcb;
|
||||
int which;
|
||||
register struct tp_ref *refp;
|
||||
{
|
||||
register struct Ccallout *cp;
|
||||
|
||||
cp = &(refp->tpr_callout[which]);
|
||||
|
||||
IFDEBUG(D_TIMER)
|
||||
printf("tp_cuntimeout(0x%x, %d) active %d\n", refp, which, cp->c_active);
|
||||
printf("tp_cuntimeout(0x%x, %d) active %d\n",
|
||||
tpcb, which, tpcb->tp_timer[which]);
|
||||
ENDDEBUG
|
||||
|
||||
IFTRACE(D_TIMER)
|
||||
tptrace(TPPTmisc, "tp_cuntimeout ref which, active", refp-tp_ref,
|
||||
which, cp->c_active, 0);
|
||||
which, tpcb->tp_timer[which], 0);
|
||||
ENDTRACE
|
||||
|
||||
if(cp->c_active)
|
||||
if (tpcb->tp_timer[which])
|
||||
IncStat(ts_Ccan_act);
|
||||
else
|
||||
IncStat(ts_Ccan_inact);
|
||||
cp->c_active = FALSE;
|
||||
tpcb->tp_timer[which] = 0;
|
||||
}
|
||||
#endif
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_timer.h 7.4 (Berkeley) 5/6/91
|
||||
* $Id: tp_timer.h,v 1.3 1993/05/20 05:28:01 cgd Exp $
|
||||
* from: @(#)tp_timer.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_timer.h,v 1.4 1994/05/13 06:09:51 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_TIMER_H_
|
||||
#define _NETISO_TP_TIMER_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,25 +61,28 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
* The callout structures used by the tp timers.
|
||||
*/
|
||||
|
||||
/* C timers - one per tpcb, generally cancelled */
|
||||
#ifndef _NETISO_TP_TIMER_H_
|
||||
#define _NETISO_TP_TIMER_H_
|
||||
|
||||
struct Ccallout {
|
||||
int c_time; /* incremental time */
|
||||
int c_active; /* this timer is active? */
|
||||
};
|
||||
#define SET_DELACK(t) {\
|
||||
(t)->tp_flags |= TPF_DELACK; \
|
||||
if ((t)->tp_fasttimeo == 0)\
|
||||
{ (t)->tp_fasttimeo = tp_ftimeolist; tp_ftimeolist = (t); } }
|
||||
|
||||
/* E timers - generally expire or there must be > 1 active per tpcb */
|
||||
struct Ecallout {
|
||||
int c_time; /* incremental time */
|
||||
int c_func; /* function to call */
|
||||
u_int c_arg1; /* argument to routine */
|
||||
u_int c_arg2; /* argument to routine */
|
||||
int c_arg3; /* argument to routine */
|
||||
struct Ecallout *c_next;
|
||||
};
|
||||
#ifdef ARGO_DEBUG
|
||||
#define TP_DEBUG_TIMERS
|
||||
#endif
|
||||
|
||||
#endif /* !_NETISO_TP_TIMER_H_ */
|
||||
#ifndef TP_DEBUG_TIMERS
|
||||
#define tp_ctimeout(tpcb, which, timo) ((tpcb)->tp_timer[which] = (timo))
|
||||
#define tp_cuntimeout(tpcb, which) ((tpcb)->tp_timer[which] = 0)
|
||||
#define tp_etimeout tp_ctimeout
|
||||
#define tp_euntimeout tp_cuntimeout
|
||||
#define tp_ctimeout_MIN(p, w, t) \
|
||||
{ if((p)->tp_timer[w] > (t)) (p)->tp_timer[w] = (t);}
|
||||
#endif /* TP_DEBUG_TIMERS */
|
||||
|
||||
#endif /* _NETISO_TP_TIMER_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_tpdu.h 7.4 (Berkeley) 5/6/91
|
||||
* $Id: tp_tpdu.h,v 1.4 1994/05/05 07:56:39 cgd Exp $
|
||||
* from: @(#)tp_tpdu.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_tpdu.h,v 1.5 1994/05/13 06:09:53 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_TPDU_H_
|
||||
#define _NETISO_TP_TPDU_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,9 +61,29 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
* This ghastly set of macros makes it possible to
|
||||
* refer to tpdu structures without going mad.
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_TPDU_H_
|
||||
#define _NETISO_TP_TPDU_H_
|
||||
|
||||
#ifndef BYTE_ORDER
|
||||
/*
|
||||
* Definitions for byte order,
|
||||
* according to byte significance from low address to high.
|
||||
*/
|
||||
#define LITTLE_ENDIAN 1234 /* least-significant byte first (vax) */
|
||||
#define BIG_ENDIAN 4321 /* most-significant byte first (IBM, net) */
|
||||
#define PDP_ENDIAN 3412 /* LSB first in word, MSW first in long (pdp) */
|
||||
|
||||
#ifdef vax
|
||||
#define BYTE_ORDER LITTLE_ENDIAN
|
||||
#else
|
||||
#define BYTE_ORDER BIG_ENDIAN /* mc68000, tahoe, most others */
|
||||
#endif
|
||||
#endif /* BYTE_ORDER */
|
||||
|
||||
/* This much of a tpdu is the same for all types of tpdus (except
|
||||
* DT tpdus in class 0; their exceptions are handled by the data
|
||||
* structure below
|
||||
@ -272,4 +289,4 @@ struct tpdu {
|
||||
union tpdu_fixed_rest _tpdufr;
|
||||
};
|
||||
|
||||
#endif /* !_NETISO_TP_TPDU_H_ */
|
||||
#endif /* _NETISO_TP_TPDU_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_trace.c 7.4 (Berkeley) 5/6/91
|
||||
* $Id: tp_trace.c,v 1.3 1993/12/18 00:44:02 mycroft Exp $
|
||||
* from: @(#)tp_trace.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_trace.c,v 1.4 1994/05/13 06:09:55 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* The whole protocol trace module.
|
||||
* We keep a circular buffer of trace structures, which are big
|
||||
* unions of different structures we might want to see.
|
||||
@ -76,7 +74,6 @@ SOFTWARE.
|
||||
#include <sys/systm.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/types.h>
|
||||
#include <sys/time.h>
|
||||
|
||||
#include <netiso/tp_param.h>
|
||||
@ -171,4 +168,4 @@ tpTrace(tpcb, event, arg, src, len, arg4, arg5)
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif TPPT
|
||||
#endif /* TPPT */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_trace.h 7.5 (Berkeley) 6/27/91
|
||||
* $Id: tp_trace.h,v 1.3 1993/05/20 05:28:06 cgd Exp $
|
||||
* from: @(#)tp_trace.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_trace.h,v 1.4 1994/05/13 06:09:56 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_TRACE_H_
|
||||
#define _NETISO_TP_TRACE_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,11 +61,13 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* Definitions needed for the protocol trace mechanism.
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_TRACE_H_
|
||||
#define _NETISO_TP_TRACE_H_
|
||||
|
||||
|
||||
#define TPPTsendack 1
|
||||
#define TPPTgotack 2
|
||||
#define TPPTXack 3
|
||||
@ -85,13 +84,13 @@ SOFTWARE.
|
||||
#define TPPTdriver 14
|
||||
#define TPPTtpduout 15
|
||||
|
||||
#include "../netiso/tp_pcb.h"
|
||||
#include <netiso/tp_pcb.h>
|
||||
|
||||
/* this #if is to avoid lint */
|
||||
|
||||
#if defined(TP_TRACEFILE)||!defined(KERNEL)
|
||||
|
||||
#include "../netiso/tp_tpdu.h"
|
||||
#include <netiso/tp_tpdu.h>
|
||||
|
||||
#define TPTRACE_STRLEN 50
|
||||
|
||||
@ -114,7 +113,7 @@ struct tp_Trace {
|
||||
struct inpcb tpt_Inpcb; /* protocol control block */
|
||||
struct tp_ref tpt_Ref; /* ref part of pcb */
|
||||
struct tpdu tpt_Tpdu; /* header*/
|
||||
struct tp_param tpt_Param; /* ?? bytes, make sure < 128??*/
|
||||
struct tp_refinfo tpt_Param; /* ?? bytes, make sure < 128??*/
|
||||
struct tp_timeval tpt_Time;
|
||||
struct {
|
||||
u_int tptm_2;
|
||||
@ -145,7 +144,7 @@ struct tp_Trace {
|
||||
#define tpt_window tpt_stuff.tpt_Time.tptv_window
|
||||
#define tpt_size tpt_stuff.tpt_Time.tptv_size
|
||||
|
||||
#endif defined(TP_TRACEFILE)||!defined(KERNEL)
|
||||
#endif /* defined(TP_TRACEFILE)||!defined(KERNEL) */
|
||||
|
||||
|
||||
#ifdef TPPT
|
||||
@ -173,8 +172,7 @@ int tp_Tracen = 0;
|
||||
*/
|
||||
#define ENDTRACE }
|
||||
|
||||
|
||||
#else TPPT
|
||||
#else /* TPPT */
|
||||
|
||||
/***********************************************
|
||||
* NO TPPT TRACE STUFF
|
||||
@ -187,6 +185,6 @@ int tp_Tracen = 0;
|
||||
#define IFTRACE(ascii) if (0) {
|
||||
#define ENDTRACE }
|
||||
|
||||
#endif TPPT
|
||||
#endif /* TPPT */
|
||||
|
||||
#endif /* !_NETISO_TP_TRACE_H_ */
|
||||
#endif /* _NETISO_TP_TRACE_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,13 +30,10 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_user.h 7.10 (Berkeley) 5/6/91
|
||||
* $Id: tp_user.h,v 1.3 1993/05/20 05:28:08 cgd Exp $
|
||||
* from: @(#)tp_user.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_user.h,v 1.4 1994/05/13 06:09:57 mycroft Exp $
|
||||
*/
|
||||
|
||||
#ifndef _NETISO_TP_USER_H_
|
||||
#define _NETISO_TP_USER_H_
|
||||
|
||||
/***********************************************************
|
||||
Copyright IBM Corporation 1987
|
||||
|
||||
@ -64,18 +61,13 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* These are the values a real-live user ;-) needs.
|
||||
*/
|
||||
|
||||
#ifndef _TYPES_
|
||||
#ifdef KERNEL
|
||||
#include "../sys/types.h"
|
||||
#else KERNEL
|
||||
#include <sys/types.h>
|
||||
#endif KERNEL
|
||||
#endif
|
||||
#include <sys/types.h>
|
||||
|
||||
#ifndef _NETISO_TP_USER_H_
|
||||
#define _NETISO_TP_USER_H_
|
||||
|
||||
struct tp_conn_param {
|
||||
/* PER CONNECTION parameters */
|
||||
@ -94,7 +86,7 @@ struct tp_conn_param {
|
||||
short p_ref_ticks;
|
||||
short p_inact_ticks;
|
||||
|
||||
short p_unused; /* was .. local credit fraction reported (>0) */
|
||||
short p_ptpdusize; /* preferred tpdusize/128 */
|
||||
short p_winsize;
|
||||
|
||||
u_char p_tpdusize; /* log 2 of size */
|
||||
@ -134,12 +126,11 @@ struct tp_conn_param {
|
||||
#define TPOPT_DISC_DATA 0x500
|
||||
#define TPOPT_CFRM_DATA 0x600
|
||||
#define TPOPT_CDDATA_CLEAR 0x700
|
||||
#define TPOPT_MY_TSEL 0x800
|
||||
#define TPOPT_PEER_TSEL 0x900
|
||||
#define TPOPT_PERF_MEAS 0xa00
|
||||
#define TPOPT_PSTATISTICS 0xb00
|
||||
#define TPOPT_PARAMS 0xc00 /* to replace a bunch of the others */
|
||||
#define TPOPT_MY_TSEL 0x800
|
||||
#define TPOPT_PEER_TSEL 0x900
|
||||
#define TPOPT_NGC8_ACCEPT 0xd00 /* negotiate connection requests */
|
||||
#define TPOPT_DISC_REASON 0xe00
|
||||
|
||||
struct tp_disc_reason {
|
||||
@ -152,18 +143,14 @@ struct tp_disc_reason {
|
||||
*/
|
||||
|
||||
/* read only flags */
|
||||
#define TPFLAG_DISC_DATA_OUT (u_char)0x10 /* disc data present */
|
||||
#define TPFLAG_DISC_DATA_IN (u_char)0x20 /* disc data present */
|
||||
#define TPFLAG_CONN_DATA_OUT (u_char)0x40 /* conn data present */
|
||||
#define TPFLAG_CONN_DATA_IN (u_char)0x80 /* conn data present */
|
||||
#define TPFLAG_XPD_PRESENT (u_char)0x08 /* xpd data present */
|
||||
#define TPFLAG_PEER_ON_SAMENET (u_char)0x02
|
||||
#define TPFLAG_NLQOS_PDN (u_char)0x01
|
||||
#define TPFLAG_NGC8_ACCEPT (u_char)0x04 /* negotiate conn rq's */
|
||||
#define TPFLAG_PEER_ON_SAMENET (u_char)0x02
|
||||
#define TPFLAG_GENERAL_ADDR (u_char)0x04 /* bound to wildcard addr */
|
||||
|
||||
|
||||
/*
|
||||
***********************end flags******************************
|
||||
*/
|
||||
|
||||
#endif /* !_NETISO_TP_USER_H_ */
|
||||
|
||||
#endif /* _NETISO_TP_USER_H_ */
|
||||
|
@ -1,6 +1,6 @@
|
||||
/*-
|
||||
* Copyright (c) 1991 The Regents of the University of California.
|
||||
* All rights reserved.
|
||||
* Copyright (c) 1991, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
@ -30,8 +30,8 @@
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tp_usrreq.c 7.17 (Berkeley) 6/27/91
|
||||
* $Id: tp_usrreq.c,v 1.3 1993/12/18 00:44:04 mycroft Exp $
|
||||
* from: @(#)tp_usrreq.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tp_usrreq.c,v 1.4 1994/05/13 06:09:59 mycroft Exp $
|
||||
*/
|
||||
|
||||
/***********************************************************
|
||||
@ -61,8 +61,6 @@ SOFTWARE.
|
||||
* ARGO Project, Computer Sciences Dept., University of Wisconsin - Madison
|
||||
*/
|
||||
/*
|
||||
* ARGO TP
|
||||
*
|
||||
* tp_usrreq(), the fellow that gets called from most of the socket code.
|
||||
* Pretty straighforward.
|
||||
* THe only really awful stuff here is the OOB processing, which is done
|
||||
@ -92,7 +90,7 @@ SOFTWARE.
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/iso_errno.h>
|
||||
|
||||
int tp_attach(), tp_driver();
|
||||
int tp_attach(), tp_pcbbind();
|
||||
int TNew;
|
||||
int TPNagle1, TPNagle2;
|
||||
struct tp_pcb *tp_listeners, *tp_intercepts;
|
||||
@ -137,7 +135,7 @@ dump_mbuf(n, str)
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
#endif notdef
|
||||
#endif /* notdef */
|
||||
if (n->m_next == n) {
|
||||
printf("LOOP!\n");
|
||||
return;
|
||||
@ -149,7 +147,7 @@ dump_mbuf(n, str)
|
||||
printf("\n");
|
||||
}
|
||||
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
@ -206,7 +204,7 @@ restart:
|
||||
* uipc_socket2.c (like sbappend).
|
||||
*/
|
||||
|
||||
sblock(sb);
|
||||
sblock(sb, M_WAITOK);
|
||||
for (nn = &sb->sb_mb; n = *nn; nn = &n->m_act)
|
||||
if (n->m_type == MT_OOBDATA)
|
||||
break;
|
||||
@ -243,7 +241,8 @@ restart:
|
||||
if ((inflags & MSG_PEEK) == 0) {
|
||||
n = *nn;
|
||||
*nn = n->m_act;
|
||||
sb->sb_cc -= m->m_len;
|
||||
for (; n; n = m_free(n))
|
||||
sbfree(sb, n);
|
||||
}
|
||||
|
||||
release:
|
||||
@ -311,7 +310,7 @@ tp_sendoob(tpcb, so, xdata, outflags)
|
||||
while (sb->sb_mb) {
|
||||
sbunlock(&so->so_snd); /* already locked by sosend */
|
||||
sbwait(&so->so_snd);
|
||||
sblock(&so->so_snd); /* sosend will unlock on return */
|
||||
sblock(&so->so_snd, M_WAITOK); /* sosend will unlock on return */
|
||||
}
|
||||
}
|
||||
|
||||
@ -370,7 +369,7 @@ tp_sendoob(tpcb, so, xdata, outflags)
|
||||
*
|
||||
*/
|
||||
/*ARGSUSED*/
|
||||
ProtoHook
|
||||
int
|
||||
tp_usrreq(so, req, m, nam, controlp)
|
||||
struct socket *so;
|
||||
u_int req;
|
||||
@ -406,18 +405,15 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
case PRU_ATTACH:
|
||||
if (tpcb) {
|
||||
error = EISCONN;
|
||||
break;
|
||||
}
|
||||
if (error = tp_attach(so, so->so_proto->pr_domain->dom_family))
|
||||
break;
|
||||
tpcb = sototpcb(so);
|
||||
} else if ((error = tp_attach(so, (int)nam)) == 0)
|
||||
tpcb = sototpcb(so);
|
||||
break;
|
||||
|
||||
case PRU_ABORT: /* called from close() */
|
||||
/* called for each incoming connect queued on the
|
||||
* parent (accepting) socket
|
||||
*/
|
||||
if (tpcb->tp_state == TP_OPEN) {
|
||||
if (tpcb->tp_state == TP_OPEN || tpcb->tp_state == TP_CONFIRMING) {
|
||||
E.ATTR(T_DISC_req).e_reason = E_TP_NO_SESSION;
|
||||
error = DoEvent(T_DISC_req); /* pretend it was a close() */
|
||||
break;
|
||||
@ -425,27 +421,14 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
|
||||
case PRU_DETACH: /* called from close() */
|
||||
/* called only after disconnect was called */
|
||||
if (tpcb->tp_state == TP_LISTENING) {
|
||||
register struct tp_pcb **tt;
|
||||
for (tt = &tp_listeners; *tt; tt = &((*tt)->tp_nextlisten))
|
||||
if (*tt == tpcb)
|
||||
break;
|
||||
if (*tt)
|
||||
*tt = tpcb->tp_nextlisten;
|
||||
else {
|
||||
for (tt = &tp_intercepts; *tt; tt = &((*tt)->tp_nextlisten))
|
||||
if (*tt == tpcb)
|
||||
break;
|
||||
if (*tt)
|
||||
*tt = tpcb->tp_nextlisten;
|
||||
else
|
||||
printf("tp_usrreq - detach: should panic\n");
|
||||
}
|
||||
}
|
||||
if (tpcb->tp_next)
|
||||
remque(tpcb);
|
||||
error = DoEvent(T_DETACH);
|
||||
if (tpcb->tp_state == TP_CLOSED) {
|
||||
if (tpcb->tp_notdetached) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf("PRU_DETACH: not detached\n");
|
||||
ENDDEBUG
|
||||
tp_detach(tpcb);
|
||||
}
|
||||
free((caddr_t)tpcb, M_PCB);
|
||||
tpcb = 0;
|
||||
}
|
||||
@ -459,30 +442,24 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
break;
|
||||
|
||||
case PRU_BIND:
|
||||
error = (tpcb->tp_nlproto->nlp_pcbbind)(so->so_pcb, nam);
|
||||
if (error == 0) {
|
||||
(tpcb->tp_nlproto->nlp_getsufx)(so->so_pcb, &tpcb->tp_lsuffixlen,
|
||||
tpcb->tp_lsuffix, TP_LOCAL);
|
||||
}
|
||||
error = tp_pcbbind(tpcb, nam);
|
||||
break;
|
||||
|
||||
case PRU_LISTEN:
|
||||
if (tpcb->tp_lsuffixlen == 0) {
|
||||
if (error = (tpcb->tp_nlproto->nlp_pcbbind)(so->so_pcb, MNULL))
|
||||
break;
|
||||
(tpcb->tp_nlproto->nlp_getsufx)(so->so_pcb, &tpcb->tp_lsuffixlen,
|
||||
tpcb->tp_lsuffix, TP_LOCAL);
|
||||
}
|
||||
if (tpcb->tp_next == 0) {
|
||||
if (tpcb->tp_state != TP_CLOSED || tpcb->tp_lsuffixlen == 0 ||
|
||||
tpcb->tp_next == 0)
|
||||
error = EINVAL;
|
||||
else {
|
||||
register struct tp_pcb **tt;
|
||||
remque(tpcb);
|
||||
tpcb->tp_next = tpcb->tp_prev = tpcb;
|
||||
tpcb->tp_nextlisten = tp_listeners;
|
||||
tp_listeners = tpcb;
|
||||
for (tt = &tp_listeners; *tt; tt = &((*tt)->tp_nextlisten))
|
||||
if ((*tt)->tp_lsuffixlen)
|
||||
break;
|
||||
tpcb->tp_nextlisten = *tt;
|
||||
*tt = tpcb;
|
||||
error = DoEvent(T_LISTEN_req);
|
||||
}
|
||||
IFDEBUG(D_TPISO)
|
||||
if (tpcb->tp_state != TP_CLOSED)
|
||||
printf("LISTEN ERROR: state 0x%x\n", tpcb->tp_state);
|
||||
ENDDEBUG
|
||||
error = DoEvent(T_LISTEN_req);
|
||||
break;
|
||||
|
||||
case PRU_CONNECT2:
|
||||
@ -502,16 +479,13 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
tpcb->tp_class);
|
||||
ENDDEBUG
|
||||
if (tpcb->tp_lsuffixlen == 0) {
|
||||
if (error = (tpcb->tp_nlproto->nlp_pcbbind)(so->so_pcb, MNULL)) {
|
||||
if (error = tp_pcbbind(tpcb, MNULL)) {
|
||||
IFDEBUG(D_CONN)
|
||||
printf("pcbbind returns error 0x%x\n", error);
|
||||
ENDDEBUG
|
||||
break;
|
||||
}
|
||||
(tpcb->tp_nlproto->nlp_getsufx)(so->so_pcb, &tpcb->tp_lsuffixlen,
|
||||
tpcb->tp_lsuffix, TP_LOCAL);
|
||||
}
|
||||
|
||||
IFDEBUG(D_CONN)
|
||||
printf("isop 0x%x isop->isop_socket offset 12 :\n", tpcb->tp_npcb);
|
||||
dump_buf(tpcb->tp_npcb, 16);
|
||||
@ -527,16 +501,14 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
ENDDEBUG
|
||||
if (tpcb->tp_fsuffixlen == 0) {
|
||||
/* didn't set peer extended suffix */
|
||||
(tpcb->tp_nlproto->nlp_getsufx)(so->so_pcb, &tpcb->tp_fsuffixlen,
|
||||
(tpcb->tp_nlproto->nlp_getsufx)(tpcb->tp_npcb, &tpcb->tp_fsuffixlen,
|
||||
tpcb->tp_fsuffix, TP_FOREIGN);
|
||||
}
|
||||
(void) (tpcb->tp_nlproto->nlp_mtu)(so, so->so_pcb,
|
||||
&tpcb->tp_l_tpdusize, &tpcb->tp_tpdusize, 0);
|
||||
if (tpcb->tp_state == TP_CLOSED) {
|
||||
soisconnecting(so);
|
||||
error = DoEvent(T_CONN_req);
|
||||
} else {
|
||||
(tpcb->tp_nlproto->nlp_pcbdisc)(so->so_pcb);
|
||||
(tpcb->tp_nlproto->nlp_pcbdisc)(tpcb->tp_npcb);
|
||||
error = EISCONN;
|
||||
}
|
||||
IFPERF(tpcb)
|
||||
@ -551,7 +523,7 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
break;
|
||||
|
||||
case PRU_ACCEPT:
|
||||
(tpcb->tp_nlproto->nlp_getnetaddr)(so->so_pcb, nam, TP_FOREIGN);
|
||||
(tpcb->tp_nlproto->nlp_getnetaddr)(tpcb->tp_npcb, nam, TP_FOREIGN);
|
||||
IFDEBUG(D_REQUEST)
|
||||
printf("ACCEPT PEERADDDR:");
|
||||
dump_buf(mtod(nam, char *), nam->m_len);
|
||||
@ -647,19 +619,12 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
* possibly by a whole cluster.
|
||||
*/
|
||||
{
|
||||
register struct mbuf *n = m;
|
||||
register struct sockbuf *sb = &so->so_snd;
|
||||
int maxsize = tpcb->tp_l_tpdusize
|
||||
- tp_headersize(DT_TPDU_type, tpcb)
|
||||
- (tpcb->tp_use_checksum?4:0) ;
|
||||
int totlen = n->m_pkthdr.len;
|
||||
int mbufcnt = 0;
|
||||
struct mbuf *nn;
|
||||
|
||||
/*
|
||||
* Could have eotsdu and no data.(presently MUST have
|
||||
* an mbuf though, even if its length == 0)
|
||||
*/
|
||||
int totlen = m->m_pkthdr.len;
|
||||
struct sockbuf *sb = &so->so_snd;
|
||||
IFPERF(tpcb)
|
||||
PStat(tpcb, Nb_from_sess) += totlen;
|
||||
tpmeas(tpcb->tp_lref, TPtime_from_session, 0, 0,
|
||||
@ -672,65 +637,9 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
dump_mbuf(sb->sb_mb, "so_snd.sb_mb");
|
||||
dump_mbuf(m, "m : to be added");
|
||||
ENDDEBUG
|
||||
/*
|
||||
* Pre-packetize the data in the sockbuf
|
||||
* according to negotiated mtu. Do it here
|
||||
* where we can safely wait for mbufs.
|
||||
*
|
||||
* This presumes knowledge of sockbuf conventions.
|
||||
*/
|
||||
if (n = sb->sb_mb)
|
||||
while (n->m_act)
|
||||
n = n->m_act;
|
||||
if ((nn = n) && n->m_pkthdr.len < maxsize) {
|
||||
u_int space = maxsize - n->m_pkthdr.len;
|
||||
|
||||
do {
|
||||
if (n->m_flags & M_EOR)
|
||||
goto on1;
|
||||
} while (n->m_next && (n = n->m_next));
|
||||
if (totlen <= space) {
|
||||
TPNagle1++;
|
||||
n->m_next = m;
|
||||
nn->m_pkthdr.len += totlen;
|
||||
while (n = n->m_next)
|
||||
sballoc(sb, n);
|
||||
if (eotsdu)
|
||||
nn->m_flags |= M_EOR;
|
||||
goto on2;
|
||||
} else {
|
||||
/*
|
||||
* Can't sleep here, because when you wake up
|
||||
* packet you want to attach to may be gone!
|
||||
*/
|
||||
if (TNew && (n->m_next = m_copym(m, 0, space, M_NOWAIT))) {
|
||||
nn->m_pkthdr.len += space;
|
||||
TPNagle2++;
|
||||
while (n = n->m_next)
|
||||
sballoc(sb, n);
|
||||
m_adj(m, space);
|
||||
}
|
||||
}
|
||||
}
|
||||
on1: mbufcnt++;
|
||||
for (n = m; n->m_pkthdr.len > maxsize;) {
|
||||
nn = m_copym(n, 0, maxsize, M_WAIT);
|
||||
sbappendrecord(sb, nn);
|
||||
m_adj(n, maxsize);
|
||||
mbufcnt++;
|
||||
}
|
||||
if (eotsdu)
|
||||
n->m_flags |= M_EOR;
|
||||
sbappendrecord(sb, n);
|
||||
on2:
|
||||
IFTRACE(D_DATA)
|
||||
tptraceTPCB(TPPTmisc,
|
||||
"SEND BF: maxsize totlen mbufcnt eotsdu",
|
||||
maxsize, totlen, mbufcnt, eotsdu);
|
||||
ENDTRACE
|
||||
tp_packetize(tpcb, m, eotsdu);
|
||||
IFDEBUG(D_SYSCALL)
|
||||
printf("PRU_SEND: eot %d after sbappend 0x%x mbufcnt 0x%x\n",
|
||||
eotsdu, n, mbufcnt);
|
||||
printf("PRU_SEND: eot %d after sbappend 0x%x\n", eotsdu, m);
|
||||
dump_mbuf(sb->sb_mb, "so_snd.sb_mb");
|
||||
ENDDEBUG
|
||||
if (tpcb->tp_state == TP_OPEN)
|
||||
@ -745,11 +654,11 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
break;
|
||||
|
||||
case PRU_SOCKADDR:
|
||||
(tpcb->tp_nlproto->nlp_getnetaddr)(so->so_pcb, nam, TP_LOCAL);
|
||||
(tpcb->tp_nlproto->nlp_getnetaddr)(tpcb->tp_npcb, nam, TP_LOCAL);
|
||||
break;
|
||||
|
||||
case PRU_PEERADDR:
|
||||
(tpcb->tp_nlproto->nlp_getnetaddr)(so->so_pcb, nam, TP_FOREIGN);
|
||||
(tpcb->tp_nlproto->nlp_getnetaddr)(tpcb->tp_npcb, nam, TP_FOREIGN);
|
||||
break;
|
||||
|
||||
case PRU_CONTROL:
|
||||
@ -767,18 +676,18 @@ tp_usrreq(so, req, m, nam, controlp)
|
||||
default:
|
||||
#ifdef ARGO_DEBUG
|
||||
printf("tp_usrreq UNKNOWN PRU %d\n", req);
|
||||
#endif ARGO_DEBUG
|
||||
#endif /* ARGO_DEBUG */
|
||||
error = EOPNOTSUPP;
|
||||
}
|
||||
|
||||
IFDEBUG(D_REQUEST)
|
||||
printf("%s, so 0x%x, tpcb 0x%x, error %d, state %d\n",
|
||||
"returning from tp_usrreq", so, tpcb, error,
|
||||
tpcb ? 0 : tpcb->tp_state);
|
||||
tpcb ? tpcb->tp_state : 0);
|
||||
ENDDEBUG
|
||||
IFTRACE(D_REQUEST)
|
||||
tptraceTPCB(TPPTusrreq, "END req so m state [", req, so, m,
|
||||
tpcb?0:tpcb->tp_state);
|
||||
tpcb ? tpcb->tp_state : 0);
|
||||
ENDTRACE
|
||||
if (controlp) {
|
||||
m_freem(controlp);
|
||||
|
350
sys/netiso/tuba_subr.c
Normal file
350
sys/netiso/tuba_subr.c
Normal file
@ -0,0 +1,350 @@
|
||||
/*
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tuba_subr.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tuba_subr.c,v 1.1 1994/05/13 06:10:01 mycroft Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/proc.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/malloc.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/errno.h>
|
||||
|
||||
#include <net/route.h>
|
||||
#include <net/if.h>
|
||||
|
||||
#include <netinet/in.h>
|
||||
#include <netinet/in_systm.h>
|
||||
#include <netinet/ip.h>
|
||||
#include <netinet/in_pcb.h>
|
||||
#include <netinet/ip_var.h>
|
||||
#include <netinet/ip_icmp.h>
|
||||
#include <netinet/tcp.h>
|
||||
#include <netinet/tcp_fsm.h>
|
||||
#include <netinet/tcp_seq.h>
|
||||
#include <netinet/tcp_timer.h>
|
||||
#include <netinet/tcp_var.h>
|
||||
#include <netinet/tcpip.h>
|
||||
#include <netinet/tcp_debug.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/clnp.h>
|
||||
#include <netiso/iso_pcb.h>
|
||||
#include <netiso/iso_var.h>
|
||||
#include <netiso/tuba_table.h>
|
||||
|
||||
static struct sockaddr_iso null_siso = { sizeof(null_siso), AF_ISO, };
|
||||
extern int tuba_table_size, tcp_keepidle, tcp_keepintvl, tcp_maxidle;
|
||||
extern int tcppcbcachemiss, tcppredack, tcppreddat, tcprexmtthresh;
|
||||
extern struct tcpiphdr tcp_saveti;
|
||||
struct inpcb tuba_inpcb;
|
||||
struct inpcb *tuba_last_inpcb = &tuba_inpcb;
|
||||
struct isopcb tuba_isopcb;
|
||||
/*
|
||||
* Tuba initialization
|
||||
*/
|
||||
void
|
||||
tuba_init()
|
||||
{
|
||||
#define TUBAHDRSIZE (3 /*LLC*/ + 9 /*CLNP Fixed*/ + 42 /*Addresses*/ \
|
||||
+ 6 /*CLNP Segment*/ + 20 /*TCP*/)
|
||||
|
||||
tuba_inpcb.inp_next = tuba_inpcb.inp_prev = &tuba_inpcb;
|
||||
tuba_isopcb.isop_next = tuba_isopcb.isop_prev = &tuba_isopcb;
|
||||
tuba_isopcb.isop_faddr = &tuba_isopcb.isop_sfaddr;
|
||||
tuba_isopcb.isop_laddr = &tuba_isopcb.isop_sladdr;
|
||||
if (max_protohdr < TUBAHDRSIZE)
|
||||
max_protohdr = TUBAHDRSIZE;
|
||||
if (max_linkhdr + TUBAHDRSIZE > MHLEN)
|
||||
panic("tuba_init");
|
||||
}
|
||||
|
||||
struct addr_arg {
|
||||
int error;
|
||||
int offset;
|
||||
u_long sum;
|
||||
};
|
||||
|
||||
/*
|
||||
* Calculate contribution to fudge factor for TCP checksum,
|
||||
* and coincidentally set pointer for convenience of clnp_output
|
||||
* if we are are responding when there is no isopcb around.
|
||||
*/
|
||||
static void
|
||||
tuba_getaddr(arg, siso, index)
|
||||
register struct addr_arg *arg;
|
||||
struct sockaddr_iso **siso;
|
||||
u_long index;
|
||||
{
|
||||
register struct tuba_cache *tc;
|
||||
if (index <= tuba_table_size && (tc = tuba_table[index])) {
|
||||
if (siso)
|
||||
*siso = &tc->tc_siso;
|
||||
arg->sum += (arg->offset & 1 ? tc->tc_ssum : tc->tc_sum)
|
||||
+ (0xffff ^ index);
|
||||
arg->offset += tc->tc_siso.siso_nlen + 1;
|
||||
} else
|
||||
arg->error = 1;
|
||||
}
|
||||
|
||||
tuba_output(m, tp)
|
||||
register struct mbuf *m;
|
||||
struct tcpcb *tp;
|
||||
{
|
||||
register struct tcpiphdr *n;
|
||||
struct isopcb *isop;
|
||||
struct addr_arg arg;
|
||||
|
||||
if (tp == 0 || (n = tp->t_template) == 0 ||
|
||||
(isop = (struct isopcb *)tp->t_tuba_pcb) == 0) {
|
||||
isop = &tuba_isopcb;
|
||||
n = mtod(m, struct tcpiphdr *);
|
||||
arg.error = arg.sum = arg.offset = 0;
|
||||
tuba_getaddr(&arg, &tuba_isopcb.isop_faddr, n->ti_dst.s_addr);
|
||||
tuba_getaddr(&arg, &tuba_isopcb.isop_laddr, n->ti_src.s_addr);
|
||||
REDUCE(arg.sum, arg.sum);
|
||||
goto adjust;
|
||||
}
|
||||
if (n->ti_sum == 0) {
|
||||
arg.error = arg.sum = arg.offset = 0;
|
||||
tuba_getaddr(&arg, (struct sockaddr_iso **)0, n->ti_dst.s_addr);
|
||||
tuba_getaddr(&arg, (struct sockaddr_iso **)0, n->ti_src.s_addr);
|
||||
REDUCE(arg.sum, arg.sum);
|
||||
n->ti_sum = arg.sum;
|
||||
n = mtod(m, struct tcpiphdr *);
|
||||
adjust:
|
||||
if (arg.error) {
|
||||
m_freem(m);
|
||||
return (EADDRNOTAVAIL);
|
||||
}
|
||||
REDUCE(n->ti_sum, n->ti_sum + (0xffff ^ arg.sum));
|
||||
}
|
||||
m->m_len -= sizeof (struct ip);
|
||||
m->m_pkthdr.len -= sizeof (struct ip);
|
||||
m->m_data += sizeof (struct ip);
|
||||
return (clnp_output(m, isop, m->m_pkthdr.len, 0));
|
||||
}
|
||||
|
||||
tuba_refcnt(isop, delta)
|
||||
struct isopcb *isop;
|
||||
{
|
||||
register struct tuba_cache *tc;
|
||||
unsigned index, sum;
|
||||
|
||||
if (delta != 1)
|
||||
delta = -1;
|
||||
if (isop == 0 || isop->isop_faddr == 0 || isop->isop_laddr == 0 ||
|
||||
(delta == -1 && isop->isop_tuba_cached == 0) ||
|
||||
(delta == 1 && isop->isop_tuba_cached != 0))
|
||||
return;
|
||||
isop->isop_tuba_cached = (delta == 1);
|
||||
if ((index = tuba_lookup(isop->isop_faddr, M_DONTWAIT)) != 0 &&
|
||||
(tc = tuba_table[index]) != 0 && (delta == 1 || tc->tc_refcnt > 0))
|
||||
tc->tc_refcnt += delta;
|
||||
if ((index = tuba_lookup(isop->isop_laddr, M_DONTWAIT)) != 0 &&
|
||||
(tc = tuba_table[index]) != 0 && (delta == 1 || tc->tc_refcnt > 0))
|
||||
tc->tc_refcnt += delta;
|
||||
}
|
||||
|
||||
tuba_pcbdetach(isop)
|
||||
struct isopcb *isop;
|
||||
{
|
||||
if (isop == 0)
|
||||
return;
|
||||
tuba_refcnt(isop, -1);
|
||||
isop->isop_socket = 0;
|
||||
iso_pcbdetach(isop);
|
||||
}
|
||||
|
||||
/*
|
||||
* Avoid in_pcbconnect in faked out tcp_input()
|
||||
*/
|
||||
tuba_pcbconnect(inp, nam)
|
||||
register struct inpcb *inp;
|
||||
struct mbuf *nam;
|
||||
{
|
||||
register struct sockaddr_iso *siso;
|
||||
struct sockaddr_in *sin = mtod(nam, struct sockaddr_in *);
|
||||
struct tcpcb *tp = intotcpcb(inp);
|
||||
struct isopcb *isop = (struct isopcb *)tp->t_tuba_pcb;
|
||||
int error;
|
||||
|
||||
/* hardwire iso_pcbbind() here */
|
||||
siso = isop->isop_laddr = &isop->isop_sladdr;
|
||||
*siso = tuba_table[inp->inp_laddr.s_addr]->tc_siso;
|
||||
siso->siso_tlen = sizeof(inp->inp_lport);
|
||||
bcopy((caddr_t)&inp->inp_lport, TSEL(siso), sizeof(inp->inp_lport));
|
||||
|
||||
/* hardwire in_pcbconnect() here without assigning route */
|
||||
inp->inp_fport = sin->sin_port;
|
||||
inp->inp_faddr = sin->sin_addr;
|
||||
|
||||
/* reuse nam argument to call iso_pcbconnect() */
|
||||
nam->m_len = sizeof(*siso);
|
||||
siso = mtod(nam, struct sockaddr_iso *);
|
||||
*siso = tuba_table[inp->inp_faddr.s_addr]->tc_siso;
|
||||
siso->siso_tlen = sizeof(inp->inp_fport);
|
||||
bcopy((caddr_t)&inp->inp_fport, TSEL(siso), sizeof(inp->inp_fport));
|
||||
|
||||
if ((error = iso_pcbconnect(isop, nam)) == 0)
|
||||
tuba_refcnt(isop, 1);
|
||||
return (error);
|
||||
}
|
||||
|
||||
/*
|
||||
* CALLED FROM:
|
||||
* clnp's input routine, indirectly through the protosw.
|
||||
* FUNCTION and ARGUMENTS:
|
||||
* Take a packet (m) from clnp, strip off the clnp header
|
||||
* and do tcp input processing.
|
||||
* No return value.
|
||||
*/
|
||||
tuba_tcpinput(m, src, dst)
|
||||
register struct mbuf *m;
|
||||
struct sockaddr_iso *src, *dst;
|
||||
{
|
||||
unsigned long sum, lindex, findex;
|
||||
register struct tcpiphdr *ti;
|
||||
register struct inpcb *inp;
|
||||
caddr_t optp = NULL;
|
||||
int optlen;
|
||||
int len, tlen, off;
|
||||
register struct tcpcb *tp = 0;
|
||||
int tiflags;
|
||||
struct socket *so;
|
||||
int todrop, acked, ourfinisacked, needoutput = 0;
|
||||
short ostate;
|
||||
struct in_addr laddr;
|
||||
int dropsocket = 0, iss = 0;
|
||||
u_long tiwin, ts_val, ts_ecr;
|
||||
int ts_present = 0;
|
||||
|
||||
if ((m->m_flags & M_PKTHDR) == 0)
|
||||
panic("tuba_tcpinput");
|
||||
/*
|
||||
* Do some housekeeping looking up CLNP addresses.
|
||||
* If we are out of space might as well drop the packet now.
|
||||
*/
|
||||
tcpstat.tcps_rcvtotal++;
|
||||
lindex = tuba_lookup(dst, M_DONTWAIT);
|
||||
findex = tuba_lookup(src, M_DONTWAIT);
|
||||
if (lindex == 0 || findex == 0)
|
||||
goto drop;
|
||||
/*
|
||||
* CLNP gave us an mbuf chain WITH the clnp header pulled up,
|
||||
* but the data pointer pushed past it.
|
||||
*/
|
||||
len = m->m_len;
|
||||
tlen = m->m_pkthdr.len;
|
||||
m->m_data -= sizeof(struct ip);
|
||||
m->m_len += sizeof(struct ip);
|
||||
m->m_pkthdr.len += sizeof(struct ip);
|
||||
m->m_flags &= ~(M_MCAST|M_BCAST); /* XXX should do this in clnp_input */
|
||||
/*
|
||||
* The reassembly code assumes it will be overwriting a useless
|
||||
* part of the packet, which is why we need to have it point
|
||||
* into the packet itself.
|
||||
*
|
||||
* Check to see if the data is properly alligned
|
||||
* so that we can save copying the tcp header.
|
||||
* This code knows way too much about the structure of mbufs!
|
||||
*/
|
||||
off = ((sizeof (long) - 1) & ((m->m_flags & M_EXT) ?
|
||||
(m->m_data - m->m_ext.ext_buf) : (m->m_data - m->m_pktdat)));
|
||||
if (off || len < sizeof(struct tcphdr)) {
|
||||
struct mbuf *m0 = m;
|
||||
|
||||
MGETHDR(m, M_DONTWAIT, MT_DATA);
|
||||
if (m == 0) {
|
||||
m = m0;
|
||||
goto drop;
|
||||
}
|
||||
m->m_next = m0;
|
||||
m->m_data += max_linkhdr;
|
||||
m->m_pkthdr = m0->m_pkthdr;
|
||||
m->m_flags = m0->m_flags & M_COPYFLAGS;
|
||||
if (len < sizeof(struct tcphdr)) {
|
||||
m->m_len = 0;
|
||||
if ((m = m_pullup(m, sizeof(struct tcpiphdr))) == 0) {
|
||||
tcpstat.tcps_rcvshort++;
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
bcopy(mtod(m0, caddr_t) + sizeof(struct ip),
|
||||
mtod(m, caddr_t) + sizeof(struct ip),
|
||||
sizeof(struct tcphdr));
|
||||
m0->m_len -= sizeof(struct tcpiphdr);
|
||||
m0->m_data += sizeof(struct tcpiphdr);
|
||||
m->m_len = sizeof(struct tcpiphdr);
|
||||
}
|
||||
}
|
||||
/*
|
||||
* Calculate checksum of extended TCP header and data,
|
||||
* replacing what would have been IP addresses by
|
||||
* the IP checksum of the CLNP addresses.
|
||||
*/
|
||||
ti = mtod(m, struct tcpiphdr *);
|
||||
ti->ti_dst.s_addr = tuba_table[lindex]->tc_sum;
|
||||
if (dst->siso_nlen & 1)
|
||||
ti->ti_src.s_addr = tuba_table[findex]->tc_sum;
|
||||
else
|
||||
ti->ti_src.s_addr = tuba_table[findex]->tc_ssum;
|
||||
ti->ti_prev = ti->ti_next = 0;
|
||||
ti->ti_x1 = 0; ti->ti_pr = ISOPROTO_TCP;
|
||||
ti->ti_len = htons((u_short)tlen);
|
||||
if (ti->ti_sum = in_cksum(m, m->m_pkthdr.len)) {
|
||||
tcpstat.tcps_rcvbadsum++;
|
||||
goto drop;
|
||||
}
|
||||
ti->ti_src.s_addr = findex;
|
||||
ti->ti_dst.s_addr = lindex;
|
||||
/*
|
||||
* Now include the rest of TCP input
|
||||
*/
|
||||
#define TUBA_INCLUDE
|
||||
#define in_pcbconnect tuba_pcbconnect
|
||||
#define tcb tuba_inpcb
|
||||
#define tcp_last_inpcb tuba_last_inpcb
|
||||
|
||||
#include <netinet/tcp_input.c>
|
||||
}
|
||||
|
||||
#define tcp_slowtimo tuba_slowtimo
|
||||
#define tcp_fasttimo tuba_fasttimo
|
||||
|
||||
#include <netinet/tcp_timer.c>
|
144
sys/netiso/tuba_table.c
Normal file
144
sys/netiso/tuba_table.c
Normal file
@ -0,0 +1,144 @@
|
||||
/*
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tuba_table.c 8.2 (Berkeley) 11/15/93
|
||||
* $Id: tuba_table.c,v 1.1 1994/05/13 06:10:04 mycroft Exp $
|
||||
*/
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/proc.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/domain.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/ioctl.h>
|
||||
#include <sys/time.h>
|
||||
#include <sys/kernel.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#include <net/radix.h>
|
||||
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/tuba_table.h>
|
||||
|
||||
int tuba_table_size;
|
||||
struct tuba_cache **tuba_table;
|
||||
struct radix_node_head *tuba_tree;
|
||||
extern int arpt_keep, arpt_prune; /* use same values as arp cache */
|
||||
|
||||
void
|
||||
tuba_timer()
|
||||
{
|
||||
int s = splnet();
|
||||
int i;
|
||||
register struct tuba_cache *tc;
|
||||
long timelimit = time.tv_sec - arpt_keep;
|
||||
|
||||
timeout(tuba_timer, (caddr_t)0, arpt_prune * hz);
|
||||
for (i = tuba_table_size; i > 0; i--)
|
||||
if ((tc = tuba_table[i]) && (tc->tc_refcnt == 0) &&
|
||||
(tc->tc_time < timelimit)) {
|
||||
tuba_table[i] = 0;
|
||||
rn_delete(&tc->tc_siso.siso_addr, NULL, tuba_tree);
|
||||
free((caddr_t)tc, M_RTABLE);
|
||||
}
|
||||
splx(s);
|
||||
}
|
||||
|
||||
tuba_table_init()
|
||||
{
|
||||
rn_inithead((void **)&tuba_tree, 40);
|
||||
timeout(tuba_timer, (caddr_t)0, arpt_prune * hz);
|
||||
}
|
||||
|
||||
int
|
||||
tuba_lookup(siso, wait)
|
||||
register struct sockaddr_iso *siso;
|
||||
{
|
||||
struct radix_node *rn, *rn_match();
|
||||
register struct tuba_cache *tc;
|
||||
struct tuba_cache **new;
|
||||
int dupentry = 0, sum_a = 0, sum_b = 0, old_size, i;
|
||||
|
||||
if ((rn = rn_match((caddr_t)&siso->siso_addr, tuba_tree->rnh_treetop))
|
||||
&& ((rn->rn_flags & RNF_ROOT) == 0)) {
|
||||
tc = (struct tuba_cache *)rn;
|
||||
tc->tc_time = time.tv_sec;
|
||||
return (tc->tc_index);
|
||||
}
|
||||
if ((tc = (struct tuba_cache *)malloc(sizeof(*tc), M_RTABLE, wait))
|
||||
== NULL)
|
||||
return (0);
|
||||
bzero((caddr_t)tc, sizeof (*tc));
|
||||
bcopy(siso->siso_data, tc->tc_siso.siso_data,
|
||||
tc->tc_siso.siso_nlen = siso->siso_nlen);
|
||||
rn_insert(&tc->tc_siso.siso_addr, tuba_tree, &dupentry, tc->tc_nodes);
|
||||
if (dupentry)
|
||||
panic("tuba_lookup 1");
|
||||
tc->tc_siso.siso_family = AF_ISO;
|
||||
tc->tc_siso.siso_len = sizeof(tc->tc_siso);
|
||||
tc->tc_time = time.tv_sec;
|
||||
for (i = sum_a = tc->tc_siso.siso_nlen; --i >= 0; )
|
||||
(i & 1 ? sum_a : sum_b) += (u_char)tc->tc_siso.siso_data[i];
|
||||
REDUCE(tc->tc_sum, (sum_a << 8) + sum_b);
|
||||
HTONS(tc->tc_sum);
|
||||
SWAB(tc->tc_ssum, tc->tc_sum);
|
||||
for (i = tuba_table_size; i > 0; i--)
|
||||
if (tuba_table[i] == 0)
|
||||
goto fixup;
|
||||
old_size = tuba_table_size;
|
||||
if (tuba_table_size == 0)
|
||||
tuba_table_size = 15;
|
||||
if (tuba_table_size > 0x7fff)
|
||||
return (0);
|
||||
tuba_table_size = 1 + 2 * tuba_table_size;
|
||||
i = (tuba_table_size + 1) * sizeof(tc);
|
||||
new = (struct tuba_cache **)malloc((unsigned)i, M_RTABLE, wait);
|
||||
if (new == 0) {
|
||||
tuba_table_size = old_size;
|
||||
rn_delete(&tc->tc_siso.siso_addr, NULL, tuba_tree);
|
||||
free((caddr_t)tc, M_RTABLE);
|
||||
return (0);
|
||||
}
|
||||
bzero((caddr_t)new, (unsigned)i);
|
||||
if (tuba_table) {
|
||||
bcopy((caddr_t)tuba_table, (caddr_t)new, i >> 1);
|
||||
free((caddr_t)tuba_table, M_RTABLE);
|
||||
}
|
||||
tuba_table = new;
|
||||
i = tuba_table_size;
|
||||
fixup:
|
||||
tuba_table[i] = tc;
|
||||
tc->tc_index = i;
|
||||
return (tc->tc_index);
|
||||
}
|
60
sys/netiso/tuba_table.h
Normal file
60
sys/netiso/tuba_table.h
Normal file
@ -0,0 +1,60 @@
|
||||
/*-
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tuba_table.h 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tuba_table.h,v 1.1 1994/05/13 06:10:07 mycroft Exp $
|
||||
*/
|
||||
|
||||
struct tuba_cache {
|
||||
struct radix_node tc_nodes[2]; /* convenient lookup */
|
||||
int tc_refcnt;
|
||||
int tc_time; /* last looked up */
|
||||
int tc_flags;
|
||||
#define TCF_PERM 1
|
||||
int tc_index;
|
||||
u_short tc_sum; /* cksum of nsap inc. length */
|
||||
u_short tc_ssum; /* swab(tc_sum) */
|
||||
struct sockaddr_iso tc_siso; /* for responding */
|
||||
};
|
||||
|
||||
#define ADDCARRY(x) (x >= 65535 ? x -= 65535 : x)
|
||||
#define REDUCE(a, b) { union { u_short s[2]; long l;} l_util; long x; \
|
||||
l_util.l = (b); x = l_util.s[0] + l_util.s[1]; ADDCARRY(x); \
|
||||
if (x == 0) x = 0xffff; a = x;}
|
||||
#define SWAB(a, b) { union { u_char c[2]; u_short s;} s; u_char t; \
|
||||
s.s = (b); t = s.c[0]; s.c[0] = s.c[1]; s.c[1] = t; a = s.s;}
|
||||
|
||||
#ifdef KERNEL
|
||||
extern int tuba_table_size;
|
||||
extern struct tuba_cache **tuba_table;
|
||||
extern struct radix_node_head *tuba_tree;
|
||||
#endif
|
313
sys/netiso/tuba_usrreq.c
Normal file
313
sys/netiso/tuba_usrreq.c
Normal file
@ -0,0 +1,313 @@
|
||||
/*
|
||||
* Copyright (c) 1992, 1993
|
||||
* The Regents of the University of California. All rights reserved.
|
||||
*
|
||||
* Redistribution and use in source and binary forms, with or without
|
||||
* modification, are permitted provided that the following conditions
|
||||
* are met:
|
||||
* 1. Redistributions of source code must retain the above copyright
|
||||
* notice, this list of conditions and the following disclaimer.
|
||||
* 2. Redistributions in binary form must reproduce the above copyright
|
||||
* notice, this list of conditions and the following disclaimer in the
|
||||
* documentation and/or other materials provided with the distribution.
|
||||
* 3. All advertising materials mentioning features or use of this software
|
||||
* must display the following acknowledgement:
|
||||
* This product includes software developed by the University of
|
||||
* California, Berkeley and its contributors.
|
||||
* 4. Neither the name of the University nor the names of its contributors
|
||||
* may be used to endorse or promote products derived from this software
|
||||
* without specific prior written permission.
|
||||
*
|
||||
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
|
||||
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
|
||||
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
|
||||
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
|
||||
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
|
||||
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
|
||||
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
|
||||
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
|
||||
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
|
||||
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
|
||||
* SUCH DAMAGE.
|
||||
*
|
||||
* from: @(#)tuba_usrreq.c 8.1 (Berkeley) 6/10/93
|
||||
* $Id: tuba_usrreq.c,v 1.1 1994/05/13 06:10:10 mycroft Exp $
|
||||
*/
|
||||
|
||||
#include <sys/param.h>
|
||||
#include <sys/systm.h>
|
||||
#include <sys/malloc.h>
|
||||
#include <sys/mbuf.h>
|
||||
#include <sys/socket.h>
|
||||
#include <sys/socketvar.h>
|
||||
#include <sys/protosw.h>
|
||||
#include <sys/errno.h>
|
||||
#include <sys/stat.h>
|
||||
|
||||
#include <net/if.h>
|
||||
#include <net/route.h>
|
||||
|
||||
#include <netinet/in.h>
|
||||
#include <netinet/in_systm.h>
|
||||
#include <netinet/ip.h>
|
||||
#include <netinet/in_pcb.h>
|
||||
#include <netinet/ip_var.h>
|
||||
#include <netinet/tcp.h>
|
||||
#include <netinet/tcp_fsm.h>
|
||||
#include <netinet/tcp_seq.h>
|
||||
#include <netinet/tcp_timer.h>
|
||||
#include <netinet/tcp_var.h>
|
||||
#include <netinet/tcpip.h>
|
||||
#include <netinet/tcp_debug.h>
|
||||
|
||||
#include <netiso/argo_debug.h>
|
||||
#include <netiso/iso.h>
|
||||
#include <netiso/clnp.h>
|
||||
#include <netiso/iso_pcb.h>
|
||||
#include <netiso/iso_var.h>
|
||||
#include <netiso/tuba_table.h>
|
||||
/*
|
||||
* TCP protocol interface to socket abstraction.
|
||||
*/
|
||||
extern char *tcpstates[];
|
||||
extern struct inpcb tuba_inpcb;
|
||||
extern struct isopcb tuba_isopcb;
|
||||
|
||||
/*
|
||||
* Process a TCP user request for TCP tb. If this is a send request
|
||||
* then m is the mbuf chain of send data. If this is a timer expiration
|
||||
* (called from the software clock routine), then timertype tells which timer.
|
||||
*/
|
||||
/*ARGSUSED*/
|
||||
tuba_usrreq(so, req, m, nam, control)
|
||||
struct socket *so;
|
||||
int req;
|
||||
struct mbuf *m, *nam, *control;
|
||||
{
|
||||
register struct inpcb *inp;
|
||||
register struct isopcb *isop;
|
||||
register struct tcpcb *tp;
|
||||
int s;
|
||||
int error = 0;
|
||||
int ostate;
|
||||
struct sockaddr_iso *siso;
|
||||
|
||||
if (req == PRU_CONTROL)
|
||||
return (iso_control(so, (int)m, (caddr_t)nam,
|
||||
(struct ifnet *)control));
|
||||
|
||||
s = splnet();
|
||||
inp = sotoinpcb(so);
|
||||
/*
|
||||
* When a TCP is attached to a socket, then there will be
|
||||
* a (struct inpcb) pointed at by the socket, and this
|
||||
* structure will point at a subsidary (struct tcpcb).
|
||||
*/
|
||||
if (inp == 0 && req != PRU_ATTACH) {
|
||||
splx(s);
|
||||
return (EINVAL); /* XXX */
|
||||
}
|
||||
if (inp) {
|
||||
tp = intotcpcb(inp);
|
||||
if (tp == 0)
|
||||
panic("tuba_usrreq");
|
||||
ostate = tp->t_state;
|
||||
isop = (struct isopcb *)tp->t_tuba_pcb;
|
||||
if (isop == 0)
|
||||
panic("tuba_usrreq 2");
|
||||
} else
|
||||
ostate = 0;
|
||||
switch (req) {
|
||||
|
||||
/*
|
||||
* TCP attaches to socket via PRU_ATTACH, reserving space,
|
||||
* and an internet control block. We also need to
|
||||
* allocate an isopcb and separate the control block from
|
||||
* tcp/ip ones.
|
||||
*/
|
||||
case PRU_ATTACH:
|
||||
if (error = iso_pcballoc(so, &tuba_isopcb))
|
||||
break;
|
||||
isop = (struct isopcb *)so->so_pcb;
|
||||
so->so_pcb = 0;
|
||||
if (error = tcp_usrreq(so, req, m, nam, control)) {
|
||||
isop->isop_socket = 0;
|
||||
iso_pcbdetach(isop);
|
||||
} else {
|
||||
inp = sotoinpcb(so);
|
||||
remque(inp);
|
||||
insque(inp, &tuba_inpcb);
|
||||
inp->inp_head = &tuba_inpcb;
|
||||
tp = intotcpcb(inp);
|
||||
if (tp == 0)
|
||||
panic("tuba_usrreq 3");
|
||||
tp->t_tuba_pcb = (caddr_t) isop;
|
||||
}
|
||||
goto notrace;
|
||||
|
||||
/*
|
||||
* PRU_DETACH detaches the TCP protocol from the socket.
|
||||
* If the protocol state is non-embryonic, then can't
|
||||
* do this directly: have to initiate a PRU_DISCONNECT,
|
||||
* which may finish later; embryonic TCB's can just
|
||||
* be discarded here.
|
||||
*/
|
||||
case PRU_DETACH:
|
||||
if (tp->t_state > TCPS_LISTEN)
|
||||
tp = tcp_disconnect(tp);
|
||||
else
|
||||
tp = tcp_close(tp);
|
||||
if (tp == 0)
|
||||
tuba_pcbdetach(isop);
|
||||
break;
|
||||
|
||||
/*
|
||||
* Give the socket an address.
|
||||
*/
|
||||
case PRU_BIND:
|
||||
siso = mtod(nam, struct sockaddr_iso *);
|
||||
if (siso->siso_tlen && siso->siso_tlen != 2) {
|
||||
error = EINVAL;
|
||||
break;
|
||||
}
|
||||
if ((error = iso_pcbbind(isop, nam)) ||
|
||||
(siso = isop->isop_laddr) == 0)
|
||||
break;
|
||||
bcopy(TSEL(siso), &inp->inp_lport, 2);
|
||||
if (siso->siso_nlen &&
|
||||
!(inp->inp_laddr.s_addr = tuba_lookup(siso, M_WAITOK)))
|
||||
error = ENOBUFS;
|
||||
break;
|
||||
|
||||
/*
|
||||
* Prepare to accept connections.
|
||||
*/
|
||||
case PRU_CONNECT:
|
||||
case PRU_LISTEN:
|
||||
if (inp->inp_lport == 0 &&
|
||||
(error = iso_pcbbind(isop, (struct mbuf *)0)))
|
||||
break;
|
||||
bcopy(TSEL(isop->isop_laddr), &inp->inp_lport, 2);
|
||||
if (req == PRU_LISTEN) {
|
||||
tp->t_state = TCPS_LISTEN;
|
||||
break;
|
||||
}
|
||||
/*FALLTHROUGH*/
|
||||
/*
|
||||
* Initiate connection to peer.
|
||||
* Create a template for use in transmissions on this connection.
|
||||
* Enter SYN_SENT state, and mark socket as connecting.
|
||||
* Start keep-alive timer, and seed output sequence space.
|
||||
* Send initial segment on connection.
|
||||
*/
|
||||
/* case PRU_CONNECT: */
|
||||
if (error = iso_pcbconnect(isop, nam))
|
||||
break;
|
||||
if ((siso = isop->isop_laddr) && siso->siso_nlen > 1)
|
||||
siso->siso_data[siso->siso_nlen - 1] = ISOPROTO_TCP;
|
||||
else
|
||||
panic("tuba_usrreq: connect");
|
||||
siso = mtod(nam, struct sockaddr_iso *);
|
||||
if (!(inp->inp_faddr.s_addr = tuba_lookup(siso, M_WAITOK))) {
|
||||
unconnect:
|
||||
iso_pcbdisconnect(isop);
|
||||
error = ENOBUFS;
|
||||
break;
|
||||
}
|
||||
bcopy(TSEL(isop->isop_faddr), &inp->inp_fport, 2);
|
||||
if (inp->inp_laddr.s_addr == 0 &&
|
||||
(inp->inp_laddr.s_addr =
|
||||
tuba_lookup(isop->isop_laddr, M_WAITOK)) == 0)
|
||||
goto unconnect;
|
||||
if ((tp->t_template = tcp_template(tp)) == 0)
|
||||
goto unconnect;
|
||||
soisconnecting(so);
|
||||
tcpstat.tcps_connattempt++;
|
||||
tp->t_state = TCPS_SYN_SENT;
|
||||
tp->t_timer[TCPT_KEEP] = TCPTV_KEEP_INIT;
|
||||
tp->iss = tcp_iss; tcp_iss += TCP_ISSINCR/2;
|
||||
tcp_sendseqinit(tp);
|
||||
error = tcp_output(tp);
|
||||
tuba_refcnt(isop, 1);
|
||||
break;
|
||||
|
||||
/*
|
||||
* Initiate disconnect from peer.
|
||||
* If connection never passed embryonic stage, just drop;
|
||||
* else if don't need to let data drain, then can just drop anyways,
|
||||
* else have to begin TCP shutdown process: mark socket disconnecting,
|
||||
* drain unread data, state switch to reflect user close, and
|
||||
* send segment (e.g. FIN) to peer. Socket will be really disconnected
|
||||
* when peer sends FIN and acks ours.
|
||||
*
|
||||
* SHOULD IMPLEMENT LATER PRU_CONNECT VIA REALLOC TCPCB.
|
||||
*/
|
||||
case PRU_DISCONNECT:
|
||||
if ((tp = tcp_disconnect(tp)) == 0)
|
||||
tuba_pcbdetach(isop);
|
||||
break;
|
||||
|
||||
/*
|
||||
* Accept a connection. Essentially all the work is
|
||||
* done at higher levels; just return the address
|
||||
* of the peer, storing through addr.
|
||||
*/
|
||||
case PRU_ACCEPT:
|
||||
bcopy((caddr_t)isop->isop_faddr, mtod(nam, caddr_t),
|
||||
nam->m_len = isop->isop_faddr->siso_len);
|
||||
break;
|
||||
|
||||
/*
|
||||
* Mark the connection as being incapable of further output.
|
||||
*/
|
||||
case PRU_SHUTDOWN:
|
||||
socantsendmore(so);
|
||||
tp = tcp_usrclosed(tp);
|
||||
if (tp)
|
||||
error = tcp_output(tp);
|
||||
else
|
||||
tuba_pcbdetach(isop);
|
||||
break;
|
||||
/*
|
||||
* Abort the TCP.
|
||||
*/
|
||||
case PRU_ABORT:
|
||||
if ((tp = tcp_drop(tp, ECONNABORTED)) == 0)
|
||||
tuba_pcbdetach(isop);
|
||||
break;
|
||||
|
||||
|
||||
case PRU_SOCKADDR:
|
||||
if (isop->isop_laddr)
|
||||
bcopy((caddr_t)isop->isop_laddr, mtod(nam, caddr_t),
|
||||
nam->m_len = isop->isop_laddr->siso_len);
|
||||
break;
|
||||
|
||||
case PRU_PEERADDR:
|
||||
if (isop->isop_faddr)
|
||||
bcopy((caddr_t)isop->isop_faddr, mtod(nam, caddr_t),
|
||||
nam->m_len = isop->isop_faddr->siso_len);
|
||||
break;
|
||||
|
||||
default:
|
||||
error = tcp_usrreq(so, req, m, nam, control);
|
||||
goto notrace;
|
||||
}
|
||||
if (tp && (so->so_options & SO_DEBUG))
|
||||
tcp_trace(TA_USER, ostate, tp, (struct tcpiphdr *)0, req);
|
||||
notrace:
|
||||
splx(s);
|
||||
return(error);
|
||||
}
|
||||
|
||||
tuba_ctloutput(op, so, level, optname, mp)
|
||||
int op;
|
||||
struct socket *so;
|
||||
int level, optname;
|
||||
struct mbuf **mp;
|
||||
{
|
||||
int clnp_ctloutput(), tcp_ctloutput();
|
||||
|
||||
return ((level != IPPROTO_TCP ? clnp_ctloutput : tcp_ctloutput)
|
||||
(op, so, level, optname, mp));
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user