Home | History | Annotate | Line # | Download | only in mrouted
kern.c revision 1.2
      1 /*
      2  * The mrouted program is covered by the license in the accompanying file
      3  * named "LICENSE".  Use of the mrouted program represents acceptance of
      4  * the terms and conditions listed in that file.
      5  *
      6  * The mrouted program is COPYRIGHT 1989 by The Board of Trustees of
      7  * Leland Stanford Junior University.
      8  *
      9  *
     10  * $Id: kern.c,v 1.2 1995/06/01 02:25:56 mycroft Exp $
     11  */
     12 
     13 
     14 #include "defs.h"
     15 
     16 
     17 void k_set_rcvbuf(bufsize)
     18     int bufsize;
     19 {
     20     if (setsockopt(igmp_socket, SOL_SOCKET, SO_RCVBUF,
     21 		   (char *)&bufsize, sizeof(bufsize)) < 0)
     22 	log(LOG_ERR, errno, "setsockopt SO_RCVBUF %u", bufsize);
     23 }
     24 
     25 
     26 void k_hdr_include(bool)
     27     int bool;
     28 {
     29 #ifdef IP_HDRINCL
     30     if (setsockopt(igmp_socket, IPPROTO_IP, IP_HDRINCL,
     31 		   (char *)&bool, sizeof(bool)) < 0)
     32 	log(LOG_ERR, errno, "setsockopt IP_HDRINCL %u", bool);
     33 #endif
     34 }
     35 
     36 
     37 void k_set_ttl(t)
     38     int t;
     39 {
     40     u_char ttl;
     41 
     42     ttl = t;
     43     if (setsockopt(igmp_socket, IPPROTO_IP, IP_MULTICAST_TTL,
     44 		   (char *)&ttl, sizeof(ttl)) < 0)
     45 	log(LOG_ERR, errno, "setsockopt IP_MULTICAST_TTL %u", ttl);
     46 }
     47 
     48 
     49 void k_set_loop(l)
     50     int l;
     51 {
     52     u_char loop;
     53 
     54     loop = l;
     55     if (setsockopt(igmp_socket, IPPROTO_IP, IP_MULTICAST_LOOP,
     56 		   (char *)&loop, sizeof(loop)) < 0)
     57 	log(LOG_ERR, errno, "setsockopt IP_MULTICAST_LOOP %u", loop);
     58 }
     59 
     60 
     61 void k_set_if(ifa)
     62     u_int32_t ifa;
     63 {
     64     struct in_addr adr;
     65 
     66     adr.s_addr = ifa;
     67     if (setsockopt(igmp_socket, IPPROTO_IP, IP_MULTICAST_IF,
     68 		   (char *)&adr, sizeof(adr)) < 0)
     69 	log(LOG_ERR, errno, "setsockopt IP_MULTICAST_IF %s",
     70 	    		    inet_fmt(ifa, s1));
     71 }
     72 
     73 
     74 void k_join(grp, ifa)
     75     u_int32_t grp;
     76     u_int32_t ifa;
     77 {
     78     struct ip_mreq mreq;
     79 
     80     mreq.imr_multiaddr.s_addr = grp;
     81     mreq.imr_interface.s_addr = ifa;
     82 
     83     if (setsockopt(igmp_socket, IPPROTO_IP, IP_ADD_MEMBERSHIP,
     84 		   (char *)&mreq, sizeof(mreq)) < 0)
     85 	log(LOG_WARNING, errno, "can't join group %s on interface %s",
     86 				inet_fmt(grp, s1), inet_fmt(ifa, s2));
     87 }
     88 
     89 
     90 void k_leave(grp, ifa)
     91     u_int32_t grp;
     92     u_int32_t ifa;
     93 {
     94     struct ip_mreq mreq;
     95 
     96     mreq.imr_multiaddr.s_addr = grp;
     97     mreq.imr_interface.s_addr = ifa;
     98 
     99     if (setsockopt(igmp_socket, IPPROTO_IP, IP_DROP_MEMBERSHIP,
    100 		   (char *)&mreq, sizeof(mreq)) < 0)
    101 	log(LOG_WARNING, errno, "can't leave group %s on interface %s",
    102 				inet_fmt(grp, s1), inet_fmt(ifa, s2));
    103 }
    104 
    105 
    106 void k_init_dvmrp()
    107 {
    108 #ifdef OLD_KERNEL
    109     if (setsockopt(igmp_socket, IPPROTO_IP, MRT_INIT,
    110 		   (char *)NULL, 0) < 0)
    111 #else
    112     int v=1;
    113 
    114     if (setsockopt(igmp_socket, IPPROTO_IP, MRT_INIT,
    115 		   (char *)&v, sizeof(int)) < 0)
    116 #endif
    117 	log(LOG_ERR, errno, "can't enable Multicast routing in kernel");
    118 }
    119 
    120 
    121 void k_stop_dvmrp()
    122 {
    123     if (setsockopt(igmp_socket, IPPROTO_IP, MRT_DONE,
    124 		   (char *)NULL, 0) < 0)
    125 	log(LOG_WARNING, errno, "can't disable Multicast routing in kernel");
    126 }
    127 
    128 
    129 void k_add_vif(vifi, v)
    130     vifi_t vifi;
    131     struct uvif *v;
    132 {
    133     struct vifctl vc;
    134 
    135     vc.vifc_vifi            = vifi;
    136     vc.vifc_flags           = v->uv_flags & VIFF_KERNEL_FLAGS;
    137     vc.vifc_threshold       = v->uv_threshold;
    138     vc.vifc_rate_limit	    = v->uv_rate_limit;
    139     vc.vifc_lcl_addr.s_addr = v->uv_lcl_addr;
    140     vc.vifc_rmt_addr.s_addr = v->uv_rmt_addr;
    141 
    142     if (setsockopt(igmp_socket, IPPROTO_IP, MRT_ADD_VIF,
    143 		   (char *)&vc, sizeof(vc)) < 0)
    144 	log(LOG_ERR, errno, "setsockopt MRT_ADD_VIF");
    145 }
    146 
    147 
    148 void k_del_vif(vifi)
    149     vifi_t vifi;
    150 {
    151     if (setsockopt(igmp_socket, IPPROTO_IP, MRT_DEL_VIF,
    152 		   (char *)&vifi, sizeof(vifi)) < 0)
    153 	log(LOG_ERR, errno, "setsockopt MRT_DEL_VIF");
    154 }
    155 
    156 
    157 /*
    158  * Adds a (source, mcastgrp) entry to the kernel
    159  */
    160 void k_add_rg(origin, g)
    161     u_long origin;
    162     struct gtable *g;
    163 {
    164     struct mfcctl mc;
    165     int i;
    166 
    167     /* copy table values so that setsockopt can process it */
    168     mc.mfcc_origin.s_addr = origin;
    169 #ifdef OLD_KERNEL
    170     mc.mfcc_originmask.s_addr = 0xffffffff;
    171 #endif
    172     mc.mfcc_mcastgrp.s_addr = g->gt_mcastgrp;
    173     mc.mfcc_parent = g->gt_route ? g->gt_route->rt_parent : NO_VIF;
    174     for (i = 0; i < numvifs; i++)
    175 	mc.mfcc_ttls[i] = g->gt_ttls[i];
    176 
    177     /* write to kernel space */
    178     if (setsockopt(igmp_socket, IPPROTO_IP, MRT_ADD_MFC,
    179 		   (char *)&mc, sizeof(mc)) < 0)
    180 	log(LOG_WARNING, errno, "setsockopt MRT_ADD_MFC");
    181 }
    182 
    183 
    184 /*
    185  * Deletes a (source, mcastgrp) entry from the kernel
    186  */
    187 int k_del_rg(origin, g)
    188     u_long origin;
    189     struct gtable *g;
    190 {
    191     struct mfcctl mc;
    192     int retval, i;
    193 
    194     /* copy table values so that setsockopt can process it */
    195     mc.mfcc_origin.s_addr = origin;
    196 #ifdef OLD_KERNEL
    197     mc.mfcc_originmask.s_addr = 0xffffffff;
    198 #endif
    199     mc.mfcc_mcastgrp.s_addr = g->gt_mcastgrp;
    200 
    201     /* write to kernel space */
    202     if ((retval = setsockopt(igmp_socket, IPPROTO_IP, MRT_DEL_MFC,
    203 		   (char *)&mc, sizeof(mc))) < 0)
    204 	log(LOG_WARNING, errno, "setsockopt MRT_DEL_MFC");
    205 
    206     return retval;
    207 }
    208 
    209 /*
    210  * Get the kernel's idea of what version of mrouted needs to run with it.
    211  */
    212 int k_get_version()
    213 {
    214     int vers;
    215     int len = sizeof(vers);
    216 
    217     if (getsockopt(igmp_socket, IPPROTO_IP, MRT_VERSION,
    218 			(char *)&vers, &len) < 0)
    219 	log(LOG_ERR, errno,
    220 		"getsockopt MRT_VERSION: perhaps your kernel is too old");
    221 
    222     return vers;
    223 }
    224