3 #include <sys/socket.h>
5 #include <sys/protosw.h>
6 #include <sys/domain.h>
9 #include <net/if_arp.h>
11 #include <net/route.h>
13 #include <net/netisr.h>
15 #include <sun/vddrv.h>
17 #include <netinet/in.h>
19 #include <netinet/if_ether.h>
21 #include <netatalk/at.h>
22 #include <netatalk/at_var.h>
23 #include <netatalk/ddp_var.h>
24 #include <netatalk/phase2.h>
30 VDMAGIC_USER, "netatalk"
33 struct ifqueue *atef_input();
37 extern u_char aarp_org_code[ 3 ];
38 extern u_char at_org_code[ 3 ];
41 * Entries in this table are inserted into the ether_families linked
42 * list at the beginnning. As such, they will be searched by the input
43 * and output routines opposite to the order here.
45 * In order to do both phase 1 and phase 2 during output, we have a
46 * special entry (the AF_APPLETALK entry) whose ethertype field is
47 * changed by the output function, to reflect the actual link layer
48 * to be used. This ether_family entry is never seen during Ethernet
49 * input, since the earlier entry captures all packets (it is seen
50 * during loopback input, in that the input function is called directly
51 * on loopback output).
53 struct ether_family ether_atalk[] = {
55 AF_APPLETALK, 0, /* Changed by atef_output() */
56 atef_input, atef_output, atintr,
64 atef_input, 0, atintr,
68 atef_input, 0, atintr,
71 int ether_atalkN = sizeof( ether_atalk ) / sizeof( ether_atalk[ 0 ] );
73 extern struct ether_family *ether_families;
75 extern int atalk_hash(), atalk_netmatch();
76 extern int null_hash(), null_netmatch();
78 xxxinit( cmd, vdd, vdi, vds )
84 struct ether_family *ef;
91 vdd->vdd_vdtab = (struct vdlinkage *)&atvdl;
94 * Register with the network-interface layer (ethernet).
96 for ( i = 0; i < ether_atalkN; i++ ) {
97 ether_register( ðer_atalk[ i ] );
101 * Register with the socket layer.
103 atalkdomain.dom_next = domains;
104 domains = &atalkdomain;
105 if ( atalkdomain.dom_init ) {
106 (*atalkdomain.dom_init)();
108 for ( pr = atalkdomain.dom_protosw;
109 pr < atalkdomain.dom_protoswNPROTOSW; pr++ ) {
116 * Cobble ourselves into the routing table.
118 afswitch[ AF_APPLETALK ].af_hash = atalk_hash;
119 afswitch[ AF_APPLETALK ].af_netmatch = atalk_netmatch;
124 * Make sure that there are no open appletalk sockets.
126 if ( ddpcb != NULL ) {
131 * There is no ether_unregister(), so we'll have to do it
134 for ( i = 0; i < ether_atalkN; i++ ) {
135 if ( ether_families == ðer_atalk[ i ] ) {
136 ether_families = ether_families->ef_next;
139 for ( ef = ether_families; ef->ef_next; ef = ef->ef_next ) {
140 if ( ef->ef_next == ðer_atalk[ i ] ) {
141 ef->ef_next = ef->ef_next->ef_next;
149 * Remove aarp timers and held packets.
154 * Remove AppleTalk interface addresses.
159 * Remove our routines from the routing table.
161 afswitch[ AF_APPLETALK ].af_hash = null_hash;
162 afswitch[ AF_APPLETALK ].af_netmatch = null_netmatch;
165 * Remove atalkdomain from the domains list.
166 * Unlikely, but someone may have registered after us.
168 if ( domains == &atalkdomain ) {
169 domains = domains->dom_next;
171 for ( dom = domains; dom->dom_next; dom = dom->dom_next ) {
172 if ( dom->dom_next == &atalkdomain ) {
173 dom->dom_next = dom->dom_next->dom_next;
188 * Input routine for netatalk on suns. There are five possible
189 * packets. First, packets received on the loopback interface
190 * are immediately sent to the phase 1 interrupt queue (this will
191 * have to change if we ever do a phase 2 only version). Second,
192 * IEEE802 packet are sent to either the aarpinput() routine or
193 * the phase 2 interrupt queue. Finally, DIX packets are sent
194 * to either aarpinput() or the phase 1 interrupt queue.
197 atef_input( ifp, m, header )
200 struct ether_header *header;
206 * Check first for LOOPBACK flag, since loopback code passes NULL for
209 if ( ifp->if_flags & IFF_LOOPBACK ) {
214 * Before SunOS 4.1, the ether_type was passed as is from the
215 * packet. After SunOS 4.1, the ether_type is swapped in
216 * do_protocol(), before the ether_family routines are called.
218 #if defined( sun ) && defined( i386 )
219 header->ether_type = ntohs( header->ether_type );
222 if ( header->ether_type <= ETHERMTU ) { /* IEEE802 */
224 * We need to remove the interface pointer from the beginning of this
225 * packet. We can't always use IF_ADJ(), since it can (and will,
226 * very often) MFREE() the first mbuf in our chain. If IF_ADJ()
227 * would free the first mbuf, we just advance our pointer to the
228 * next mbuf. Since our calling routine passes m by value, we're
229 * not actually losing m. Later, we don't need to put the interface
230 * pointer back on, since the caller still has it in its copy of m.
232 if ( m->m_len == sizeof( struct ifnet * )) {
240 * We can't call m_pullup(), since we need to preserve
243 if ( m->m_len < sizeof( struct llc )) {
244 printf( "atef_input size llc\n" );
245 ( n ) ? m_freem( n ) : m_freem( m );
248 bcopy( mtod( m, caddr_t ), &llc, sizeof( struct llc ));
249 if ( llc.llc_dsap != LLC_SNAP_LSAP || llc.llc_ssap != LLC_SNAP_LSAP ||
250 llc.llc_control != LLC_UI ) {
251 ( n ) ? m_freem( n ) : m_freem( m );
256 * See IF_ADJ() above. Here we prepend ifp to the mbuf chain. If we
257 * didn't remove it earlier, we don't replace it here.
260 m_adj( m, sizeof( struct llc ));
262 m_adj( m, sizeof( struct llc ) - sizeof( struct ifnet *));
263 if ( m->m_len < sizeof( struct ifnet * )) {
264 printf( "atef_input too small!\n" );
268 *mtod( m, struct ifnet ** ) = ifp;
271 if ( ntohs( llc.llc_ether_type ) == ETHERTYPE_AT &&
272 bcmp( llc.llc_org_code, at_org_code,
273 sizeof( at_org_code )) == 0 ) {
277 /* do we really want to pass m, here? what happened to n? XXX */
278 if ( ntohs( llc.llc_ether_type ) == ETHERTYPE_AARP &&
279 bcmp( llc.llc_org_code, aarp_org_code,
280 sizeof( aarp_org_code )) == 0 ) {
281 aarpinput( ifp, n ? n : m );
286 switch ( header->ether_type ) {
290 case ETHERTYPE_AARP :
296 ( n ) ? m_freem( n ) : m_freem( m );
301 * If the destination is on a 802.3 wire, do phase 2 encapsulation,
302 * adding the 802.2 and SNAP headers. Always fill in the edst with the
303 * ethernet address of the destination.
305 atef_output( dst, m, ifp, edst )
306 struct sockaddr_at *dst;
309 struct ether_addr *edst;
311 struct at_ifaddr *aa;
317 if ( !aarpresolve( ifp, m, dst, edst )) {
324 * ifaddr is the first thing in at_ifaddr
326 if (( aa = (struct at_ifaddr *)at_ifawithnet( dst, ifp->if_addrlist ))
333 * In the phase 2 case, we need to prepend an mbuf for the llc header.
334 * Since we must preserve the value of m, which is passed to us by
335 * value, we m_copy() the first mbuf, and use it for our llc header.
337 * We could worry about leaving space for the ether header, but
338 * since we'll have to go through all sorts of hoops, including a
339 * possibly large copy, there's really no sense.
341 if ( aa->aa_flags & AFA_PHASE2 ) {
342 if ( M_HASCL( m ) || m->m_off - MMINOFF < sizeof( struct llc )) {
343 if (( m0 = m_copy( m, 0, m->m_len )) == 0 ) {
347 if ( M_HASCL( m )) { /* m is a cluster */
354 m0->m_next = m->m_next;
356 m->m_off = MMAXOFF - sizeof( struct llc );
357 m->m_len = sizeof( struct llc );
359 m->m_off -= sizeof( struct llc );
360 m->m_len += sizeof( struct llc );
363 llc.llc_dsap = llc.llc_ssap = LLC_SNAP_LSAP;
364 llc.llc_control = LLC_UI;
365 bcopy( at_org_code, llc.llc_org_code, sizeof( at_org_code ));
366 llc.llc_ether_type = htons( ETHERTYPE_AT );
367 bcopy( &llc, mtod( m, caddr_t ), sizeof( struct llc ));
368 ether_atalk[ 0 ].ef_ethertype = EF_8023_TYPE;
371 ether_atalk[ 0 ].ef_ethertype = ETHERTYPE_AT;