Commit | Line | Data |
---|---|---|
af0b24db | 1 | /* if.c 4.24 82/11/13 */ |
1bfd8df7 BJ |
2 | |
3 | #include "../h/param.h" | |
4 | #include "../h/systm.h" | |
ee787340 | 5 | #include "../h/socket.h" |
72e4f44e | 6 | #include "../h/protosw.h" |
1bfd8df7 | 7 | #include "../net/if.h" |
ee787340 | 8 | #include "../net/af.h" |
1bfd8df7 | 9 | |
1e977657 BJ |
10 | int ifqmaxlen = IFQ_MAXLEN; |
11 | ||
ee787340 SL |
12 | /* |
13 | * Network interface utility routines. | |
14 | * | |
15 | * Routines with if_ifwith* names take sockaddr *'s as | |
16 | * parameters. Other routines take value parameters, | |
17 | * e.g. if_ifwithnet takes the network number. | |
18 | */ | |
19 | ||
85ce71f2 BJ |
20 | ifinit() |
21 | { | |
22 | register struct ifnet *ifp; | |
23 | ||
24 | for (ifp = ifnet; ifp; ifp = ifp->if_next) | |
1e977657 | 25 | if (ifp->if_init) { |
ee787340 | 26 | (*ifp->if_init)(ifp->if_unit); |
1e977657 BJ |
27 | if (ifp->if_snd.ifq_maxlen == 0) |
28 | ifp->if_snd.ifq_maxlen = ifqmaxlen; | |
29 | } | |
5248a70b | 30 | if_slowtimo(); |
85ce71f2 BJ |
31 | } |
32 | ||
14fa60f2 | 33 | #if vax |
ee787340 SL |
34 | /* |
35 | * Call each interface on a Unibus reset. | |
36 | */ | |
85ce71f2 BJ |
37 | ifubareset(uban) |
38 | int uban; | |
39 | { | |
40 | register struct ifnet *ifp; | |
41 | ||
42 | for (ifp = ifnet; ifp; ifp = ifp->if_next) | |
8af3ca7c BJ |
43 | if (ifp->if_reset) |
44 | (*ifp->if_reset)(uban); | |
85ce71f2 | 45 | } |
14fa60f2 | 46 | #endif |
85ce71f2 | 47 | |
ee787340 SL |
48 | /* |
49 | * Attach an interface to the | |
50 | * list of "active" interfaces. | |
51 | */ | |
405c9168 BJ |
52 | if_attach(ifp) |
53 | struct ifnet *ifp; | |
54 | { | |
c4af8b24 | 55 | register struct ifnet **p = &ifnet; |
405c9168 | 56 | |
c4af8b24 BJ |
57 | while (*p) |
58 | p = &((*p)->if_next); | |
59 | *p = ifp; | |
405c9168 BJ |
60 | } |
61 | ||
ee787340 SL |
62 | /* |
63 | * Locate an interface based on a complete address. | |
64 | */ | |
4ad99bae BJ |
65 | /*ARGSUSED*/ |
66 | struct ifnet * | |
ee787340 SL |
67 | if_ifwithaddr(addr) |
68 | struct sockaddr *addr; | |
1bfd8df7 BJ |
69 | { |
70 | register struct ifnet *ifp; | |
71 | ||
ee787340 SL |
72 | #define equal(a1, a2) \ |
73 | (bcmp((caddr_t)((a1)->sa_data), (caddr_t)((a2)->sa_data), 14) == 0) | |
74 | for (ifp = ifnet; ifp; ifp = ifp->if_next) { | |
75 | if (ifp->if_addr.sa_family != addr->sa_family) | |
76 | continue; | |
77 | if (equal(&ifp->if_addr, addr)) | |
78 | break; | |
79 | if ((ifp->if_flags & IFF_BROADCAST) && | |
80 | equal(&ifp->if_broadaddr, addr)) | |
1bfd8df7 | 81 | break; |
ee787340 | 82 | } |
1bfd8df7 BJ |
83 | return (ifp); |
84 | } | |
85 | ||
ee787340 SL |
86 | /* |
87 | * Find an interface on a specific network. If many, choice | |
88 | * is first found. | |
89 | */ | |
4ad99bae | 90 | struct ifnet * |
ee787340 SL |
91 | if_ifwithnet(addr) |
92 | register struct sockaddr *addr; | |
93 | { | |
94 | register struct ifnet *ifp; | |
14fa60f2 | 95 | register u_int af = addr->sa_family; |
e65dcd4c | 96 | register int (*netmatch)(); |
ee787340 | 97 | |
e65dcd4c SL |
98 | if (af >= AF_MAX) |
99 | return (0); | |
100 | netmatch = afswitch[af].af_netmatch; | |
ee787340 SL |
101 | for (ifp = ifnet; ifp; ifp = ifp->if_next) { |
102 | if (af != ifp->if_addr.sa_family) | |
103 | continue; | |
104 | if ((*netmatch)(addr, &ifp->if_addr)) | |
105 | break; | |
106 | } | |
107 | return (ifp); | |
108 | } | |
109 | ||
110 | /* | |
111 | * As above, but parameter is network number. | |
112 | */ | |
113 | struct ifnet * | |
114 | if_ifonnetof(net) | |
115 | register int net; | |
1bfd8df7 BJ |
116 | { |
117 | register struct ifnet *ifp; | |
1bfd8df7 | 118 | |
1bfd8df7 BJ |
119 | for (ifp = ifnet; ifp; ifp = ifp->if_next) |
120 | if (ifp->if_net == net) | |
121 | break; | |
1bfd8df7 BJ |
122 | return (ifp); |
123 | } | |
124 | ||
ee787340 SL |
125 | /* |
126 | * Find an interface using a specific address family | |
127 | */ | |
8a13b737 | 128 | struct ifnet * |
ee787340 SL |
129 | if_ifwithaf(af) |
130 | register int af; | |
8a13b737 | 131 | { |
ee787340 | 132 | register struct ifnet *ifp; |
8a13b737 | 133 | |
ee787340 SL |
134 | for (ifp = ifnet; ifp; ifp = ifp->if_next) |
135 | if (ifp->if_addr.sa_family == af) | |
136 | break; | |
137 | return (ifp); | |
8a13b737 | 138 | } |
f1b2fa5b | 139 | |
72e4f44e SL |
140 | /* |
141 | * Mark an interface down and notify protocols of | |
142 | * the transition. | |
af0b24db | 143 | * NOTE: must be called at splnet or eqivalent. |
72e4f44e SL |
144 | */ |
145 | if_down(ifp) | |
146 | register struct ifnet *ifp; | |
147 | { | |
5248a70b | 148 | |
72e4f44e SL |
149 | ifp->if_flags &= ~IFF_UP; |
150 | pfctlinput(PRC_IFDOWN, (caddr_t)&ifp->if_addr); | |
151 | } | |
de602274 SL |
152 | |
153 | /* | |
154 | * Handle interface watchdog timer routines. Called | |
155 | * from softclock, we decrement timers (if set) and | |
156 | * call the appropriate interface routine on expiration. | |
157 | */ | |
158 | if_slowtimo() | |
159 | { | |
160 | register struct ifnet *ifp; | |
161 | ||
af0b24db SL |
162 | for (ifp = ifnet; ifp; ifp = ifp->if_next) { |
163 | if (ifp->if_timer == 0 || --ifp->if_timer) | |
164 | continue; | |
165 | if (ifp->if_watchdog) | |
de602274 | 166 | (*ifp->if_watchdog)(ifp->if_unit); |
af0b24db | 167 | } |
6e7edb25 | 168 | timeout(if_slowtimo, (caddr_t)0, hz / IFNET_SLOWHZ); |
de602274 | 169 | } |