]> CyberLeo.Net >> Repos - FreeBSD/FreeBSD.git/blob - sys/netinet/ip_mroute.c
This commit was generated by cvs2svn to compensate for changes in r94970,
[FreeBSD/FreeBSD.git] / sys / netinet / ip_mroute.c
1 /*
2  * IP multicast forwarding procedures
3  *
4  * Written by David Waitzman, BBN Labs, August 1988.
5  * Modified by Steve Deering, Stanford, February 1989.
6  * Modified by Mark J. Steiglitz, Stanford, May, 1991
7  * Modified by Van Jacobson, LBL, January 1993
8  * Modified by Ajit Thyagarajan, PARC, August 1993
9  * Modified by Bill Fenner, PARC, April 1995
10  *
11  * MROUTING Revision: 3.5
12  * $FreeBSD$
13  */
14
15 #include "opt_mrouting.h"
16 #include "opt_random_ip_id.h"
17
18 #include <sys/param.h>
19 #include <sys/systm.h>
20 #include <sys/malloc.h>
21 #include <sys/mbuf.h>
22 #include <sys/socket.h>
23 #include <sys/socketvar.h>
24 #include <sys/protosw.h>
25 #include <sys/time.h>
26 #include <sys/kernel.h>
27 #include <sys/sysctl.h>
28 #include <sys/sockio.h>
29 #include <sys/syslog.h>
30 #include <net/if.h>
31 #include <net/route.h>
32 #include <netinet/in.h>
33 #include <netinet/in_systm.h>
34 #include <netinet/ip.h>
35 #include <netinet/ip_var.h>
36 #include <netinet/in_var.h>
37 #include <netinet/igmp.h>
38 #include <netinet/ip_encap.h>
39 #include <netinet/ip_mroute.h>
40 #include <netinet/udp.h>
41 #include <machine/in_cksum.h>
42
43 #ifndef MROUTING
44 extern u_long   _ip_mcast_src(int vifi);
45 extern int      _ip_mforward(struct ip *ip, struct ifnet *ifp, struct mbuf *m,
46                     struct ip_moptions *imo);
47 extern int      _ip_mrouter_done(void);
48 extern int      _ip_mrouter_get(struct socket *so, struct sockopt *sopt);
49 extern int      _ip_mrouter_set(struct socket *so, struct sockopt *sopt);
50 extern int      _mrt_ioctl(int req, caddr_t data);
51
52 /*
53  * Dummy routines and globals used when multicast routing is not compiled in.
54  */
55
56 struct socket  *ip_mrouter  = NULL;
57 u_int           rsvpdebug = 0;
58
59 int
60 _ip_mrouter_set(so, sopt)
61         struct socket *so;
62         struct sockopt *sopt;
63 {
64         return(EOPNOTSUPP);
65 }
66
67 int (*ip_mrouter_set)(struct socket *, struct sockopt *) = _ip_mrouter_set;
68
69
70 int
71 _ip_mrouter_get(so, sopt)
72         struct socket *so;
73         struct sockopt *sopt;
74 {
75         return(EOPNOTSUPP);
76 }
77
78 int (*ip_mrouter_get)(struct socket *, struct sockopt *) = _ip_mrouter_get;
79
80 int
81 _ip_mrouter_done()
82 {
83         return(0);
84 }
85
86 int (*ip_mrouter_done)(void) = _ip_mrouter_done;
87
88 int
89 _ip_mforward(ip, ifp, m, imo)
90         struct ip *ip;
91         struct ifnet *ifp;
92         struct mbuf *m;
93         struct ip_moptions *imo;
94 {
95         return(0);
96 }
97
98 int (*ip_mforward)(struct ip *, struct ifnet *, struct mbuf *,
99                    struct ip_moptions *) = _ip_mforward;
100
101 int
102 _mrt_ioctl(int req, caddr_t data)
103 {
104         return EOPNOTSUPP;
105 }
106
107 int (*mrt_ioctl)(int, caddr_t) = _mrt_ioctl;
108
109 void
110 rsvp_input(m, off)              /* XXX must fixup manually */
111         struct mbuf *m;
112         int off;
113 {
114     /* Can still get packets with rsvp_on = 0 if there is a local member
115      * of the group to which the RSVP packet is addressed.  But in this
116      * case we want to throw the packet away.
117      */
118     if (!rsvp_on) {
119         m_freem(m);
120         return;
121     }
122  
123     if (ip_rsvpd != NULL) {
124         if (rsvpdebug)
125             printf("rsvp_input: Sending packet up old-style socket\n");
126         rip_input(m, off);
127         return;
128     }
129     /* Drop the packet */
130     m_freem(m);
131 }
132
133 int (*legal_vif_num)(int) = 0;
134
135 /*
136  * This should never be called, since IP_MULTICAST_VIF should fail, but
137  * just in case it does get called, the code a little lower in ip_output
138  * will assign the packet a local address.
139  */
140 u_long
141 _ip_mcast_src(int vifi) { return INADDR_ANY; }
142 u_long (*ip_mcast_src)(int) = _ip_mcast_src;
143
144 int
145 ip_rsvp_vif_init(so, sopt)
146     struct socket *so;
147     struct sockopt *sopt;
148 {
149     return(EINVAL);
150 }
151
152 int
153 ip_rsvp_vif_done(so, sopt)
154     struct socket *so;
155     struct sockopt *sopt;
156 {
157     return(EINVAL);
158 }
159
160 void
161 ip_rsvp_force_done(so)
162     struct socket *so;
163 {
164     return;
165 }
166
167 #else /* MROUTING */
168
169 #define M_HASCL(m)      ((m)->m_flags & M_EXT)
170
171 static MALLOC_DEFINE(M_MRTABLE, "mroutetbl", "multicast routing tables");
172
173 #ifndef MROUTE_KLD
174 /* The socket used to communicate with the multicast routing daemon.  */
175 struct socket  *ip_mrouter  = NULL;
176 #endif
177
178 #if defined(MROUTING) || defined(MROUTE_KLD)
179 static struct mrtstat   mrtstat;
180 SYSCTL_STRUCT(_net_inet_ip, OID_AUTO, mrtstat, CTLFLAG_RW,
181     &mrtstat, mrtstat, "Multicast Routing Statistics (struct mrtstat, netinet/ip_mroute.h)");
182 #endif
183
184 static struct mfc       *mfctable[MFCTBLSIZ];
185 static u_char           nexpire[MFCTBLSIZ];
186 static struct vif       viftable[MAXVIFS];
187 static u_int    mrtdebug = 0;     /* debug level        */
188 #define         DEBUG_MFC       0x02
189 #define         DEBUG_FORWARD   0x04
190 #define         DEBUG_EXPIRE    0x08
191 #define         DEBUG_XMIT      0x10
192 static u_int    tbfdebug = 0;     /* tbf debug level    */
193 static u_int    rsvpdebug = 0;    /* rsvp debug level   */
194
195 static struct callout_handle expire_upcalls_ch;
196
197 #define         EXPIRE_TIMEOUT  (hz / 4)        /* 4x / second          */
198 #define         UPCALL_EXPIRE   6               /* number of timeouts   */
199
200 /*
201  * Define the token bucket filter structures
202  * tbftable -> each vif has one of these for storing info 
203  */
204
205 static struct tbf tbftable[MAXVIFS];
206 #define         TBF_REPROCESS   (hz / 100)      /* 100x / second */
207
208 /*
209  * 'Interfaces' associated with decapsulator (so we can tell
210  * packets that went through it from ones that get reflected
211  * by a broken gateway).  These interfaces are never linked into
212  * the system ifnet list & no routes point to them.  I.e., packets
213  * can't be sent this way.  They only exist as a placeholder for
214  * multicast source verification.
215  */
216 static struct ifnet multicast_decap_if[MAXVIFS];
217
218 #define ENCAP_TTL 64
219 #define ENCAP_PROTO IPPROTO_IPIP        /* 4 */
220
221 /* prototype IP hdr for encapsulated packets */
222 static struct ip multicast_encap_iphdr = {
223 #if BYTE_ORDER == LITTLE_ENDIAN
224         sizeof(struct ip) >> 2, IPVERSION,
225 #else
226         IPVERSION, sizeof(struct ip) >> 2,
227 #endif
228         0,                              /* tos */
229         sizeof(struct ip),              /* total length */
230         0,                              /* id */
231         0,                              /* frag offset */
232         ENCAP_TTL, ENCAP_PROTO, 
233         0,                              /* checksum */
234 };
235
236 /*
237  * Private variables.
238  */
239 static vifi_t      numvifs = 0;
240 static const struct encaptab *encap_cookie = NULL;
241
242 /*
243  * one-back cache used by mroute_encapcheck to locate a tunnel's vif
244  * given a datagram's src ip address.
245  */
246 static u_long last_encap_src;
247 static struct vif *last_encap_vif;
248
249 static u_long   X_ip_mcast_src(int vifi);
250 static int      X_ip_mforward(struct ip *ip, struct ifnet *ifp, struct mbuf *m, struct ip_moptions *imo);
251 static int      X_ip_mrouter_done(void);
252 static int      X_ip_mrouter_get(struct socket *so, struct sockopt *m);
253 static int      X_ip_mrouter_set(struct socket *so, struct sockopt *m);
254 static int      X_legal_vif_num(int vif);
255 static int      X_mrt_ioctl(int cmd, caddr_t data);
256
257 static int get_sg_cnt(struct sioc_sg_req *);
258 static int get_vif_cnt(struct sioc_vif_req *);
259 static int ip_mrouter_init(struct socket *, int);
260 static int add_vif(struct vifctl *);
261 static int del_vif(vifi_t);
262 static int add_mfc(struct mfcctl *);
263 static int del_mfc(struct mfcctl *);
264 static int socket_send(struct socket *, struct mbuf *, struct sockaddr_in *);
265 static int set_assert(int);
266 static void expire_upcalls(void *);
267 static int ip_mdq(struct mbuf *, struct ifnet *, struct mfc *,
268                   vifi_t);
269 static void phyint_send(struct ip *, struct vif *, struct mbuf *);
270 static void encap_send(struct ip *, struct vif *, struct mbuf *);
271 static void tbf_control(struct vif *, struct mbuf *, struct ip *, u_long);
272 static void tbf_queue(struct vif *, struct mbuf *);
273 static void tbf_process_q(struct vif *);
274 static void tbf_reprocess_q(void *);
275 static int tbf_dq_sel(struct vif *, struct ip *);
276 static void tbf_send_packet(struct vif *, struct mbuf *);
277 static void tbf_update_tokens(struct vif *);
278 static int priority(struct vif *, struct ip *);
279
280 /*
281  * whether or not special PIM assert processing is enabled.
282  */
283 static int pim_assert;
284 /*
285  * Rate limit for assert notification messages, in usec
286  */
287 #define ASSERT_MSG_TIME         3000000
288
289 /*
290  * Hash function for a source, group entry
291  */
292 #define MFCHASH(a, g) MFCHASHMOD(((a) >> 20) ^ ((a) >> 10) ^ (a) ^ \
293                         ((g) >> 20) ^ ((g) >> 10) ^ (g))
294
295 /*
296  * Find a route for a given origin IP address and Multicast group address
297  * Type of service parameter to be added in the future!!!
298  */
299
300 #define MFCFIND(o, g, rt) { \
301         register struct mfc *_rt = mfctable[MFCHASH(o,g)]; \
302         rt = NULL; \
303         ++mrtstat.mrts_mfc_lookups; \
304         while (_rt) { \
305                 if ((_rt->mfc_origin.s_addr == o) && \
306                     (_rt->mfc_mcastgrp.s_addr == g) && \
307                     (_rt->mfc_stall == NULL)) { \
308                         rt = _rt; \
309                         break; \
310                 } \
311                 _rt = _rt->mfc_next; \
312         } \
313         if (rt == NULL) { \
314                 ++mrtstat.mrts_mfc_misses; \
315         } \
316 }
317
318
319 /*
320  * Macros to compute elapsed time efficiently
321  * Borrowed from Van Jacobson's scheduling code
322  */
323 #define TV_DELTA(a, b, delta) { \
324             register int xxs; \
325                 \
326             delta = (a).tv_usec - (b).tv_usec; \
327             if ((xxs = (a).tv_sec - (b).tv_sec)) { \
328                switch (xxs) { \
329                       case 2: \
330                           delta += 1000000; \
331                               /* fall through */ \
332                       case 1: \
333                           delta += 1000000; \
334                           break; \
335                       default: \
336                           delta += (1000000 * xxs); \
337                } \
338             } \
339 }
340
341 #define TV_LT(a, b) (((a).tv_usec < (b).tv_usec && \
342               (a).tv_sec <= (b).tv_sec) || (a).tv_sec < (b).tv_sec)
343
344 #ifdef UPCALL_TIMING
345 u_long upcall_data[51];
346 static void collate(struct timeval *);
347 #endif /* UPCALL_TIMING */
348
349
350 /*
351  * Handle MRT setsockopt commands to modify the multicast routing tables.
352  */
353 static int
354 X_ip_mrouter_set(so, sopt)
355         struct socket *so;
356         struct sockopt *sopt;
357 {
358         int     error, optval;
359         vifi_t  vifi;
360         struct  vifctl vifc;
361         struct  mfcctl mfc;
362
363         if (so != ip_mrouter && sopt->sopt_name != MRT_INIT)
364                 return (EPERM);
365
366         error = 0;
367         switch (sopt->sopt_name) {
368         case MRT_INIT:
369                 error = sooptcopyin(sopt, &optval, sizeof optval, 
370                                     sizeof optval);
371                 if (error)
372                         break;
373                 error = ip_mrouter_init(so, optval);
374                 break;
375
376         case MRT_DONE:
377                 error = ip_mrouter_done();
378                 break;
379
380         case MRT_ADD_VIF:
381                 error = sooptcopyin(sopt, &vifc, sizeof vifc, sizeof vifc);
382                 if (error)
383                         break;
384                 error = add_vif(&vifc);
385                 break;
386
387         case MRT_DEL_VIF:
388                 error = sooptcopyin(sopt, &vifi, sizeof vifi, sizeof vifi);
389                 if (error)
390                         break;
391                 error = del_vif(vifi);
392                 break;
393
394         case MRT_ADD_MFC:
395         case MRT_DEL_MFC:
396                 error = sooptcopyin(sopt, &mfc, sizeof mfc, sizeof mfc);
397                 if (error)
398                         break;
399                 if (sopt->sopt_name == MRT_ADD_MFC)
400                         error = add_mfc(&mfc);
401                 else
402                         error = del_mfc(&mfc);
403                 break;
404
405         case MRT_ASSERT:
406                 error = sooptcopyin(sopt, &optval, sizeof optval, 
407                                     sizeof optval);
408                 if (error)
409                         break;
410                 set_assert(optval);
411                 break;
412
413         default:
414                 error = EOPNOTSUPP;
415                 break;
416         }
417         return (error);
418 }
419
420 #ifndef MROUTE_KLD
421 int (*ip_mrouter_set)(struct socket *, struct sockopt *) = X_ip_mrouter_set;
422 #endif
423
424 /*
425  * Handle MRT getsockopt commands
426  */
427 static int
428 X_ip_mrouter_get(so, sopt)
429         struct socket *so;
430         struct sockopt *sopt;
431 {
432         int error;
433         static int version = 0x0305; /* !!! why is this here? XXX */
434
435         switch (sopt->sopt_name) {
436         case MRT_VERSION:
437                 error = sooptcopyout(sopt, &version, sizeof version);
438                 break;
439
440         case MRT_ASSERT:
441                 error = sooptcopyout(sopt, &pim_assert, sizeof pim_assert);
442                 break;
443         default:
444                 error = EOPNOTSUPP;
445                 break;
446         }
447         return (error);
448 }
449
450 #ifndef MROUTE_KLD
451 int (*ip_mrouter_get)(struct socket *, struct sockopt *) = X_ip_mrouter_get;
452 #endif
453
454 /*
455  * Handle ioctl commands to obtain information from the cache
456  */
457 static int
458 X_mrt_ioctl(cmd, data)
459     int cmd;
460     caddr_t data;
461 {
462     int error = 0;
463
464     switch (cmd) {
465         case (SIOCGETVIFCNT):
466             return (get_vif_cnt((struct sioc_vif_req *)data));
467             break;
468         case (SIOCGETSGCNT):
469             return (get_sg_cnt((struct sioc_sg_req *)data));
470             break;
471         default:
472             return (EINVAL);
473             break;
474     }
475     return error;
476 }
477
478 #ifndef MROUTE_KLD
479 int (*mrt_ioctl)(int, caddr_t) = X_mrt_ioctl;
480 #endif
481
482 /*
483  * returns the packet, byte, rpf-failure count for the source group provided
484  */
485 static int
486 get_sg_cnt(req)
487     register struct sioc_sg_req *req;
488 {
489     register struct mfc *rt;
490     int s;
491
492     s = splnet();
493     MFCFIND(req->src.s_addr, req->grp.s_addr, rt);
494     splx(s);
495     if (rt != NULL) {
496         req->pktcnt = rt->mfc_pkt_cnt;
497         req->bytecnt = rt->mfc_byte_cnt;
498         req->wrong_if = rt->mfc_wrong_if;
499     } else
500         req->pktcnt = req->bytecnt = req->wrong_if = 0xffffffff;
501
502     return 0;
503 }
504
505 /*
506  * returns the input and output packet and byte counts on the vif provided
507  */
508 static int
509 get_vif_cnt(req)
510     register struct sioc_vif_req *req;
511 {
512     register vifi_t vifi = req->vifi;
513
514     if (vifi >= numvifs) return EINVAL;
515
516     req->icount = viftable[vifi].v_pkt_in;
517     req->ocount = viftable[vifi].v_pkt_out;
518     req->ibytes = viftable[vifi].v_bytes_in;
519     req->obytes = viftable[vifi].v_bytes_out;
520
521     return 0;
522 }
523
524 /*
525  * Enable multicast routing
526  */
527 static int
528 ip_mrouter_init(so, version)
529         struct socket *so;
530         int version;
531 {
532     if (mrtdebug)
533         log(LOG_DEBUG,"ip_mrouter_init: so_type = %d, pr_protocol = %d\n",
534                 so->so_type, so->so_proto->pr_protocol);
535
536     if (so->so_type != SOCK_RAW ||
537         so->so_proto->pr_protocol != IPPROTO_IGMP) return EOPNOTSUPP;
538
539     if (version != 1)
540         return ENOPROTOOPT;
541
542     if (ip_mrouter != NULL) return EADDRINUSE;
543
544     ip_mrouter = so;
545
546     bzero((caddr_t)mfctable, sizeof(mfctable));
547     bzero((caddr_t)nexpire, sizeof(nexpire));
548
549     pim_assert = 0;
550
551     expire_upcalls_ch = timeout(expire_upcalls, (caddr_t)NULL, EXPIRE_TIMEOUT);
552
553     if (mrtdebug)
554         log(LOG_DEBUG, "ip_mrouter_init\n");
555
556     return 0;
557 }
558
559 /*
560  * Disable multicast routing
561  */
562 static int
563 X_ip_mrouter_done()
564 {
565     vifi_t vifi;
566     int i;
567     struct ifnet *ifp;
568     struct ifreq ifr;
569     struct mfc *rt;
570     struct rtdetq *rte;
571     int s;
572
573     s = splnet();
574
575     /*
576      * For each phyint in use, disable promiscuous reception of all IP
577      * multicasts.
578      */
579     for (vifi = 0; vifi < numvifs; vifi++) {
580         if (viftable[vifi].v_lcl_addr.s_addr != 0 &&
581             !(viftable[vifi].v_flags & VIFF_TUNNEL)) {
582             ((struct sockaddr_in *)&(ifr.ifr_addr))->sin_family = AF_INET;
583             ((struct sockaddr_in *)&(ifr.ifr_addr))->sin_addr.s_addr
584                                                                 = INADDR_ANY;
585             ifp = viftable[vifi].v_ifp;
586             if_allmulti(ifp, 0);
587         }
588     }
589     bzero((caddr_t)tbftable, sizeof(tbftable));
590     bzero((caddr_t)viftable, sizeof(viftable));
591     numvifs = 0;
592     pim_assert = 0;
593
594     untimeout(expire_upcalls, (caddr_t)NULL, expire_upcalls_ch);
595
596     /*
597      * Free all multicast forwarding cache entries.
598      */
599     for (i = 0; i < MFCTBLSIZ; i++) {
600         for (rt = mfctable[i]; rt != NULL; ) {
601             struct mfc *nr = rt->mfc_next;
602
603             for (rte = rt->mfc_stall; rte != NULL; ) {
604                 struct rtdetq *n = rte->next;
605
606                 m_freem(rte->m);
607                 free(rte, M_MRTABLE);
608                 rte = n;
609             }
610             free(rt, M_MRTABLE);
611             rt = nr;
612         }
613     }
614
615     bzero((caddr_t)mfctable, sizeof(mfctable));
616
617     /*
618      * Reset de-encapsulation cache
619      */
620     last_encap_src = 0;
621     last_encap_vif = NULL;
622     if (encap_cookie) {
623         encap_detach(encap_cookie);
624         encap_cookie = NULL;
625     }
626  
627     ip_mrouter = NULL;
628
629     splx(s);
630
631     if (mrtdebug)
632         log(LOG_DEBUG, "ip_mrouter_done\n");
633
634     return 0;
635 }
636
637 #ifndef MROUTE_KLD
638 int (*ip_mrouter_done)(void) = X_ip_mrouter_done;
639 #endif
640
641 /*
642  * Set PIM assert processing global
643  */
644 static int
645 set_assert(i)
646         int i;
647 {
648     if ((i != 1) && (i != 0))
649         return EINVAL;
650
651     pim_assert = i;
652
653     return 0;
654 }
655
656 /*
657  * Decide if a packet is from a tunnelled peer.
658  * Return 0 if not, 64 if so.
659  */
660 static int
661 mroute_encapcheck(const struct mbuf *m, int off, int proto, void *arg)
662 {
663     struct ip *ip = mtod(m, struct ip *);
664     int hlen = ip->ip_hl << 2;
665     register struct vif *vifp;
666
667     /*
668      * don't claim the packet if it's not to a multicast destination or if
669      * we don't have an encapsulating tunnel with the source.
670      * Note:  This code assumes that the remote site IP address
671      * uniquely identifies the tunnel (i.e., that this site has
672      * at most one tunnel with the remote site).
673      */
674     if (! IN_MULTICAST(ntohl(((struct ip *)((char *)ip + hlen))->ip_dst.s_addr))) {
675         return 0;
676     }
677     if (ip->ip_src.s_addr != last_encap_src) {
678         register struct vif *vife;
679         
680         vifp = viftable;
681         vife = vifp + numvifs;
682         last_encap_src = ip->ip_src.s_addr;
683         last_encap_vif = 0;
684         for ( ; vifp < vife; ++vifp)
685             if (vifp->v_rmt_addr.s_addr == ip->ip_src.s_addr) {
686                 if ((vifp->v_flags & (VIFF_TUNNEL|VIFF_SRCRT))
687                     == VIFF_TUNNEL)
688                     last_encap_vif = vifp;
689                 break;
690             }
691     }
692     if ((vifp = last_encap_vif) == 0) {
693         last_encap_src = 0;
694         return 0;
695     }
696     return 64;
697 }
698
699 /*
700  * De-encapsulate a packet and feed it back through ip input (this
701  * routine is called whenever IP gets a packet that mroute_encap_func()
702  * claimed).
703  */
704 static void
705 mroute_encap_input(struct mbuf *m, int off)
706 {
707     struct ip *ip = mtod(m, struct ip *);
708     int hlen = ip->ip_hl << 2;
709
710     if (hlen > sizeof(struct ip))
711       ip_stripoptions(m, (struct mbuf *) 0);
712     m->m_data += sizeof(struct ip);
713     m->m_len -= sizeof(struct ip);
714     m->m_pkthdr.len -= sizeof(struct ip);
715
716     m->m_pkthdr.rcvif = last_encap_vif->v_ifp;
717
718     (void) IF_HANDOFF(&ipintrq, m, NULL);
719         /*
720          * normally we would need a "schednetisr(NETISR_IP)"
721          * here but we were called by ip_input and it is going
722          * to loop back & try to dequeue the packet we just
723          * queued as soon as we return so we avoid the
724          * unnecessary software interrrupt.
725          */
726 }
727
728 extern struct domain inetdomain;
729 static struct protosw mroute_encap_protosw =
730 { SOCK_RAW,     &inetdomain,    IPPROTO_IPV4,   PR_ATOMIC|PR_ADDR,
731   mroute_encap_input,   0,      0,              rip_ctloutput,
732   0,
733   0,            0,              0,              0,
734   &rip_usrreqs
735 };
736
737 /*
738  * Add a vif to the vif table
739  */
740 static int
741 add_vif(vifcp)
742     register struct vifctl *vifcp;
743 {
744     register struct vif *vifp = viftable + vifcp->vifc_vifi;
745     static struct sockaddr_in sin = {sizeof sin, AF_INET};
746     struct ifaddr *ifa;
747     struct ifnet *ifp;
748     int error, s;
749     struct tbf *v_tbf = tbftable + vifcp->vifc_vifi;
750
751     if (vifcp->vifc_vifi >= MAXVIFS)  return EINVAL;
752     if (vifp->v_lcl_addr.s_addr != 0) return EADDRINUSE;
753
754     /* Find the interface with an address in AF_INET family */
755     sin.sin_addr = vifcp->vifc_lcl_addr;
756     ifa = ifa_ifwithaddr((struct sockaddr *)&sin);
757     if (ifa == 0) return EADDRNOTAVAIL;
758     ifp = ifa->ifa_ifp;
759
760     if (vifcp->vifc_flags & VIFF_TUNNEL) {
761         if ((vifcp->vifc_flags & VIFF_SRCRT) == 0) {
762                 /*
763                  * An encapsulating tunnel is wanted.  Tell
764                  * mroute_encap_input() to start paying attention
765                  * to encapsulated packets.
766                  */
767                 if (encap_cookie == NULL) {
768                         encap_cookie = encap_attach_func(AF_INET, -1,
769                                 mroute_encapcheck,
770                                 (struct protosw *)&mroute_encap_protosw, NULL);
771
772                         if (encap_cookie == NULL) {
773                                 printf("ip_mroute: unable to attach encap\n");
774                                 return (EIO);   /* XXX */
775                         }
776                         for (s = 0; s < MAXVIFS; ++s) {
777                                 multicast_decap_if[s].if_name = "mdecap";
778                                 multicast_decap_if[s].if_unit = s;
779                         }
780                 }
781                 /*
782                  * Set interface to fake encapsulator interface
783                  */
784                 ifp = &multicast_decap_if[vifcp->vifc_vifi];
785                 /*
786                  * Prepare cached route entry
787                  */
788                 bzero(&vifp->v_route, sizeof(vifp->v_route));
789         } else {
790             log(LOG_ERR, "source routed tunnels not supported\n");
791             return EOPNOTSUPP;
792         }
793     } else {
794         /* Make sure the interface supports multicast */
795         if ((ifp->if_flags & IFF_MULTICAST) == 0)
796             return EOPNOTSUPP;
797
798         /* Enable promiscuous reception of all IP multicasts from the if */
799         s = splnet();
800         error = if_allmulti(ifp, 1);
801         splx(s);
802         if (error)
803             return error;
804     }
805
806     s = splnet();
807     /* define parameters for the tbf structure */
808     vifp->v_tbf = v_tbf;
809     GET_TIME(vifp->v_tbf->tbf_last_pkt_t);
810     vifp->v_tbf->tbf_n_tok = 0;
811     vifp->v_tbf->tbf_q_len = 0;
812     vifp->v_tbf->tbf_max_q_len = MAXQSIZE;
813     vifp->v_tbf->tbf_q = vifp->v_tbf->tbf_t = NULL;
814
815     vifp->v_flags     = vifcp->vifc_flags;
816     vifp->v_threshold = vifcp->vifc_threshold;
817     vifp->v_lcl_addr  = vifcp->vifc_lcl_addr;
818     vifp->v_rmt_addr  = vifcp->vifc_rmt_addr;
819     vifp->v_ifp       = ifp;
820     /* scaling up here allows division by 1024 in critical code */
821     vifp->v_rate_limit= vifcp->vifc_rate_limit * 1024 / 1000;
822     vifp->v_rsvp_on   = 0;
823     vifp->v_rsvpd     = NULL;
824     /* initialize per vif pkt counters */
825     vifp->v_pkt_in    = 0;
826     vifp->v_pkt_out   = 0;
827     vifp->v_bytes_in  = 0;
828     vifp->v_bytes_out = 0;
829     splx(s);
830
831     /* Adjust numvifs up if the vifi is higher than numvifs */
832     if (numvifs <= vifcp->vifc_vifi) numvifs = vifcp->vifc_vifi + 1;
833
834     if (mrtdebug)
835         log(LOG_DEBUG, "add_vif #%d, lcladdr %lx, %s %lx, thresh %x, rate %d\n",
836             vifcp->vifc_vifi, 
837             (u_long)ntohl(vifcp->vifc_lcl_addr.s_addr),
838             (vifcp->vifc_flags & VIFF_TUNNEL) ? "rmtaddr" : "mask",
839             (u_long)ntohl(vifcp->vifc_rmt_addr.s_addr),
840             vifcp->vifc_threshold,
841             vifcp->vifc_rate_limit);    
842
843     return 0;
844 }
845
846 /*
847  * Delete a vif from the vif table
848  */
849 static int
850 del_vif(vifi)
851         vifi_t vifi;
852 {
853     register struct vif *vifp = &viftable[vifi];
854     register struct mbuf *m;
855     struct ifnet *ifp;
856     struct ifreq ifr;
857     int s;
858
859     if (vifi >= numvifs) return EINVAL;
860     if (vifp->v_lcl_addr.s_addr == 0) return EADDRNOTAVAIL;
861
862     s = splnet();
863
864     if (!(vifp->v_flags & VIFF_TUNNEL)) {
865         ((struct sockaddr_in *)&(ifr.ifr_addr))->sin_family = AF_INET;
866         ((struct sockaddr_in *)&(ifr.ifr_addr))->sin_addr.s_addr = INADDR_ANY;
867         ifp = vifp->v_ifp;
868         if_allmulti(ifp, 0);
869     }
870
871     if (vifp == last_encap_vif) {
872         last_encap_vif = 0;
873         last_encap_src = 0;
874     }
875
876     /*
877      * Free packets queued at the interface
878      */
879     while (vifp->v_tbf->tbf_q) {
880         m = vifp->v_tbf->tbf_q;
881         vifp->v_tbf->tbf_q = m->m_act;
882         m_freem(m);
883     }
884
885     bzero((caddr_t)vifp->v_tbf, sizeof(*(vifp->v_tbf)));
886     bzero((caddr_t)vifp, sizeof (*vifp));
887
888     if (mrtdebug)
889       log(LOG_DEBUG, "del_vif %d, numvifs %d\n", vifi, numvifs);
890
891     /* Adjust numvifs down */
892     for (vifi = numvifs; vifi > 0; vifi--)
893         if (viftable[vifi-1].v_lcl_addr.s_addr != 0) break;
894     numvifs = vifi;
895
896     splx(s);
897
898     return 0;
899 }
900
901 /*
902  * Add an mfc entry
903  */
904 static int
905 add_mfc(mfccp)
906     struct mfcctl *mfccp;
907 {
908     struct mfc *rt;
909     u_long hash;
910     struct rtdetq *rte;
911     register u_short nstl;
912     int s;
913     int i;
914
915     MFCFIND(mfccp->mfcc_origin.s_addr, mfccp->mfcc_mcastgrp.s_addr, rt);
916
917     /* If an entry already exists, just update the fields */
918     if (rt) {
919         if (mrtdebug & DEBUG_MFC)
920             log(LOG_DEBUG,"add_mfc update o %lx g %lx p %x\n",
921                 (u_long)ntohl(mfccp->mfcc_origin.s_addr),
922                 (u_long)ntohl(mfccp->mfcc_mcastgrp.s_addr),
923                 mfccp->mfcc_parent);
924
925         s = splnet();
926         rt->mfc_parent = mfccp->mfcc_parent;
927         for (i = 0; i < numvifs; i++)
928             rt->mfc_ttls[i] = mfccp->mfcc_ttls[i];
929         splx(s);
930         return 0;
931     }
932
933     /* 
934      * Find the entry for which the upcall was made and update
935      */
936     s = splnet();
937     hash = MFCHASH(mfccp->mfcc_origin.s_addr, mfccp->mfcc_mcastgrp.s_addr);
938     for (rt = mfctable[hash], nstl = 0; rt; rt = rt->mfc_next) {
939
940         if ((rt->mfc_origin.s_addr == mfccp->mfcc_origin.s_addr) &&
941             (rt->mfc_mcastgrp.s_addr == mfccp->mfcc_mcastgrp.s_addr) &&
942             (rt->mfc_stall != NULL)) {
943   
944             if (nstl++)
945                 log(LOG_ERR, "add_mfc %s o %lx g %lx p %x dbx %p\n",
946                     "multiple kernel entries",
947                     (u_long)ntohl(mfccp->mfcc_origin.s_addr),
948                     (u_long)ntohl(mfccp->mfcc_mcastgrp.s_addr),
949                     mfccp->mfcc_parent, (void *)rt->mfc_stall);
950
951             if (mrtdebug & DEBUG_MFC)
952                 log(LOG_DEBUG,"add_mfc o %lx g %lx p %x dbg %p\n",
953                     (u_long)ntohl(mfccp->mfcc_origin.s_addr),
954                     (u_long)ntohl(mfccp->mfcc_mcastgrp.s_addr),
955                     mfccp->mfcc_parent, (void *)rt->mfc_stall);
956
957             rt->mfc_origin     = mfccp->mfcc_origin;
958             rt->mfc_mcastgrp   = mfccp->mfcc_mcastgrp;
959             rt->mfc_parent     = mfccp->mfcc_parent;
960             for (i = 0; i < numvifs; i++)
961                 rt->mfc_ttls[i] = mfccp->mfcc_ttls[i];
962             /* initialize pkt counters per src-grp */
963             rt->mfc_pkt_cnt    = 0;
964             rt->mfc_byte_cnt   = 0;
965             rt->mfc_wrong_if   = 0;
966             rt->mfc_last_assert.tv_sec = rt->mfc_last_assert.tv_usec = 0;
967
968             rt->mfc_expire = 0; /* Don't clean this guy up */
969             nexpire[hash]--;
970
971             /* free packets Qed at the end of this entry */
972             for (rte = rt->mfc_stall; rte != NULL; ) {
973                 struct rtdetq *n = rte->next;
974
975                 ip_mdq(rte->m, rte->ifp, rt, -1);
976                 m_freem(rte->m);
977 #ifdef UPCALL_TIMING
978                 collate(&(rte->t));
979 #endif /* UPCALL_TIMING */
980                 free(rte, M_MRTABLE);
981                 rte = n;
982             }
983             rt->mfc_stall = NULL;
984         }
985     }
986
987     /*
988      * It is possible that an entry is being inserted without an upcall
989      */
990     if (nstl == 0) {
991         if (mrtdebug & DEBUG_MFC)
992             log(LOG_DEBUG,"add_mfc no upcall h %lu o %lx g %lx p %x\n",
993                 hash, (u_long)ntohl(mfccp->mfcc_origin.s_addr),
994                 (u_long)ntohl(mfccp->mfcc_mcastgrp.s_addr),
995                 mfccp->mfcc_parent);
996         
997         for (rt = mfctable[hash]; rt != NULL; rt = rt->mfc_next) {
998             
999             if ((rt->mfc_origin.s_addr == mfccp->mfcc_origin.s_addr) &&
1000                 (rt->mfc_mcastgrp.s_addr == mfccp->mfcc_mcastgrp.s_addr)) {
1001
1002                 rt->mfc_origin     = mfccp->mfcc_origin;
1003                 rt->mfc_mcastgrp   = mfccp->mfcc_mcastgrp;
1004                 rt->mfc_parent     = mfccp->mfcc_parent;
1005                 for (i = 0; i < numvifs; i++)
1006                     rt->mfc_ttls[i] = mfccp->mfcc_ttls[i];
1007                 /* initialize pkt counters per src-grp */
1008                 rt->mfc_pkt_cnt    = 0;
1009                 rt->mfc_byte_cnt   = 0;
1010                 rt->mfc_wrong_if   = 0;
1011                 rt->mfc_last_assert.tv_sec = rt->mfc_last_assert.tv_usec = 0;
1012                 if (rt->mfc_expire)
1013                     nexpire[hash]--;
1014                 rt->mfc_expire     = 0;
1015             }
1016         }
1017         if (rt == NULL) {
1018             /* no upcall, so make a new entry */
1019             rt = (struct mfc *)malloc(sizeof(*rt), M_MRTABLE, M_NOWAIT);
1020             if (rt == NULL) {
1021                 splx(s);
1022                 return ENOBUFS;
1023             }
1024             
1025             /* insert new entry at head of hash chain */
1026             rt->mfc_origin     = mfccp->mfcc_origin;
1027             rt->mfc_mcastgrp   = mfccp->mfcc_mcastgrp;
1028             rt->mfc_parent     = mfccp->mfcc_parent;
1029             for (i = 0; i < numvifs; i++)
1030                     rt->mfc_ttls[i] = mfccp->mfcc_ttls[i];
1031             /* initialize pkt counters per src-grp */
1032             rt->mfc_pkt_cnt    = 0;
1033             rt->mfc_byte_cnt   = 0;
1034             rt->mfc_wrong_if   = 0;
1035             rt->mfc_last_assert.tv_sec = rt->mfc_last_assert.tv_usec = 0;
1036             rt->mfc_expire     = 0;
1037             rt->mfc_stall      = NULL;
1038             
1039             /* link into table */
1040             rt->mfc_next = mfctable[hash];
1041             mfctable[hash] = rt;
1042         }
1043     }
1044     splx(s);
1045     return 0;
1046 }
1047
1048 #ifdef UPCALL_TIMING
1049 /*
1050  * collect delay statistics on the upcalls 
1051  */
1052 static void collate(t)
1053 register struct timeval *t;
1054 {
1055     register u_long d;
1056     register struct timeval tp;
1057     register u_long delta;
1058     
1059     GET_TIME(tp);
1060     
1061     if (TV_LT(*t, tp))
1062     {
1063         TV_DELTA(tp, *t, delta);
1064         
1065         d = delta >> 10;
1066         if (d > 50)
1067             d = 50;
1068         
1069         ++upcall_data[d];
1070     }
1071 }
1072 #endif /* UPCALL_TIMING */
1073
1074 /*
1075  * Delete an mfc entry
1076  */
1077 static int
1078 del_mfc(mfccp)
1079     struct mfcctl *mfccp;
1080 {
1081     struct in_addr      origin;
1082     struct in_addr      mcastgrp;
1083     struct mfc          *rt;
1084     struct mfc          **nptr;
1085     u_long              hash;
1086     int s;
1087
1088     origin = mfccp->mfcc_origin;
1089     mcastgrp = mfccp->mfcc_mcastgrp;
1090     hash = MFCHASH(origin.s_addr, mcastgrp.s_addr);
1091
1092     if (mrtdebug & DEBUG_MFC)
1093         log(LOG_DEBUG,"del_mfc orig %lx mcastgrp %lx\n",
1094             (u_long)ntohl(origin.s_addr), (u_long)ntohl(mcastgrp.s_addr));
1095
1096     s = splnet();
1097
1098     nptr = &mfctable[hash];
1099     while ((rt = *nptr) != NULL) {
1100         if (origin.s_addr == rt->mfc_origin.s_addr &&
1101             mcastgrp.s_addr == rt->mfc_mcastgrp.s_addr &&
1102             rt->mfc_stall == NULL)
1103             break;
1104
1105         nptr = &rt->mfc_next;
1106     }
1107     if (rt == NULL) {
1108         splx(s);
1109         return EADDRNOTAVAIL;
1110     }
1111
1112     *nptr = rt->mfc_next;
1113     free(rt, M_MRTABLE);
1114
1115     splx(s);
1116
1117     return 0;
1118 }
1119
1120 /*
1121  * Send a message to mrouted on the multicast routing socket
1122  */
1123 static int
1124 socket_send(s, mm, src)
1125         struct socket *s;
1126         struct mbuf *mm;
1127         struct sockaddr_in *src;
1128 {
1129         if (s) {
1130                 if (sbappendaddr(&s->so_rcv,
1131                                  (struct sockaddr *)src,
1132                                  mm, (struct mbuf *)0) != 0) {
1133                         sorwakeup(s);
1134                         return 0;
1135                 }
1136         }
1137         m_freem(mm);
1138         return -1;
1139 }
1140
1141 /*
1142  * IP multicast forwarding function. This function assumes that the packet
1143  * pointed to by "ip" has arrived on (or is about to be sent to) the interface
1144  * pointed to by "ifp", and the packet is to be relayed to other networks
1145  * that have members of the packet's destination IP multicast group.
1146  *
1147  * The packet is returned unscathed to the caller, unless it is
1148  * erroneous, in which case a non-zero return value tells the caller to
1149  * discard it.
1150  */
1151
1152 #define TUNNEL_LEN  12  /* # bytes of IP option for tunnel encapsulation  */
1153
1154 static int
1155 X_ip_mforward(ip, ifp, m, imo)
1156     register struct ip *ip;
1157     struct ifnet *ifp;
1158     struct mbuf *m;
1159     struct ip_moptions *imo;
1160 {
1161     register struct mfc *rt;
1162     register u_char *ipoptions;
1163     static struct sockaddr_in   k_igmpsrc       = { sizeof k_igmpsrc, AF_INET };
1164     static int srctun = 0;
1165     register struct mbuf *mm;
1166     int s;
1167     vifi_t vifi;
1168     struct vif *vifp;
1169
1170     if (mrtdebug & DEBUG_FORWARD)
1171         log(LOG_DEBUG, "ip_mforward: src %lx, dst %lx, ifp %p\n",
1172             (u_long)ntohl(ip->ip_src.s_addr), (u_long)ntohl(ip->ip_dst.s_addr),
1173             (void *)ifp);
1174
1175     if (ip->ip_hl < (sizeof(struct ip) + TUNNEL_LEN) >> 2 ||
1176         (ipoptions = (u_char *)(ip + 1))[1] != IPOPT_LSRR ) {
1177         /*
1178          * Packet arrived via a physical interface or
1179          * an encapsulated tunnel.
1180          */
1181     } else {
1182         /*
1183          * Packet arrived through a source-route tunnel.
1184          * Source-route tunnels are no longer supported.
1185          */
1186         if ((srctun++ % 1000) == 0)
1187             log(LOG_ERR,
1188                 "ip_mforward: received source-routed packet from %lx\n",
1189                 (u_long)ntohl(ip->ip_src.s_addr));
1190
1191         return 1;
1192     }
1193
1194     if ((imo) && ((vifi = imo->imo_multicast_vif) < numvifs)) {
1195         if (ip->ip_ttl < 255)
1196                 ip->ip_ttl++;   /* compensate for -1 in *_send routines */
1197         if (rsvpdebug && ip->ip_p == IPPROTO_RSVP) {
1198             vifp = viftable + vifi;
1199             printf("Sending IPPROTO_RSVP from %lx to %lx on vif %d (%s%s%d)\n",
1200                 (long)ntohl(ip->ip_src.s_addr), (long)ntohl(ip->ip_dst.s_addr),
1201                 vifi,
1202                 (vifp->v_flags & VIFF_TUNNEL) ? "tunnel on " : "",
1203                 vifp->v_ifp->if_name, vifp->v_ifp->if_unit);
1204         }
1205         return (ip_mdq(m, ifp, NULL, vifi));
1206     }
1207     if (rsvpdebug && ip->ip_p == IPPROTO_RSVP) {
1208         printf("Warning: IPPROTO_RSVP from %lx to %lx without vif option\n",
1209             (long)ntohl(ip->ip_src.s_addr), (long)ntohl(ip->ip_dst.s_addr));
1210         if(!imo)
1211                 printf("In fact, no options were specified at all\n");
1212     }
1213
1214     /*
1215      * Don't forward a packet with time-to-live of zero or one,
1216      * or a packet destined to a local-only group.
1217      */
1218     if (ip->ip_ttl <= 1 ||
1219         ntohl(ip->ip_dst.s_addr) <= INADDR_MAX_LOCAL_GROUP)
1220         return 0;
1221
1222     /*
1223      * Determine forwarding vifs from the forwarding cache table
1224      */
1225     s = splnet();
1226     MFCFIND(ip->ip_src.s_addr, ip->ip_dst.s_addr, rt);
1227
1228     /* Entry exists, so forward if necessary */
1229     if (rt != NULL) {
1230         splx(s);
1231         return (ip_mdq(m, ifp, rt, -1));
1232     } else {
1233         /*
1234          * If we don't have a route for packet's origin,
1235          * Make a copy of the packet &
1236          * send message to routing daemon
1237          */
1238
1239         register struct mbuf *mb0;
1240         register struct rtdetq *rte;
1241         register u_long hash;
1242         int hlen = ip->ip_hl << 2;
1243 #ifdef UPCALL_TIMING
1244         struct timeval tp;
1245
1246         GET_TIME(tp);
1247 #endif
1248
1249         mrtstat.mrts_no_route++;
1250         if (mrtdebug & (DEBUG_FORWARD | DEBUG_MFC))
1251             log(LOG_DEBUG, "ip_mforward: no rte s %lx g %lx\n",
1252                 (u_long)ntohl(ip->ip_src.s_addr),
1253                 (u_long)ntohl(ip->ip_dst.s_addr));
1254
1255         /*
1256          * Allocate mbufs early so that we don't do extra work if we are
1257          * just going to fail anyway.  Make sure to pullup the header so
1258          * that other people can't step on it.
1259          */
1260         rte = (struct rtdetq *)malloc((sizeof *rte), M_MRTABLE, M_NOWAIT);
1261         if (rte == NULL) {
1262             splx(s);
1263             return ENOBUFS;
1264         }
1265         mb0 = m_copy(m, 0, M_COPYALL);
1266         if (mb0 && (M_HASCL(mb0) || mb0->m_len < hlen))
1267             mb0 = m_pullup(mb0, hlen);
1268         if (mb0 == NULL) {
1269             free(rte, M_MRTABLE);
1270             splx(s);
1271             return ENOBUFS;
1272         }
1273
1274         /* is there an upcall waiting for this packet? */
1275         hash = MFCHASH(ip->ip_src.s_addr, ip->ip_dst.s_addr);
1276         for (rt = mfctable[hash]; rt; rt = rt->mfc_next) {
1277             if ((ip->ip_src.s_addr == rt->mfc_origin.s_addr) &&
1278                 (ip->ip_dst.s_addr == rt->mfc_mcastgrp.s_addr) &&
1279                 (rt->mfc_stall != NULL))
1280                 break;
1281         }
1282
1283         if (rt == NULL) {
1284             int i;
1285             struct igmpmsg *im;
1286
1287             /* no upcall, so make a new entry */
1288             rt = (struct mfc *)malloc(sizeof(*rt), M_MRTABLE, M_NOWAIT);
1289             if (rt == NULL) {
1290                 free(rte, M_MRTABLE);
1291                 m_freem(mb0);
1292                 splx(s);
1293                 return ENOBUFS;
1294             }
1295             /* Make a copy of the header to send to the user level process */
1296             mm = m_copy(mb0, 0, hlen);
1297             if (mm == NULL) {
1298                 free(rte, M_MRTABLE);
1299                 m_freem(mb0);
1300                 free(rt, M_MRTABLE);
1301                 splx(s);
1302                 return ENOBUFS;
1303             }
1304
1305             /* 
1306              * Send message to routing daemon to install 
1307              * a route into the kernel table
1308              */
1309             k_igmpsrc.sin_addr = ip->ip_src;
1310             
1311             im = mtod(mm, struct igmpmsg *);
1312             im->im_msgtype      = IGMPMSG_NOCACHE;
1313             im->im_mbz          = 0;
1314
1315             mrtstat.mrts_upcalls++;
1316
1317             if (socket_send(ip_mrouter, mm, &k_igmpsrc) < 0) {
1318                 log(LOG_WARNING, "ip_mforward: ip_mrouter socket queue full\n");
1319                 ++mrtstat.mrts_upq_sockfull;
1320                 free(rte, M_MRTABLE);
1321                 m_freem(mb0);
1322                 free(rt, M_MRTABLE);
1323                 splx(s);
1324                 return ENOBUFS;
1325             }
1326
1327             /* insert new entry at head of hash chain */
1328             rt->mfc_origin.s_addr     = ip->ip_src.s_addr;
1329             rt->mfc_mcastgrp.s_addr   = ip->ip_dst.s_addr;
1330             rt->mfc_expire            = UPCALL_EXPIRE;
1331             nexpire[hash]++;
1332             for (i = 0; i < numvifs; i++)
1333                 rt->mfc_ttls[i] = 0;
1334             rt->mfc_parent = -1;
1335
1336             /* link into table */
1337             rt->mfc_next   = mfctable[hash];
1338             mfctable[hash] = rt;
1339             rt->mfc_stall = rte;
1340
1341         } else {
1342             /* determine if q has overflowed */
1343             int npkts = 0;
1344             struct rtdetq **p;
1345
1346             for (p = &rt->mfc_stall; *p != NULL; p = &(*p)->next)
1347                 npkts++;
1348
1349             if (npkts > MAX_UPQ) {
1350                 mrtstat.mrts_upq_ovflw++;
1351                 free(rte, M_MRTABLE);
1352                 m_freem(mb0);
1353                 splx(s);
1354                 return 0;
1355             }
1356
1357             /* Add this entry to the end of the queue */
1358             *p = rte;
1359         }
1360
1361         rte->m                  = mb0;
1362         rte->ifp                = ifp;
1363 #ifdef UPCALL_TIMING
1364         rte->t                  = tp;
1365 #endif
1366         rte->next               = NULL;
1367
1368         splx(s);
1369
1370         return 0;
1371     }           
1372 }
1373
1374 #ifndef MROUTE_KLD
1375 int (*ip_mforward)(struct ip *, struct ifnet *, struct mbuf *,
1376                    struct ip_moptions *) = X_ip_mforward;
1377 #endif
1378
1379 /*
1380  * Clean up the cache entry if upcall is not serviced
1381  */
1382 static void
1383 expire_upcalls(void *unused)
1384 {
1385     struct rtdetq *rte;
1386     struct mfc *mfc, **nptr;
1387     int i;
1388     int s;
1389
1390     s = splnet();
1391     for (i = 0; i < MFCTBLSIZ; i++) {
1392         if (nexpire[i] == 0)
1393             continue;
1394         nptr = &mfctable[i];
1395         for (mfc = *nptr; mfc != NULL; mfc = *nptr) {
1396             /*
1397              * Skip real cache entries
1398              * Make sure it wasn't marked to not expire (shouldn't happen)
1399              * If it expires now
1400              */
1401             if (mfc->mfc_stall != NULL &&
1402                 mfc->mfc_expire != 0 &&
1403                 --mfc->mfc_expire == 0) {
1404                 if (mrtdebug & DEBUG_EXPIRE)
1405                     log(LOG_DEBUG, "expire_upcalls: expiring (%lx %lx)\n",
1406                         (u_long)ntohl(mfc->mfc_origin.s_addr),
1407                         (u_long)ntohl(mfc->mfc_mcastgrp.s_addr));
1408                 /*
1409                  * drop all the packets
1410                  * free the mbuf with the pkt, if, timing info
1411                  */
1412                 for (rte = mfc->mfc_stall; rte; ) {
1413                     struct rtdetq *n = rte->next;
1414
1415                     m_freem(rte->m);
1416                     free(rte, M_MRTABLE);
1417                     rte = n;
1418                 }
1419                 ++mrtstat.mrts_cache_cleanups;
1420                 nexpire[i]--;
1421
1422                 *nptr = mfc->mfc_next;
1423                 free(mfc, M_MRTABLE);
1424             } else {
1425                 nptr = &mfc->mfc_next;
1426             }
1427         }
1428     }
1429     splx(s);
1430     expire_upcalls_ch = timeout(expire_upcalls, (caddr_t)NULL, EXPIRE_TIMEOUT);
1431 }
1432
1433 /*
1434  * Packet forwarding routine once entry in the cache is made
1435  */
1436 static int
1437 ip_mdq(m, ifp, rt, xmt_vif)
1438     register struct mbuf *m;
1439     register struct ifnet *ifp;
1440     register struct mfc *rt;
1441     register vifi_t xmt_vif;
1442 {
1443     register struct ip  *ip = mtod(m, struct ip *);
1444     register vifi_t vifi;
1445     register struct vif *vifp;
1446     register int plen = ip->ip_len;
1447
1448 /*
1449  * Macro to send packet on vif.  Since RSVP packets don't get counted on
1450  * input, they shouldn't get counted on output, so statistics keeping is
1451  * separate.
1452  */
1453 #define MC_SEND(ip,vifp,m) {                             \
1454                 if ((vifp)->v_flags & VIFF_TUNNEL)       \
1455                     encap_send((ip), (vifp), (m));       \
1456                 else                                     \
1457                     phyint_send((ip), (vifp), (m));      \
1458 }
1459
1460     /*
1461      * If xmt_vif is not -1, send on only the requested vif.
1462      *
1463      * (since vifi_t is u_short, -1 becomes MAXUSHORT, which > numvifs.)
1464      */
1465     if (xmt_vif < numvifs) {
1466         MC_SEND(ip, viftable + xmt_vif, m);
1467         return 1;
1468     }
1469
1470     /*
1471      * Don't forward if it didn't arrive from the parent vif for its origin.
1472      */
1473     vifi = rt->mfc_parent;
1474     if ((vifi >= numvifs) || (viftable[vifi].v_ifp != ifp)) {
1475         /* came in the wrong interface */
1476         if (mrtdebug & DEBUG_FORWARD)
1477             log(LOG_DEBUG, "wrong if: ifp %p vifi %d vififp %p\n",
1478                 (void *)ifp, vifi, (void *)viftable[vifi].v_ifp); 
1479         ++mrtstat.mrts_wrong_if;
1480         ++rt->mfc_wrong_if;
1481         /*
1482          * If we are doing PIM assert processing, and we are forwarding
1483          * packets on this interface, and it is a broadcast medium
1484          * interface (and not a tunnel), send a message to the routing daemon.
1485          */
1486         if (pim_assert && rt->mfc_ttls[vifi] &&
1487                 (ifp->if_flags & IFF_BROADCAST) &&
1488                 !(viftable[vifi].v_flags & VIFF_TUNNEL)) {
1489             struct sockaddr_in k_igmpsrc;
1490             struct mbuf *mm;
1491             struct igmpmsg *im;
1492             int hlen = ip->ip_hl << 2;
1493             struct timeval now;
1494             register u_long delta;
1495
1496             GET_TIME(now);
1497
1498             TV_DELTA(rt->mfc_last_assert, now, delta);
1499
1500             if (delta > ASSERT_MSG_TIME) {
1501                 mm = m_copy(m, 0, hlen);
1502                 if (mm && (M_HASCL(mm) || mm->m_len < hlen))
1503                     mm = m_pullup(mm, hlen);
1504                 if (mm == NULL) {
1505                     return ENOBUFS;
1506                 }
1507
1508                 rt->mfc_last_assert = now;
1509
1510                 im = mtod(mm, struct igmpmsg *);
1511                 im->im_msgtype  = IGMPMSG_WRONGVIF;
1512                 im->im_mbz              = 0;
1513                 im->im_vif              = vifi;
1514
1515                 k_igmpsrc.sin_addr = im->im_src;
1516
1517                 socket_send(ip_mrouter, mm, &k_igmpsrc);
1518             }
1519         }
1520         return 0;
1521     }
1522
1523     /* If I sourced this packet, it counts as output, else it was input. */
1524     if (ip->ip_src.s_addr == viftable[vifi].v_lcl_addr.s_addr) {
1525         viftable[vifi].v_pkt_out++;
1526         viftable[vifi].v_bytes_out += plen;
1527     } else {
1528         viftable[vifi].v_pkt_in++;
1529         viftable[vifi].v_bytes_in += plen;
1530     }
1531     rt->mfc_pkt_cnt++;
1532     rt->mfc_byte_cnt += plen;
1533
1534     /*
1535      * For each vif, decide if a copy of the packet should be forwarded.
1536      * Forward if:
1537      *          - the ttl exceeds the vif's threshold
1538      *          - there are group members downstream on interface
1539      */
1540     for (vifp = viftable, vifi = 0; vifi < numvifs; vifp++, vifi++)
1541         if ((rt->mfc_ttls[vifi] > 0) &&
1542             (ip->ip_ttl > rt->mfc_ttls[vifi])) {
1543             vifp->v_pkt_out++;
1544             vifp->v_bytes_out += plen;
1545             MC_SEND(ip, vifp, m);
1546         }
1547
1548     return 0;
1549 }
1550
1551 /*
1552  * check if a vif number is legal/ok. This is used by ip_output, to export
1553  * numvifs there, 
1554  */
1555 static int
1556 X_legal_vif_num(vif)
1557     int vif;
1558 {
1559     if (vif >= 0 && vif < numvifs)
1560        return(1);
1561     else
1562        return(0);
1563 }
1564
1565 #ifndef MROUTE_KLD
1566 int (*legal_vif_num)(int) = X_legal_vif_num;
1567 #endif
1568
1569 /*
1570  * Return the local address used by this vif
1571  */
1572 static u_long
1573 X_ip_mcast_src(vifi)
1574     int vifi;
1575 {
1576     if (vifi >= 0 && vifi < numvifs)
1577         return viftable[vifi].v_lcl_addr.s_addr;
1578     else
1579         return INADDR_ANY;
1580 }
1581
1582 #ifndef MROUTE_KLD
1583 u_long (*ip_mcast_src)(int) = X_ip_mcast_src;
1584 #endif
1585
1586 static void
1587 phyint_send(ip, vifp, m)
1588     struct ip *ip;
1589     struct vif *vifp;
1590     struct mbuf *m;
1591 {
1592     register struct mbuf *mb_copy;
1593     register int hlen = ip->ip_hl << 2;
1594
1595     /*
1596      * Make a new reference to the packet; make sure that
1597      * the IP header is actually copied, not just referenced,
1598      * so that ip_output() only scribbles on the copy.
1599      */
1600     mb_copy = m_copy(m, 0, M_COPYALL);
1601     if (mb_copy && (M_HASCL(mb_copy) || mb_copy->m_len < hlen))
1602         mb_copy = m_pullup(mb_copy, hlen);
1603     if (mb_copy == NULL)
1604         return;
1605
1606     if (vifp->v_rate_limit == 0)
1607         tbf_send_packet(vifp, mb_copy);
1608     else
1609         tbf_control(vifp, mb_copy, mtod(mb_copy, struct ip *), ip->ip_len);
1610 }
1611
1612 static void
1613 encap_send(ip, vifp, m)
1614     register struct ip *ip;
1615     register struct vif *vifp;
1616     register struct mbuf *m;
1617 {
1618     register struct mbuf *mb_copy;
1619     register struct ip *ip_copy;
1620     register int i, len = ip->ip_len;
1621
1622     /*
1623      * copy the old packet & pullup its IP header into the
1624      * new mbuf so we can modify it.  Try to fill the new
1625      * mbuf since if we don't the ethernet driver will.
1626      */
1627     MGETHDR(mb_copy, M_DONTWAIT, MT_HEADER);
1628     if (mb_copy == NULL)
1629         return;
1630     mb_copy->m_data += max_linkhdr;
1631     mb_copy->m_len = sizeof(multicast_encap_iphdr);
1632
1633     if ((mb_copy->m_next = m_copy(m, 0, M_COPYALL)) == NULL) {
1634         m_freem(mb_copy);
1635         return;
1636     }
1637     i = MHLEN - M_LEADINGSPACE(mb_copy);
1638     if (i > len)
1639         i = len;
1640     mb_copy = m_pullup(mb_copy, i);
1641     if (mb_copy == NULL)
1642         return;
1643     mb_copy->m_pkthdr.len = len + sizeof(multicast_encap_iphdr);
1644
1645     /*
1646      * fill in the encapsulating IP header.
1647      */
1648     ip_copy = mtod(mb_copy, struct ip *);
1649     *ip_copy = multicast_encap_iphdr;
1650 #ifdef RANDOM_IP_ID
1651     ip_copy->ip_id = ip_randomid();
1652 #else
1653     ip_copy->ip_id = htons(ip_id++);
1654 #endif
1655     ip_copy->ip_len += len;
1656     ip_copy->ip_src = vifp->v_lcl_addr;
1657     ip_copy->ip_dst = vifp->v_rmt_addr;
1658
1659     /*
1660      * turn the encapsulated IP header back into a valid one.
1661      */
1662     ip = (struct ip *)((caddr_t)ip_copy + sizeof(multicast_encap_iphdr));
1663     --ip->ip_ttl;
1664     ip->ip_len = htons(ip->ip_len);
1665     ip->ip_off = htons(ip->ip_off);
1666     ip->ip_sum = 0;
1667     mb_copy->m_data += sizeof(multicast_encap_iphdr);
1668     ip->ip_sum = in_cksum(mb_copy, ip->ip_hl << 2);
1669     mb_copy->m_data -= sizeof(multicast_encap_iphdr);
1670
1671     if (vifp->v_rate_limit == 0)
1672         tbf_send_packet(vifp, mb_copy);
1673     else
1674         tbf_control(vifp, mb_copy, ip, ip_copy->ip_len);
1675 }
1676
1677 /*
1678  * Token bucket filter module
1679  */
1680
1681 static void
1682 tbf_control(vifp, m, ip, p_len)
1683         register struct vif *vifp;
1684         register struct mbuf *m;
1685         register struct ip *ip;
1686         register u_long p_len;
1687 {
1688     register struct tbf *t = vifp->v_tbf;
1689
1690     if (p_len > MAX_BKT_SIZE) {
1691         /* drop if packet is too large */
1692         mrtstat.mrts_pkt2large++;
1693         m_freem(m);
1694         return;
1695     }
1696
1697     tbf_update_tokens(vifp);
1698
1699     /* if there are enough tokens, 
1700      * and the queue is empty,
1701      * send this packet out
1702      */
1703
1704     if (t->tbf_q_len == 0) {
1705         /* queue empty, send packet if enough tokens */
1706         if (p_len <= t->tbf_n_tok) {
1707             t->tbf_n_tok -= p_len;
1708             tbf_send_packet(vifp, m);
1709         } else {
1710             /* queue packet and timeout till later */
1711             tbf_queue(vifp, m);
1712             timeout(tbf_reprocess_q, (caddr_t)vifp, TBF_REPROCESS);
1713         }
1714     } else if (t->tbf_q_len < t->tbf_max_q_len) {
1715         /* finite queue length, so queue pkts and process queue */
1716         tbf_queue(vifp, m);
1717         tbf_process_q(vifp);
1718     } else {
1719         /* queue length too much, try to dq and queue and process */
1720         if (!tbf_dq_sel(vifp, ip)) {
1721             mrtstat.mrts_q_overflow++;
1722             m_freem(m);
1723             return;
1724         } else {
1725             tbf_queue(vifp, m);
1726             tbf_process_q(vifp);
1727         }
1728     }
1729     return;
1730 }
1731
1732 /* 
1733  * adds a packet to the queue at the interface
1734  */
1735 static void
1736 tbf_queue(vifp, m) 
1737         register struct vif *vifp;
1738         register struct mbuf *m;
1739 {
1740     register int s = splnet();
1741     register struct tbf *t = vifp->v_tbf;
1742
1743     if (t->tbf_t == NULL) {
1744         /* Queue was empty */
1745         t->tbf_q = m;
1746     } else {
1747         /* Insert at tail */
1748         t->tbf_t->m_act = m;
1749     }
1750
1751     /* Set new tail pointer */
1752     t->tbf_t = m;
1753
1754 #ifdef DIAGNOSTIC
1755     /* Make sure we didn't get fed a bogus mbuf */
1756     if (m->m_act)
1757         panic("tbf_queue: m_act");
1758 #endif
1759     m->m_act = NULL;
1760
1761     t->tbf_q_len++;
1762
1763     splx(s);
1764 }
1765
1766
1767 /* 
1768  * processes the queue at the interface
1769  */
1770 static void
1771 tbf_process_q(vifp)
1772     register struct vif *vifp;
1773 {
1774     register struct mbuf *m;
1775     register int len;
1776     register int s = splnet();
1777     register struct tbf *t = vifp->v_tbf;
1778
1779     /* loop through the queue at the interface and send as many packets
1780      * as possible
1781      */
1782     while (t->tbf_q_len > 0) {
1783         m = t->tbf_q;
1784
1785         len = mtod(m, struct ip *)->ip_len;
1786
1787         /* determine if the packet can be sent */
1788         if (len <= t->tbf_n_tok) {
1789             /* if so,
1790              * reduce no of tokens, dequeue the packet,
1791              * send the packet.
1792              */
1793             t->tbf_n_tok -= len;
1794
1795             t->tbf_q = m->m_act;
1796             if (--t->tbf_q_len == 0)
1797                 t->tbf_t = NULL;
1798
1799             m->m_act = NULL;
1800             tbf_send_packet(vifp, m);
1801
1802         } else break;
1803     }
1804     splx(s);
1805 }
1806
1807 static void
1808 tbf_reprocess_q(xvifp)
1809         void *xvifp;
1810 {
1811     register struct vif *vifp = xvifp;
1812     if (ip_mrouter == NULL) 
1813         return;
1814
1815     tbf_update_tokens(vifp);
1816
1817     tbf_process_q(vifp);
1818
1819     if (vifp->v_tbf->tbf_q_len)
1820         timeout(tbf_reprocess_q, (caddr_t)vifp, TBF_REPROCESS);
1821 }
1822
1823 /* function that will selectively discard a member of the queue
1824  * based on the precedence value and the priority
1825  */
1826 static int
1827 tbf_dq_sel(vifp, ip)
1828     register struct vif *vifp;
1829     register struct ip *ip;
1830 {
1831     register int s = splnet();
1832     register u_int p;
1833     register struct mbuf *m, *last;
1834     register struct mbuf **np;
1835     register struct tbf *t = vifp->v_tbf;
1836
1837     p = priority(vifp, ip);
1838
1839     np = &t->tbf_q;
1840     last = NULL;
1841     while ((m = *np) != NULL) {
1842         if (p > priority(vifp, mtod(m, struct ip *))) {
1843             *np = m->m_act;
1844             /* If we're removing the last packet, fix the tail pointer */
1845             if (m == t->tbf_t)
1846                 t->tbf_t = last;
1847             m_freem(m);
1848             /* it's impossible for the queue to be empty, but
1849              * we check anyway. */
1850             if (--t->tbf_q_len == 0)
1851                 t->tbf_t = NULL;
1852             splx(s);
1853             mrtstat.mrts_drop_sel++;
1854             return(1);
1855         }
1856         np = &m->m_act;
1857         last = m;
1858     }
1859     splx(s);
1860     return(0);
1861 }
1862
1863 static void
1864 tbf_send_packet(vifp, m)
1865     register struct vif *vifp;
1866     register struct mbuf *m;
1867 {
1868     struct ip_moptions imo;
1869     int error;
1870     static struct route ro;
1871     int s = splnet();
1872
1873     if (vifp->v_flags & VIFF_TUNNEL) {
1874         /* If tunnel options */
1875         ip_output(m, (struct mbuf *)0, &vifp->v_route,
1876                   IP_FORWARDING, (struct ip_moptions *)0);
1877     } else {
1878         imo.imo_multicast_ifp  = vifp->v_ifp;
1879         imo.imo_multicast_ttl  = mtod(m, struct ip *)->ip_ttl - 1;
1880         imo.imo_multicast_loop = 1;
1881         imo.imo_multicast_vif  = -1;
1882
1883         /*
1884          * Re-entrancy should not be a problem here, because
1885          * the packets that we send out and are looped back at us
1886          * should get rejected because they appear to come from
1887          * the loopback interface, thus preventing looping.
1888          */
1889         error = ip_output(m, (struct mbuf *)0, &ro,
1890                           IP_FORWARDING, &imo);
1891
1892         if (mrtdebug & DEBUG_XMIT)
1893             log(LOG_DEBUG, "phyint_send on vif %d err %d\n", 
1894                 vifp - viftable, error);
1895     }
1896     splx(s);
1897 }
1898
1899 /* determine the current time and then
1900  * the elapsed time (between the last time and time now)
1901  * in milliseconds & update the no. of tokens in the bucket
1902  */
1903 static void
1904 tbf_update_tokens(vifp)
1905     register struct vif *vifp;
1906 {
1907     struct timeval tp;
1908     register u_long tm;
1909     register int s = splnet();
1910     register struct tbf *t = vifp->v_tbf;
1911
1912     GET_TIME(tp);
1913
1914     TV_DELTA(tp, t->tbf_last_pkt_t, tm);
1915
1916     /*
1917      * This formula is actually
1918      * "time in seconds" * "bytes/second".
1919      *
1920      * (tm / 1000000) * (v_rate_limit * 1000 * (1000/1024) / 8)
1921      *
1922      * The (1000/1024) was introduced in add_vif to optimize
1923      * this divide into a shift.
1924      */
1925     t->tbf_n_tok += tm * vifp->v_rate_limit / 1024 / 8;
1926     t->tbf_last_pkt_t = tp;
1927
1928     if (t->tbf_n_tok > MAX_BKT_SIZE)
1929         t->tbf_n_tok = MAX_BKT_SIZE;
1930
1931     splx(s);
1932 }
1933
1934 static int
1935 priority(vifp, ip)
1936     register struct vif *vifp;
1937     register struct ip *ip;
1938 {
1939     register int prio;
1940
1941     /* temporary hack; may add general packet classifier some day */
1942
1943     /*
1944      * The UDP port space is divided up into four priority ranges:
1945      * [0, 16384)     : unclassified - lowest priority
1946      * [16384, 32768) : audio - highest priority
1947      * [32768, 49152) : whiteboard - medium priority
1948      * [49152, 65536) : video - low priority
1949      */
1950     if (ip->ip_p == IPPROTO_UDP) {
1951         struct udphdr *udp = (struct udphdr *)(((char *)ip) + (ip->ip_hl << 2));
1952         switch (ntohs(udp->uh_dport) & 0xc000) {
1953             case 0x4000:
1954                 prio = 70;
1955                 break;
1956             case 0x8000:
1957                 prio = 60;
1958                 break;
1959             case 0xc000:
1960                 prio = 55;
1961                 break;
1962             default:
1963                 prio = 50;
1964                 break;
1965         }
1966         if (tbfdebug > 1)
1967                 log(LOG_DEBUG, "port %x prio%d\n", ntohs(udp->uh_dport), prio);
1968     } else {
1969             prio = 50;
1970     }
1971     return prio;
1972 }
1973
1974 /*
1975  * End of token bucket filter modifications 
1976  */
1977
1978 int
1979 ip_rsvp_vif_init(so, sopt)
1980         struct socket *so;
1981         struct sockopt *sopt;
1982 {
1983     int error, i, s;
1984
1985     if (rsvpdebug)
1986         printf("ip_rsvp_vif_init: so_type = %d, pr_protocol = %d\n",
1987                so->so_type, so->so_proto->pr_protocol);
1988
1989     if (so->so_type != SOCK_RAW || so->so_proto->pr_protocol != IPPROTO_RSVP)
1990         return EOPNOTSUPP;
1991
1992     /* Check mbuf. */
1993     error = sooptcopyin(sopt, &i, sizeof i, sizeof i);
1994     if (error)
1995             return (error);
1996  
1997     if (rsvpdebug)
1998         printf("ip_rsvp_vif_init: vif = %d rsvp_on = %d\n", i, rsvp_on);
1999  
2000     s = splnet();
2001
2002     /* Check vif. */
2003     if (!legal_vif_num(i)) {
2004         splx(s);
2005         return EADDRNOTAVAIL;
2006     }
2007
2008     /* Check if socket is available. */
2009     if (viftable[i].v_rsvpd != NULL) {
2010         splx(s);
2011         return EADDRINUSE;
2012     }
2013
2014     viftable[i].v_rsvpd = so;
2015     /* This may seem silly, but we need to be sure we don't over-increment
2016      * the RSVP counter, in case something slips up.
2017      */
2018     if (!viftable[i].v_rsvp_on) {
2019         viftable[i].v_rsvp_on = 1;
2020         rsvp_on++;
2021     }
2022
2023     splx(s);
2024     return 0;
2025 }
2026
2027 int
2028 ip_rsvp_vif_done(so, sopt)
2029         struct socket *so;
2030         struct sockopt *sopt;
2031 {
2032         int error, i, s;
2033  
2034         if (rsvpdebug)
2035                 printf("ip_rsvp_vif_done: so_type = %d, pr_protocol = %d\n",
2036                        so->so_type, so->so_proto->pr_protocol);
2037  
2038         if (so->so_type != SOCK_RAW || 
2039             so->so_proto->pr_protocol != IPPROTO_RSVP)
2040                 return EOPNOTSUPP;
2041  
2042         error = sooptcopyin(sopt, &i, sizeof i, sizeof i);
2043         if (error)
2044                 return (error);
2045  
2046         s = splnet();
2047  
2048         /* Check vif. */
2049         if (!legal_vif_num(i)) {
2050                 splx(s);
2051                 return EADDRNOTAVAIL;
2052         }
2053
2054         if (rsvpdebug)
2055                 printf("ip_rsvp_vif_done: v_rsvpd = %p so = %p\n",
2056                        viftable[i].v_rsvpd, so);
2057
2058         viftable[i].v_rsvpd = NULL;
2059         /*
2060          * This may seem silly, but we need to be sure we don't over-decrement
2061          * the RSVP counter, in case something slips up.
2062          */
2063         if (viftable[i].v_rsvp_on) {
2064                 viftable[i].v_rsvp_on = 0;
2065                 rsvp_on--;
2066         }
2067
2068         splx(s);
2069         return 0;
2070 }
2071
2072 void
2073 ip_rsvp_force_done(so)
2074     struct socket *so;
2075 {
2076     int vifi;
2077     register int s;
2078
2079     /* Don't bother if it is not the right type of socket. */
2080     if (so->so_type != SOCK_RAW || so->so_proto->pr_protocol != IPPROTO_RSVP)
2081         return;
2082
2083     s = splnet();
2084
2085     /* The socket may be attached to more than one vif...this
2086      * is perfectly legal.
2087      */
2088     for (vifi = 0; vifi < numvifs; vifi++) {
2089         if (viftable[vifi].v_rsvpd == so) {
2090             viftable[vifi].v_rsvpd = NULL;
2091             /* This may seem silly, but we need to be sure we don't
2092              * over-decrement the RSVP counter, in case something slips up.
2093              */
2094             if (viftable[vifi].v_rsvp_on) {
2095                 viftable[vifi].v_rsvp_on = 0;
2096                 rsvp_on--;
2097             }
2098         }
2099     }
2100
2101     splx(s);
2102     return;
2103 }
2104
2105 void
2106 rsvp_input(m, off)
2107         struct mbuf *m;
2108         int off;
2109 {
2110     int vifi;
2111     register struct ip *ip = mtod(m, struct ip *);
2112     static struct sockaddr_in rsvp_src = { sizeof rsvp_src, AF_INET };
2113     register int s;
2114     struct ifnet *ifp;
2115
2116     if (rsvpdebug)
2117         printf("rsvp_input: rsvp_on %d\n",rsvp_on);
2118
2119     /* Can still get packets with rsvp_on = 0 if there is a local member
2120      * of the group to which the RSVP packet is addressed.  But in this
2121      * case we want to throw the packet away.
2122      */
2123     if (!rsvp_on) {
2124         m_freem(m);
2125         return;
2126     }
2127
2128     s = splnet();
2129
2130     if (rsvpdebug)
2131         printf("rsvp_input: check vifs\n");
2132
2133 #ifdef DIAGNOSTIC
2134     if (!(m->m_flags & M_PKTHDR))
2135             panic("rsvp_input no hdr");
2136 #endif
2137
2138     ifp = m->m_pkthdr.rcvif;
2139     /* Find which vif the packet arrived on. */
2140     for (vifi = 0; vifi < numvifs; vifi++)
2141         if (viftable[vifi].v_ifp == ifp)
2142             break;
2143
2144     if (vifi == numvifs || viftable[vifi].v_rsvpd == NULL) {
2145         /*
2146          * If the old-style non-vif-associated socket is set,
2147          * then use it.  Otherwise, drop packet since there
2148          * is no specific socket for this vif.
2149          */
2150         if (ip_rsvpd != NULL) {
2151             if (rsvpdebug)
2152                 printf("rsvp_input: Sending packet up old-style socket\n");
2153             rip_input(m, off);  /* xxx */
2154         } else {
2155             if (rsvpdebug && vifi == numvifs)
2156                 printf("rsvp_input: Can't find vif for packet.\n");
2157             else if (rsvpdebug && viftable[vifi].v_rsvpd == NULL)
2158                 printf("rsvp_input: No socket defined for vif %d\n",vifi);
2159             m_freem(m);
2160         }
2161         splx(s);
2162         return;
2163     }
2164     rsvp_src.sin_addr = ip->ip_src;
2165
2166     if (rsvpdebug && m)
2167         printf("rsvp_input: m->m_len = %d, sbspace() = %ld\n",
2168                m->m_len,sbspace(&(viftable[vifi].v_rsvpd->so_rcv)));
2169
2170     if (socket_send(viftable[vifi].v_rsvpd, m, &rsvp_src) < 0) {
2171         if (rsvpdebug)
2172             printf("rsvp_input: Failed to append to socket\n");
2173     } else {
2174         if (rsvpdebug)
2175             printf("rsvp_input: send packet up\n");
2176     }
2177
2178     splx(s);
2179 }
2180
2181 #ifdef MROUTE_KLD
2182
2183 static int
2184 ip_mroute_modevent(module_t mod, int type, void *unused)
2185 {
2186         int s;
2187
2188         switch (type) {
2189                 static u_long (*old_ip_mcast_src)(int);
2190                 static int (*old_ip_mrouter_set)(struct socket *,
2191                         struct sockopt *);
2192                 static int (*old_ip_mrouter_get)(struct socket *,
2193                         struct sockopt *);
2194                 static int (*old_ip_mrouter_done)(void);
2195                 static int (*old_ip_mforward)(struct ip *, struct ifnet *,
2196                         struct mbuf *, struct ip_moptions *);
2197                 static int (*old_mrt_ioctl)(int, caddr_t);
2198                 static int (*old_legal_vif_num)(int);
2199
2200         case MOD_LOAD:
2201                 s = splnet();
2202                 /* XXX Protect against multiple loading */
2203                 old_ip_mcast_src = ip_mcast_src;
2204                 ip_mcast_src = X_ip_mcast_src;
2205                 old_ip_mrouter_get = ip_mrouter_get;
2206                 ip_mrouter_get = X_ip_mrouter_get;
2207                 old_ip_mrouter_set = ip_mrouter_set;
2208                 ip_mrouter_set = X_ip_mrouter_set;
2209                 old_ip_mrouter_done = ip_mrouter_done;
2210                 ip_mrouter_done = X_ip_mrouter_done;
2211                 old_ip_mforward = ip_mforward;
2212                 ip_mforward = X_ip_mforward;
2213                 old_mrt_ioctl = mrt_ioctl;
2214                 mrt_ioctl = X_mrt_ioctl;
2215                 old_legal_vif_num = legal_vif_num;
2216                 legal_vif_num = X_legal_vif_num;
2217
2218                 splx(s);
2219                 return 0;
2220
2221         case MOD_UNLOAD:
2222                 if (ip_mrouter)
2223                   return EINVAL;
2224
2225                 s = splnet();
2226                 ip_mrouter_get = old_ip_mrouter_get;
2227                 ip_mrouter_set = old_ip_mrouter_set;
2228                 ip_mrouter_done = old_ip_mrouter_done;
2229                 ip_mforward = old_ip_mforward;
2230                 mrt_ioctl = old_mrt_ioctl;
2231                 legal_vif_num = old_legal_vif_num;
2232                 splx(s);
2233                 return 0;
2234
2235         default:
2236                 break;
2237         }
2238         return 0;
2239 }
2240
2241 static moduledata_t ip_mroutemod = {
2242         "ip_mroute",
2243         ip_mroute_modevent,
2244         0
2245 };
2246 DECLARE_MODULE(ip_mroute, ip_mroutemod, SI_SUB_PSEUDO, SI_ORDER_ANY);
2247
2248 #endif /* MROUTE_KLD */
2249 #endif /* MROUTING */