Commit | Line | Data |
---|---|---|
7e7de0c9 SL |
1 | #ifndef lint |
2 | static char sccsid[] = "@(#)output.c 4.1 %G%"; | |
3 | #endif | |
4 | ||
5 | /* | |
6 | * Routing Table Management Daemon | |
7 | */ | |
8 | #include "router.h" | |
9 | ||
10 | /* | |
11 | * Apply the function "f" to all non-passive | |
12 | * interfaces. If the interface supports the | |
13 | * use of broadcasting use it, otherwise address | |
14 | * the output to the known router. | |
15 | */ | |
16 | toall(f) | |
17 | int (*f)(); | |
18 | { | |
19 | register struct interface *ifp; | |
20 | register struct sockaddr *dst; | |
21 | extern struct interface *ifnet; | |
22 | ||
23 | for (ifp = ifnet; ifp; ifp = ifp->int_next) { | |
24 | if (ifp->int_flags & IFF_PASSIVE) | |
25 | continue; | |
26 | dst = ifp->int_flags & IFF_BROADCAST ? &ifp->int_broadaddr : | |
27 | ifp->int_flags & IFF_POINTOPOINT ? &ifp->int_dstaddr : | |
28 | &ifp->int_addr; | |
29 | (*f)(dst, ifp->int_flags & IFF_INTERFACE, ifp); | |
30 | } | |
31 | } | |
32 | ||
33 | /* | |
34 | * Output a preformed packet. | |
35 | */ | |
36 | /*ARGSUSED*/ | |
37 | sendmsg(dst, dontroute, ifp) | |
38 | struct sockaddr *dst; | |
39 | int dontroute; | |
40 | struct interface *ifp; | |
41 | { | |
42 | ||
43 | (*afswitch[dst->sa_family].af_output)(dontroute ? snoroute : s, | |
44 | dst, sizeof (struct rip)); | |
45 | TRACE_OUTPUT(ifp, dst, sizeof (struct rip)); | |
46 | } | |
47 | ||
48 | /* | |
49 | * Supply dst with the contents of the routing tables. | |
50 | * If this won't fit in one packet, chop it up into several. | |
51 | */ | |
52 | supply(dst, dontroute, ifp) | |
53 | struct sockaddr *dst; | |
54 | struct interface *ifp; | |
55 | { | |
56 | register struct rt_entry *rt; | |
57 | struct netinfo *n = msg->rip_nets; | |
58 | register struct rthash *rh; | |
59 | struct rthash *base = hosthash; | |
60 | int doinghost = 1, size; | |
61 | int (*output)() = afswitch[dst->sa_family].af_output; | |
62 | int sto = dontroute ? snoroute : s; | |
63 | ||
64 | msg->rip_cmd = RIPCMD_RESPONSE; | |
65 | again: | |
66 | for (rh = base; rh < &base[ROUTEHASHSIZ]; rh++) | |
67 | for (rt = rh->rt_forw; rt != (struct rt_entry *)rh; rt = rt->rt_forw) { | |
68 | size = (char *)n - packet; | |
69 | if (size > MAXPACKETSIZE - sizeof (struct netinfo)) { | |
70 | (*output)(sto, dst, size); | |
71 | TRACE_OUTPUT(ifp, dst, size); | |
72 | n = msg->rip_nets; | |
73 | } | |
74 | n->rip_dst = rt->rt_dst; | |
75 | n->rip_metric = min(rt->rt_metric + 1, HOPCNT_INFINITY); | |
76 | n++; | |
77 | } | |
78 | if (doinghost) { | |
79 | doinghost = 0; | |
80 | base = nethash; | |
81 | goto again; | |
82 | } | |
83 | if (n != msg->rip_nets) { | |
84 | size = (char *)n - packet; | |
85 | (*output)(sto, dst, size); | |
86 | TRACE_OUTPUT(ifp, dst, size); | |
87 | } | |
88 | } |