File: | src/usr.sbin/dvmrpd/kmroute.c |
Warning: | line 97, column 7 Although the value stored to 'r' is used in the enclosing expression, the value is never actually read from 'r' |
Press '?' to see keyboard shortcuts
Keyboard shortcuts:
1 | /* $OpenBSD: kmroute.c,v 1.3 2019/06/28 13:32:47 deraadt Exp $ */ |
2 | |
3 | /* |
4 | * Copyright (c) 2005, 2006 Esben Norby <norby@openbsd.org> |
5 | * |
6 | * Permission to use, copy, modify, and distribute this software for any |
7 | * purpose with or without fee is hereby granted, provided that the above |
8 | * copyright notice and this permission notice appear in all copies. |
9 | * |
10 | * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES |
11 | * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF |
12 | * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR |
13 | * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES |
14 | * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN |
15 | * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF |
16 | * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. |
17 | */ |
18 | |
19 | #include <sys/types.h> |
20 | #include <sys/socket.h> |
21 | #include <netinet/in.h> |
22 | #include <arpa/inet.h> |
23 | #include <netinet/ip_mroute.h> |
24 | |
25 | #include <err.h> |
26 | #include <errno(*__errno()).h> |
27 | #include <stdlib.h> |
28 | #include <string.h> |
29 | |
30 | #include "igmp.h" |
31 | #include "dvmrpd.h" |
32 | #include "dvmrp.h" |
33 | #include "dvmrpe.h" |
34 | #include "log.h" |
35 | |
36 | extern struct dvmrpd_conf *conf; |
37 | char *mroute_ptr; /* packet buffer */ |
38 | |
39 | void main_imsg_compose_rde(int, pid_t, void *, u_int16_t); |
40 | |
41 | int |
42 | kmr_init(int fd) |
43 | { |
44 | struct iface *iface; |
45 | struct route_report rr; |
46 | |
47 | LIST_FOREACH(iface, &conf->iface_list, entry)for((iface) = ((&conf->iface_list)->lh_first); (iface )!= ((void *)0); (iface) = ((iface)->entry.le_next)) { |
48 | log_debug("kmr_init: interface %s", iface->name); |
49 | |
50 | rr.net.s_addr = iface->addr.s_addr & iface->mask.s_addr; |
51 | rr.mask = iface->mask; |
52 | rr.nexthop.s_addr = 0; |
53 | rr.metric = iface->metric; |
54 | rr.ifindex = iface->ifindex; |
55 | main_imsg_compose_rde(IMSG_ROUTE_REPORT, -1, &rr, sizeof(rr)); |
56 | |
57 | mrt_add_vif(conf->mroute_socket, iface); |
58 | } |
59 | |
60 | if ((mroute_ptr = calloc(1, IBUF_READ_SIZE65535)) == NULL((void *)0)) |
61 | fatal("kmr_init"); |
62 | |
63 | return (0); |
64 | } |
65 | |
66 | void |
67 | kmr_shutdown(void) |
68 | { |
69 | struct iface *iface; |
70 | |
71 | kmr_mfc_decouple(); |
72 | kmroute_clear(); |
73 | |
74 | LIST_FOREACH(iface, &conf->iface_list, entry)for((iface) = ((&conf->iface_list)->lh_first); (iface )!= ((void *)0); (iface) = ((iface)->entry.le_next)) { |
75 | log_debug("kmr_shutdown: interface %s", iface->name); |
76 | |
77 | mrt_del_vif(conf->mroute_socket, iface); |
78 | } |
79 | |
80 | free(mroute_ptr); |
81 | } |
82 | |
83 | void |
84 | kmr_recv_msg(int fd, short event, void *bula) |
85 | { |
86 | struct mfc mfc; |
87 | struct igmpmsg kernel_msg; |
88 | char *buf; |
89 | ssize_t r; |
90 | |
91 | if (event != EV_READ0x02) |
92 | return; |
93 | |
94 | /* setup buffer */ |
95 | buf = mroute_ptr; |
96 | |
97 | if ((r = recvfrom(fd, buf, IBUF_READ_SIZE65535, 0, NULL((void *)0), NULL((void *)0))) == -1) { |
Although the value stored to 'r' is used in the enclosing expression, the value is never actually read from 'r' | |
98 | if (errno(*__errno()) != EAGAIN35 && errno(*__errno()) != EINTR4) |
99 | log_debug("kmr_recv_msg: error receiving packet"); |
100 | return; |
101 | } |
102 | |
103 | memcpy(&kernel_msg, buf, sizeof(kernel_msg)); |
104 | |
105 | /* we are only interested in kernel messages */ |
106 | if (kernel_msg.im_mbz != 0) |
107 | return; |
108 | |
109 | switch (kernel_msg.im_msgtype) { |
110 | case IGMPMSG_NOCACHE1: |
111 | /* verify that dst is a multicast group */ |
112 | if (!IN_MULTICAST(ntohl(kernel_msg.im_dst.s_addr))(((u_int32_t)((__uint32_t)(__builtin_constant_p(kernel_msg.im_dst .s_addr) ? (__uint32_t)(((__uint32_t)(kernel_msg.im_dst.s_addr ) & 0xff) << 24 | ((__uint32_t)(kernel_msg.im_dst.s_addr ) & 0xff00) << 8 | ((__uint32_t)(kernel_msg.im_dst. s_addr) & 0xff0000) >> 8 | ((__uint32_t)(kernel_msg .im_dst.s_addr) & 0xff000000) >> 24) : __swap32md(kernel_msg .im_dst.s_addr))) & ((u_int32_t)(0xf0000000))) == ((u_int32_t )(0xe0000000)))) { |
113 | log_debug("kmr_recv_msg: kernel providing garbage!"); |
114 | return; |
115 | } |
116 | |
117 | /* send MFC entry to RDE */ |
118 | mfc.origin = kernel_msg.im_src; |
119 | mfc.group = kernel_msg.im_dst; |
120 | mfc.ifindex = kernel_msg.im_vif; |
121 | main_imsg_compose_rde(IMSG_MFC_ADD, 0, &mfc, sizeof(mfc)); |
122 | break; |
123 | case IGMPMSG_WRONGVIF2: |
124 | case IGMPMSG_WHOLEPKT3: |
125 | case IGMPMSG_BW_UPCALL4: |
126 | default: |
127 | log_debug("kmr_recv_msg: unhandled msg type %d!", |
128 | kernel_msg.im_msgtype); |
129 | } |
130 | } |
131 | |
132 | void |
133 | kmr_mfc_couple(void) |
134 | { |
135 | log_info("kernel multicast forwarding cache coupled"); |
136 | } |
137 | |
138 | void |
139 | kmr_mfc_decouple(void) |
140 | { |
141 | log_info("kernel multicast forwarding cache decoupled"); |
142 | } |
143 | |
144 | void |
145 | kmroute_clear(void) |
146 | { |
147 | |
148 | } |
149 | |
150 | int |
151 | mrt_init(int fd) |
152 | { |
153 | int flag = 1; |
154 | |
155 | if (setsockopt(fd, IPPROTO_IP0, MRT_INIT100, &flag, |
156 | sizeof(flag)) == -1) { |
157 | log_warn("mrt_init: error setting MRT_INIT"); |
158 | return (-1); |
159 | } |
160 | |
161 | return (0); |
162 | } |
163 | |
164 | int |
165 | mrt_done(int fd) |
166 | { |
167 | int flag = 0; |
168 | |
169 | if (setsockopt(fd, IPPROTO_IP0, MRT_DONE101, &flag, |
170 | sizeof(flag)) == -1) { |
171 | log_warn("mrt_done: error setting MRT_DONE"); |
172 | return (-1); |
173 | } |
174 | |
175 | return (0); |
176 | } |
177 | |
178 | int |
179 | mrt_add_vif(int fd, struct iface *iface) |
180 | { |
181 | struct vifctl vc; |
182 | |
183 | vc.vifc_vifi = iface->ifindex; |
184 | vc.vifc_flags = 0; |
185 | vc.vifc_threshold = 1; |
186 | vc.vifc_rate_limit = 0; |
187 | vc.vifc_lcl_addr.s_addr = iface->addr.s_addr; |
188 | vc.vifc_rmt_addr.s_addr = 0; |
189 | |
190 | if (setsockopt(fd, IPPROTO_IP0, MRT_ADD_VIF102, &vc, |
191 | sizeof(vc)) == -1) { |
192 | log_warn("mrt_add_vif: error adding VIF"); |
193 | return (-1); |
194 | } |
195 | |
196 | return (0); |
197 | } |
198 | |
199 | void |
200 | mrt_del_vif(int fd, struct iface *iface) |
201 | { |
202 | vifi_t vifi; |
203 | |
204 | vifi = iface->ifindex; |
205 | |
206 | if (setsockopt(fd, IPPROTO_IP0, MRT_DEL_VIF103, &vifi, |
207 | sizeof(vifi)) == -1) |
208 | log_warn("mrt_del_vif: error deleting VIF"); |
209 | } |
210 | |
211 | int |
212 | mrt_add_mfc(int fd, struct mfc *mfc) |
213 | { |
214 | struct mfcctl mc; |
215 | int i; |
216 | |
217 | log_debug("mrt_add_mfc: interface %d, group %s", mfc->ifindex, |
218 | inet_ntoa(mfc->group)); |
219 | |
220 | mc.mfcc_origin = mfc->origin; |
221 | mc.mfcc_mcastgrp = mfc->group; |
222 | mc.mfcc_parent = mfc->ifindex; |
223 | |
224 | for (i = 0; i < MAXVIFS32; i++) { |
225 | mc.mfcc_ttls[i] = mfc->ttls[i]; |
226 | } |
227 | |
228 | if (setsockopt(fd, IPPROTO_IP0, MRT_ADD_MFC104, &mc, sizeof(mc)) |
229 | == -1) { |
230 | log_warnx("mrt_add_mfc: error adding group %s to interface %d", |
231 | inet_ntoa(mfc->group), mfc->ifindex); |
232 | return (-1); |
233 | } |
234 | |
235 | return (0); |
236 | } |
237 | |
238 | int |
239 | mrt_del_mfc(int fd, struct mfc *mfc) |
240 | { |
241 | struct mfcctl mc; |
242 | |
243 | log_debug("mrt_del_mfc: group %s", inet_ntoa(mfc->group)); |
244 | |
245 | mc.mfcc_origin = mfc->origin; |
246 | mc.mfcc_mcastgrp = mfc->group; |
247 | |
248 | if (setsockopt(fd, IPPROTO_IP0, MRT_DEL_MFC105, &mc, sizeof(mc)) |
249 | == -1) { |
250 | log_warnx("mrt_del_mfc: error deleting group %s ", |
251 | inet_ntoa(mfc->group)); |
252 | return (-1); |
253 | } |
254 | |
255 | return (0); |
256 | } |