xref: /csrg-svn/sys/netiso/idrp_usrreq.c (revision 56888)
1*56888Ssklower /*
2*56888Ssklower  * Copyright (c) 1992 Regents of the University of California.
3*56888Ssklower  * All rights reserved.
4*56888Ssklower  *
5*56888Ssklower  * %sccs.include.redist.c%
6*56888Ssklower  *
7*56888Ssklower  *	@(#)idrp_usrreq.c	7.1 (Berkeley) 11/17/92
8*56888Ssklower  */
9*56888Ssklower 
10*56888Ssklower #include <sys/param.h>
11*56888Ssklower #include <sys/proc.h>
12*56888Ssklower #include <sys/systm.h>
13*56888Ssklower #include <sys/malloc.h>
14*56888Ssklower #include <sys/mbuf.h>
15*56888Ssklower #include <sys/socket.h>
16*56888Ssklower #include <sys/socketvar.h>
17*56888Ssklower #include <sys/protosw.h>
18*56888Ssklower #include <sys/errno.h>
19*56888Ssklower 
20*56888Ssklower #include <net/route.h>
21*56888Ssklower #include <net/if.h>
22*56888Ssklower 
23*56888Ssklower #include <netiso/argo_debug.h>
24*56888Ssklower #include <netiso/iso.h>
25*56888Ssklower #include <netiso/clnp.h>
26*56888Ssklower #include <netiso/clnl.h>
27*56888Ssklower #include <netiso/iso_pcb.h>
28*56888Ssklower #include <netiso/iso_var.h>
29*56888Ssklower 
30*56888Ssklower int idrp_input();
31*56888Ssklower struct	isopcb	idrp_isop;
32*56888Ssklower static	struct	sockaddr_iso idrp_addrs[2] =
33*56888Ssklower {  { sizeof(idrp_addrs), AF_ISO, }, { sizeof(idrp_addrs[1]), AF_ISO, } };
34*56888Ssklower /*
35*56888Ssklower  * IDRP initialization
36*56888Ssklower  */
37*56888Ssklower idrp_init()
38*56888Ssklower {
39*56888Ssklower 	extern struct clnl_protosw clnl_protox[256];
40*56888Ssklower 
41*56888Ssklower 	idrp_isop.isop_next = idrp_isop.isop_prev = &idrp_isop;
42*56888Ssklower 	idrp_isop.isop_faddr = &idrp_isop.isop_sfaddr;
43*56888Ssklower 	idrp_isop.isop_laddr = &idrp_isop.isop_sladdr;
44*56888Ssklower 	idrp_isop.isop_sladdr = idrp_addrs[1];
45*56888Ssklower 	idrp_isop.isop_sfaddr = idrp_addrs[1];
46*56888Ssklower 	clnl_protox[ISO10747_IDRP].clnl_input = idrp_input;
47*56888Ssklower }
48*56888Ssklower 
49*56888Ssklower /*
50*56888Ssklower  * CALLED FROM:
51*56888Ssklower  * 	tpclnp_input().
52*56888Ssklower  * FUNCTION and ARGUMENTS:
53*56888Ssklower  * Take a packet (m) from clnp, strip off the clnp header
54*56888Ssklower  * and mke suitable for the idrp socket.
55*56888Ssklower  * No return value.
56*56888Ssklower  */
57*56888Ssklower idrp_input(m, src, dst)
58*56888Ssklower 	register struct mbuf *m;
59*56888Ssklower 	struct sockaddr_iso *src, *dst;
60*56888Ssklower {
61*56888Ssklower 	if (idrp_isop.isop_socket == 0) {
62*56888Ssklower 	bad:	m_freem(m);
63*56888Ssklower 		return 0;
64*56888Ssklower 	}
65*56888Ssklower 	bzero(idrp_addrs[0].siso_data, sizeof(idrp_addrs[0].siso_data));
66*56888Ssklower 	bcopy((caddr_t)&(src->siso_addr), (caddr_t)&idrp_addrs[0].siso_addr,
67*56888Ssklower 		1 + src->siso_nlen);
68*56888Ssklower 	bzero(idrp_addrs[1].siso_data, sizeof(idrp_addrs[1].siso_data));
69*56888Ssklower 	bcopy((caddr_t)&(dst->siso_addr), (caddr_t)&idrp_addrs[1].siso_addr,
70*56888Ssklower 		1 + dst->siso_nlen);
71*56888Ssklower 	if (sbappendaddr(&idrp_isop.isop_socket->so_rcv,
72*56888Ssklower 		(struct sockaddr *)idrp_addrs, m, (struct mbuf *)0) == 0)
73*56888Ssklower 		goto bad;
74*56888Ssklower 	sorwakeup(idrp_isop.isop_socket);
75*56888Ssklower 	return 0;
76*56888Ssklower }
77*56888Ssklower 
78*56888Ssklower idrp_output(m, addr)
79*56888Ssklower 	struct mbuf *m, *addr;
80*56888Ssklower {
81*56888Ssklower 	register struct sockaddr_iso *siso = mtod(addr, struct sockaddr_iso *);
82*56888Ssklower 	int s = splnet(), i;
83*56888Ssklower 
84*56888Ssklower 	bcopy((caddr_t)&(siso->siso_addr),
85*56888Ssklower 	      (caddr_t)&idrp_isop.isop_sfaddr.siso_addr, 1 + siso->siso_nlen);
86*56888Ssklower 	siso++;
87*56888Ssklower 	bcopy((caddr_t)&(siso->siso_addr),
88*56888Ssklower 	      (caddr_t)&idrp_isop.isop_sladdr.siso_addr, 1 + siso->siso_nlen);
89*56888Ssklower 	i = clnp_output(m, idrp_isop, m->m_pkthdr.len, 0);
90*56888Ssklower 	splx(s);
91*56888Ssklower 	return (i);
92*56888Ssklower }
93*56888Ssklower 
94*56888Ssklower u_long	idrp_sendspace = 3072;		/* really max datagram size */
95*56888Ssklower u_long	idrp_recvspace = 40 * 1024;	/* 40 1K datagrams */
96*56888Ssklower 
97*56888Ssklower /*ARGSUSED*/
98*56888Ssklower idrp_usrreq(so, req, m, addr, control)
99*56888Ssklower 	struct socket *so;
100*56888Ssklower 	int req;
101*56888Ssklower 	struct mbuf *m, *addr, *control;
102*56888Ssklower {
103*56888Ssklower 	int error = 0;
104*56888Ssklower 
105*56888Ssklower 	 /* Note: need to block idrp_input while changing
106*56888Ssklower 	 * the udp pcb queue and/or pcb addresses.
107*56888Ssklower 	 */
108*56888Ssklower 	switch (req) {
109*56888Ssklower 
110*56888Ssklower 	case PRU_ATTACH:
111*56888Ssklower 		if (idrp_isop.isop_socket != NULL) {
112*56888Ssklower 			error = ENXIO;
113*56888Ssklower 			break;
114*56888Ssklower 		}
115*56888Ssklower 		idrp_isop.isop_socket = so;
116*56888Ssklower 		error = soreserve(so, idrp_sendspace, idrp_recvspace);
117*56888Ssklower 		break;
118*56888Ssklower 
119*56888Ssklower 	case PRU_SHUTDOWN:
120*56888Ssklower 		socantsendmore(so);
121*56888Ssklower 		break;
122*56888Ssklower 
123*56888Ssklower 	case PRU_SEND:
124*56888Ssklower 		return (idrp_output(m, addr));
125*56888Ssklower 
126*56888Ssklower 	case PRU_ABORT:
127*56888Ssklower 		soisdisconnected(so);
128*56888Ssklower 	case PRU_DETACH:
129*56888Ssklower 		idrp_isop.isop_socket = 0;
130*56888Ssklower 		break;
131*56888Ssklower 
132*56888Ssklower 
133*56888Ssklower 	case PRU_SENSE:
134*56888Ssklower 		/*
135*56888Ssklower 		 * stat: don't bother with a blocksize.
136*56888Ssklower 		 */
137*56888Ssklower 		return (0);
138*56888Ssklower 
139*56888Ssklower 	default:
140*56888Ssklower 		return (EOPNOTSUPP);	/* do not free mbuf's */
141*56888Ssklower 	}
142*56888Ssklower 
143*56888Ssklower release:
144*56888Ssklower 	if (control) {
145*56888Ssklower 		printf("idrp control data unexpectedly retained\n");
146*56888Ssklower 		m_freem(control);
147*56888Ssklower 	}
148*56888Ssklower 	if (m)
149*56888Ssklower 		m_freem(m);
150*56888Ssklower 	return (error);
151*56888Ssklower }
152