2 * Copyright (c) 1990,1991 Regents of The University of Michigan.
12 #include <sys/types.h>
13 #include <sys/errno.h>
14 #include <sys/ioctl.h>
17 #include <sys/kernel.h>
19 #include <sys/socket.h>
20 #include <sys/socketvar.h>
23 #include <net/route.h>
24 #include <netinet/in.h>
26 #include <netinet/if_ether.h>
37 # define sateqaddr(a,b) ((a)->sat_len == (b)->sat_len && \
38 (a)->sat_family == (b)->sat_family && \
39 (a)->sat_addr.s_net == (b)->sat_addr.s_net && \
40 (a)->sat_addr.s_node == (b)->sat_addr.s_node )
43 struct sockaddr_at *sat;
46 hp->afh_nethash = sat->sat_addr.s_net;
47 hp->afh_hosthash = ( sat->sat_addr.s_net << 8 ) +
52 * Note the magic to get ifa_ifwithnet() to work without adding an
53 * ifaddr entry for each net in our local range.
55 atalk_netmatch( sat1, sat2 )
56 struct sockaddr_at *sat1, *sat2;
60 for ( aa = at_ifaddr; aa; aa = aa->aa_next ) {
61 if ( AA_SAT( aa ) == sat1 ) {
66 return( ntohs( aa->aa_firstnet ) <= ntohs( sat2->sat_addr.s_net ) &&
67 ntohs( aa->aa_lastnet ) >= ntohs( sat2->sat_addr.s_net ));
69 return( sat1->sat_addr.s_net == sat2->sat_addr.s_net );
73 at_control( cmd, data, ifp )
78 struct ifreq *ifr = (struct ifreq *)data;
79 struct sockaddr_at *sat;
82 struct at_aliasreq *ifra = (struct at_aliasreq *)data;
83 struct at_ifaddr *aa0;
85 struct at_ifaddr *aa = 0;
90 for ( aa = at_ifaddr; aa; aa = aa->aa_next ) {
91 if ( aa->aa_ifp == ifp ) break;
99 if ( ifra->ifra_addr.sat_family == AF_APPLETALK ) {
100 for ( ; aa; aa = aa->aa_next ) {
101 if ( aa->aa_ifp == ifp &&
102 sateqaddr( &aa->aa_addr, &ifra->ifra_addr )) {
107 if ( cmd == SIOCDIFADDR && aa == 0 ) {
108 return( EADDRNOTAVAIL );
116 * What a great idea this is: Let's reverse the meaning of
119 if ( suser( u.u_cred, &u.u_acflag )) {
128 sat = satosat( &ifr->ifr_addr );
129 nr = (struct netrange *)sat->sat_zero;
130 if ( nr->nr_phase == 1 ) {
131 for ( ; aa; aa = aa->aa_next ) {
132 if ( aa->aa_ifp == ifp &&
133 ( aa->aa_flags & AFA_PHASE2 ) == 0 ) {
137 } else { /* default to phase 2 */
138 for ( ; aa; aa = aa->aa_next ) {
139 if ( aa->aa_ifp == ifp && ( aa->aa_flags & AFA_PHASE2 )) {
146 panic( "at_control" );
148 if ( aa == (struct at_ifaddr *) 0 ) {
149 m = m_getclr( M_WAIT, MT_IFADDR );
150 if ( m == (struct mbuf *)NULL ) {
154 if (( aa = at_ifaddr ) != NULL ) {
156 * Don't let the loopback be first, since the first
157 * address is the machine's default address for
160 if ( at_ifaddr->aa_ifp->if_flags & IFF_LOOPBACK ) {
161 aa = mtod( m, struct at_ifaddr *);
162 aa->aa_next = at_ifaddr;
165 for ( ; aa->aa_next; aa = aa->aa_next )
167 aa->aa_next = mtod( m, struct at_ifaddr *);
170 at_ifaddr = mtod( m, struct at_ifaddr *);
173 aa = mtod( m, struct at_ifaddr *);
175 if (( ifa = ifp->if_addrlist ) != NULL ) {
176 for ( ; ifa->ifa_next; ifa = ifa->ifa_next )
178 ifa->ifa_next = (struct ifaddr *)aa;
180 ifp->if_addrlist = (struct ifaddr *)aa;
184 aa->aa_ifa.ifa_addr = (struct sockaddr *)&aa->aa_addr;
185 aa->aa_ifa.ifa_dstaddr = (struct sockaddr *)&aa->aa_addr;
186 aa->aa_ifa.ifa_netmask = (struct sockaddr *)&aa->aa_netmask;
190 * Set/clear the phase 2 bit.
192 if ( nr->nr_phase == 1 ) {
193 aa->aa_flags &= ~AFA_PHASE2;
195 aa->aa_flags |= AFA_PHASE2;
204 sat = satosat( &ifr->ifr_addr );
205 nr = (struct netrange *)sat->sat_zero;
206 if ( nr->nr_phase == 1 ) {
207 for ( ; aa; aa = aa->aa_next ) {
208 if ( aa->aa_ifp == ifp &&
209 ( aa->aa_flags & AFA_PHASE2 ) == 0 ) {
213 } else { /* default to phase 2 */
214 for ( ; aa; aa = aa->aa_next ) {
215 if ( aa->aa_ifp == ifp && ( aa->aa_flags & AFA_PHASE2 )) {
221 if ( aa == (struct at_ifaddr *) 0 )
222 return( EADDRNOTAVAIL );
229 *(struct sockaddr_at *)&ifr->ifr_addr = aa->aa_addr;
231 ifr->ifr_addr = aa->aa_addr;
236 return( at_ifinit( ifp, aa, (struct sockaddr_at *)&ifr->ifr_addr ));
240 if ( sateqaddr( &ifra->ifra_addr, &aa->aa_addr )) {
243 return( at_ifinit( ifp, aa, (struct sockaddr_at *)&ifr->ifr_addr ));
247 if (( ifa = ifp->if_addrlist ) == (struct ifaddr *)aa ) {
248 ifp->if_addrlist = ifa->ifa_next;
250 while ( ifa->ifa_next && ( ifa->ifa_next != (struct ifaddr *)aa )) {
253 if ( ifa->ifa_next ) {
254 ifa->ifa_next = ((struct ifaddr *)aa)->ifa_next;
256 panic( "at_control" );
261 if ( aa0 == ( aa = at_ifaddr )) {
262 at_ifaddr = aa->aa_next;
264 while ( aa->aa_next && ( aa->aa_next != aa0 )) {
268 aa->aa_next = aa0->aa_next;
270 panic( "at_control" );
273 m_free( dtom( aa0 ));
278 if ( ifp == 0 || ifp->if_ioctl == 0 )
279 return( EOPNOTSUPP );
280 return( (*ifp->if_ioctl)( ifp, cmd, data ));
287 struct at_ifaddr *aa;
290 struct sockaddr_at netsat;
295 if ( aa->aa_flags & AFA_ROUTE ) {
297 if (( error = rtinit( &(aa->aa_ifa), RTM_DELETE,
298 ( ifp->if_flags & IFF_LOOPBACK ) ? RTF_HOST : 0 )) != 0 ) {
301 aa->aa_ifa.ifa_flags &= ~IFA_ROUTE;
303 if ( ifp->if_flags & IFF_LOOPBACK ) {
304 rtinit( &aa->aa_addr, &aa->aa_addr, SIOCDELRT, RTF_HOST );
306 bzero( &netsat, sizeof( struct sockaddr_at ));
307 netsat.sat_family = AF_APPLETALK;
308 netsat.sat_addr.s_node = ATADDR_ANYNODE;
311 * If the range is the full 0-fffe range, just use
314 if ( aa->aa_firstnet == htons( 0x0000 ) &&
315 aa->aa_lastnet == htons( 0xfffe )) {
316 netsat.sat_addr.s_net = 0;
317 rtinit((struct sockaddr *)&netsat, &aa->aa_addr,
320 for ( net = ntohs( aa->aa_firstnet );
321 net <= ntohs( aa->aa_lastnet ); net++ ) {
322 netsat.sat_addr.s_net = htons( net );
323 rtinit((struct sockaddr *)&netsat, &aa->aa_addr,
329 aa->aa_flags &= ~AFA_ROUTE;
334 extern struct timeval time;
336 at_ifinit( ifp, aa, sat )
338 struct at_ifaddr *aa;
339 struct sockaddr_at *sat;
341 struct netrange nr, onr;
343 struct sockaddr_at oldaddr;
345 struct sockaddr oldaddr;
347 struct sockaddr_at netaddr;
348 int s = splimp(), error = 0, i, j, netinc, nodeinc, nnets;
351 oldaddr = aa->aa_addr;
352 bzero( AA_SAT( aa ), sizeof( struct sockaddr_at ));
353 bcopy( sat->sat_zero, &nr, sizeof( struct netrange ));
354 nnets = ntohs( nr.nr_lastnet ) - ntohs( nr.nr_firstnet ) + 1;
356 onr.nr_firstnet = aa->aa_firstnet;
357 onr.nr_lastnet = aa->aa_lastnet;
358 aa->aa_firstnet = nr.nr_firstnet;
359 aa->aa_lastnet = nr.nr_lastnet;
362 * We could eliminate the need for a second phase 1 probe (post
363 * autoconf) if we check whether we're resetting the node. Note
364 * that phase 1 probes use only nodes, not net.node pairs. Under
365 * phase 2, both the net and node must be the same.
367 if ( ifp->if_flags & IFF_LOOPBACK ) {
369 AA_SAT( aa )->sat_len = sat->sat_len;
371 AA_SAT( aa )->sat_family = AF_APPLETALK;
372 AA_SAT( aa )->sat_addr.s_net = sat->sat_addr.s_net;
373 AA_SAT( aa )->sat_addr.s_node = sat->sat_addr.s_node;
375 aa->aa_flags |= AFA_PROBING;
376 AA_SAT( aa )->sat_family = AF_APPLETALK;
377 if ( aa->aa_flags & AFA_PHASE2 ) {
378 if ( sat->sat_addr.s_net == ATADDR_ANYNET ) {
380 net = ntohs( nr.nr_firstnet ) + time.tv_sec % ( nnets - 1 );
382 net = ntohs( nr.nr_firstnet );
385 if ( ntohs( sat->sat_addr.s_net ) < ntohs( nr.nr_firstnet ) ||
386 ntohs( sat->sat_addr.s_net ) > ntohs( nr.nr_lastnet )) {
387 aa->aa_addr = oldaddr;
388 aa->aa_firstnet = onr.nr_firstnet;
389 aa->aa_lastnet = onr.nr_lastnet;
392 net = ntohs( sat->sat_addr.s_net );
395 net = ntohs( sat->sat_addr.s_net );
398 if ( sat->sat_addr.s_node == ATADDR_ANYNODE ) {
399 AA_SAT( aa )->sat_addr.s_node = time.tv_sec;
401 AA_SAT( aa )->sat_addr.s_node = sat->sat_addr.s_node;
404 for ( i = nnets, netinc = 1; i > 0; net = ntohs( nr.nr_firstnet ) +
405 (( net - ntohs( nr.nr_firstnet ) + netinc ) % nnets ), i-- ) {
406 AA_SAT( aa )->sat_addr.s_net = htons( net );
408 for ( j = 0, nodeinc = time.tv_sec | 1; j < 256;
409 j++, AA_SAT( aa )->sat_addr.s_node += nodeinc ) {
410 if ( AA_SAT( aa )->sat_addr.s_node > 253 ||
411 AA_SAT( aa )->sat_addr.s_node < 1 ) {
415 timeout( aarpprobe, (caddr_t)ifp, hz / 5 );
417 if ( sleep( aa, PSLEP|PCATCH )) {
418 printf( "at_ifinit why did this happen?!\n" );
419 aa->aa_addr = oldaddr;
420 aa->aa_firstnet = onr.nr_firstnet;
421 aa->aa_lastnet = onr.nr_lastnet;
425 if (( aa->aa_flags & AFA_PROBING ) == 0 ) {
429 if (( aa->aa_flags & AFA_PROBING ) == 0 ) {
432 /* reset node for next network */
433 AA_SAT( aa )->sat_addr.s_node = time.tv_sec;
436 if ( aa->aa_flags & AFA_PROBING ) {
437 aa->aa_addr = oldaddr;
438 aa->aa_firstnet = onr.nr_firstnet;
439 aa->aa_lastnet = onr.nr_lastnet;
441 return( EADDRINUSE );
445 if ( ifp->if_ioctl &&
446 ( error = (*ifp->if_ioctl)( ifp, SIOCSIFADDR, aa ))) {
448 aa->aa_addr = oldaddr;
449 aa->aa_firstnet = onr.nr_firstnet;
450 aa->aa_lastnet = onr.nr_lastnet;
455 aa->aa_netmask.sat_len = 6;
456 aa->aa_netmask.sat_family = AF_APPLETALK;
457 aa->aa_netmask.sat_addr.s_net = 0xffff;
458 aa->aa_netmask.sat_addr.s_node = 0;
461 if ( ifp->if_flags & IFF_LOOPBACK ) {
463 rtinit( &aa->aa_addr, &aa->aa_addr, (int)SIOCADDRT,
466 error = rtinit( &(aa->aa_ifa), (int)RTM_ADD, RTF_HOST|RTF_UP );
471 * rtrequest looks for point-to-point links first. The
472 * broadaddr is in the same spot as the destaddr. So, if
473 * ATADDR_ANYNET is 0, and we don't fill in the broadaddr, we
474 * get 0.0 routed out the ether interface. So, initialize the
475 * broadaddr, even tho we don't use it.
477 * We *could* use the broadaddr field to reduce some of the
478 * sockaddr_at overloading that we've done. E.g. Just send
479 * to INTERFACE-NET.255, and have the kernel reroute that
480 * to broadaddr, which would be 0.255 for phase 2 interfaces,
481 * and IFACE-NET.255 for phase 1 interfaces.
483 ((struct sockaddr_at *)&aa->aa_broadaddr)->sat_addr.s_net =
485 ((struct sockaddr_at *)&aa->aa_broadaddr)->sat_addr.s_node =
488 bzero( &netaddr, sizeof( struct sockaddr_at ));
489 netaddr.sat_family = AF_APPLETALK;
490 netaddr.sat_addr.s_node = ATADDR_ANYNODE;
491 if (( aa->aa_flags & AFA_PHASE2 ) == 0 ) {
492 netaddr.sat_addr.s_net = AA_SAT( aa )->sat_addr.s_net;
493 rtinit((struct sockaddr *)&netaddr, &aa->aa_addr,
494 (int)SIOCADDRT, RTF_UP );
497 * If the range is the full 0-fffe range, just use
500 if ( aa->aa_firstnet == htons( 0x0000 ) &&
501 aa->aa_lastnet == htons( 0xfffe )) {
502 netaddr.sat_addr.s_net = 0;
503 rtinit((struct sockaddr *)&netaddr, &aa->aa_addr,
504 (int)SIOCADDRT, RTF_UP );
506 for ( net = ntohs( aa->aa_firstnet );
507 net <= ntohs( aa->aa_lastnet ); net++ ) {
508 netaddr.sat_addr.s_net = htons( net );
509 rtinit((struct sockaddr *)&netaddr, &aa->aa_addr,
510 (int)SIOCADDRT, RTF_UP );
515 error = rtinit( &(aa->aa_ifa), (int)RTM_ADD, RTF_UP );
519 aa->aa_addr = oldaddr;
520 aa->aa_firstnet = onr.nr_firstnet;
521 aa->aa_lastnet = onr.nr_lastnet;
527 aa->aa_ifa.ifa_flags |= IFA_ROUTE;
529 aa->aa_flags |= AFA_ROUTE;
535 struct sockaddr_at *sat;
537 struct at_ifaddr *aa;
539 if ( sat->sat_addr.s_node != ATADDR_BCAST ) {
542 if ( sat->sat_addr.s_net == 0 ) {
545 for ( aa = at_ifaddr; aa; aa = aa->aa_next ) {
546 if (( aa->aa_ifp->if_flags & IFF_BROADCAST ) &&
547 ( ntohs( sat->sat_addr.s_net ) >= ntohs( aa->aa_firstnet ) &&
548 ntohs( sat->sat_addr.s_net ) <= ntohs( aa->aa_lastnet ))) {
558 struct at_ifaddr *aa;
562 while ( aa = at_ifaddr ) {
565 at_ifaddr = aa->aa_next;
566 if (( ifa = ifp->if_addrlist ) == (struct ifaddr *)aa ) {
567 ifp->if_addrlist = ifa->ifa_next;
569 while ( ifa->ifa_next &&
570 ( ifa->ifa_next != (struct ifaddr *)aa )) {
573 if ( ifa->ifa_next ) {
574 ifa->ifa_next = ((struct ifaddr *)aa)->ifa_next;