PERFORCE change 164138 for review
Ana Kukec
anchie at FreeBSD.org
Thu Jun 11 19:07:41 UTC 2009
http://perforce.freebsd.org/chv.cgi?CH=164138
Change 164138 by anchie at anchie_malimis on 2009/06/11 19:06:53
Introducing the routing socket to handle the incoming ND/SeND traffic
that used to be handled by the netgraph subsystem.
Affected files ...
.. //depot/projects/soc2009/anchie_send/send_0.2/sendd/net.c#5 edit
.. //depot/projects/soc2009/anchie_send/send_0.2/sendd/proto.c#3 edit
.. //depot/projects/soc2009/anchie_send/send_0.2/sendd/sendd.c#3 edit
.. //depot/projects/soc2009/anchie_send/send_0.2/sendd/sendd_local.h#2 edit
Differences ...
==== //depot/projects/soc2009/anchie_send/send_0.2/sendd/net.c#5 (text+ko) ====
@@ -127,6 +127,7 @@
snd_recv_pkt() and snd_icmp_sock_read()
*/
}
+}
void
snd_put_buf(struct sbuff *b)
@@ -169,6 +170,62 @@
return (0);
}
+void
+snd_sock_read(void)
+{
+ struct sockaddr_in6 sin[1];
+ struct sbuff *b;
+ uint8_t *type;
+ socklen_t slen;
+
+ if (b = snd_get_buf()) == NULL) {
+ return;
+ }
+
+ slen = sizeof(*sin);
+ if ((r = recvfrom(snds, b->hread, b->rem, 0, (void *)sin, &slen))
+ < 0) {
+ applog(LOG_ERR, "%s: recvfrom: %s", __FUNCTION__,
+ strerror(errno));
+ goto done;
+ }
+ b->len = r;
+
+ DBG(&dbg, "%d bytes from %s on IF %d", r,
+ inet_ntop(AF_INET6, &sin->sin6_addr, abuf, sizeof (abuf)),
+ sin->sin6_scope_id);
+
+ if (IN6_IS_ADDR_LOOPBACK(&sin->sin6_addr)) {
+ DBG(&dbg, "Dropping request from loopback");
+ goto done;
+
+ /* Further processing should be done according to snd_recv_pkt(). */
+ type = sbuff_data(b);
+ switch (*type) {
+ case ND_NEIGHBOR_SOLICIT:
+ snd_handle_ns(b, sin, sin->sin6_scope_id);
+ break;
+ case ND_NEIGHBOR_ADVERT:
+ snd_handle_na(b, sin);
+ break;
+ case ND_ROUTER_SOLICIT:
+ snd_handle_rs(b, sin, sin->sin6_scope_id);
+ break;
+ case ND_ROUTER_ADVERT:
+ snd_process_ra(sbuff_data(b), r, sin->sin6_scope_id,
+ &sin->sin6_addr);
+ break;
+ case ND_REDIRECT:
+ break;
+ default:
+ DBG(&dbg_snd, "Unhandled ICMP6 type %d", *type);
+ break;
+ }
+
+done:
+ snd_put_buf(b);
+}
+
/*
* TODO: Linux is not yet up-to-date with rfc3542, specifically in that
* it uses the socket option IPV6_PKTINFO instead of IPV6_RECVPKTINFO.
@@ -234,11 +291,12 @@
snd_put_buf(b);
}
-int
-snd_net_init(void)
+void
+snd_net_init(int *icmp6sock, int *sndsock)
{
int v;
struct icmp6_filter filter;
+ struct icmp6_filter snd_filter;
#ifdef DEBUG
struct dlog_desc *dbgs[] = {
&dbg,
@@ -256,6 +314,12 @@
return (-1);
}
+ if ((sndsock = socket(PF_ROUTE, SOCK_RAW, 0)) < 0) {
+ applog(LOG_ERR, "%s: socket: %s", __FUNCTION__,
+ strerror(errno));
+ return(-1);
+ }
+
v = 255;
if (setsockopt(icmp6sock, IPPROTO_IPV6, IPV6_UNICAST_HOPS, &v,
sizeof (v)) < 0) {
@@ -270,12 +334,18 @@
__FUNCTION__, strerror(errno));
return (-1);
}
-
+
ICMP6_FILTER_SETBLOCKALL(&filter);
ICMP6_FILTER_SETPASS(ICMP6_SND_CPS, &filter);
ICMP6_FILTER_SETPASS(ICMP6_SND_CPA, &filter);
ICMP6_FILTER_SETPASS(ND_ROUTER_ADVERT, &filter);
+ ICMP6_FILTER_SETBLOCKALL(&snd_filter);
+ ICMP6_FILTER_SETPASS(ND_ROUTER_SOLICIT, &snd_filter);
+ ICMP6_FILTER_SETPASS(ND_ROUTER_ADVERT, &snd_filter);
+ ICMP6_FILTER_SETPASS(ND_NEIGHBOR_SOLICIT, &snd_filter);
+ ICMP6_FILTER_SETPASS(ND_NEIGHBOR_ADVERT, &snd_filter);
+
if (setsockopt(icmp6sock, IPPROTO_ICMPV6, ICMP6_FILTER, &filter,
sizeof (filter)) < 0) {
applog(LOG_ERR, "%s: setsockopt(ICMP6_FILTER): %s",
@@ -283,5 +353,10 @@
return (-1);
}
- return (icmp6sock);
+ if (setsockopt(sndsock, IPPROTO_ICMPV6, ICMP6_FILTER, &snd_filter,
+ sizeof (snd_filter)) < 0) {
+ applog(LOG_ERR, "%s: setsockopt(ICMP6_FILTER): %s",
+ __FUNCTION__, strerror(errno));
+ return (-1);
+ }
}
==== //depot/projects/soc2009/anchie_send/send_0.2/sendd/proto.c#3 (text+ko) ====
@@ -664,6 +664,9 @@
void *start;
struct ip6_hdr *iph;
+ if (!snd_iface_ok_(ifidx)) {
+ return;
+ }
start = sbuff_data(b);
DBG(&dbg, "%s", in ? "<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<<" :
==== //depot/projects/soc2009/anchie_send/send_0.2/sendd/sendd.c#3 (text+ko) ====
@@ -93,7 +93,9 @@
FD_SET(icmps, fds);
FD_SET(ctlfd, fds);
/* os_specific_add_fds(fds, &maxfd); */
- snd_add_fds(fds, &maxfd);
+ /* snd_add_fds(fds, &maxfd); */
+ /* Routing socket instead of using netgraph for ND/SeND */
+ FD_SET(snds, fds);
tv = get_next_wait(tvb);
if (select(maxfd + 1, fds, NULL, NULL, tv) < 0) {
@@ -120,7 +122,10 @@
if (FD_ISSET(ctlfd, fds)) {
snd_ctl_read(ctlfd);
}
- snd_dispatch_fds(fds);
+ if (FD_ISSET(snds, fds)) {
+ snd_sock_read();
+ }
+ /* snd_dispatch_fds(fds); */
/* os_specific_dispatch_fds(fds); */
snd_replace_non_cga_linklocals();
}
@@ -168,7 +173,7 @@
int
main(int argc, char **argv)
{
- int r, c, icmps, ctlfd, do_daemon = 1;
+ int r, c, icmps, snds, ctlfd, do_daemon = 1;
char *cfile = SNDD_CONF_FILE;
#ifdef DEBUG
@@ -235,6 +240,8 @@
exit(1);
}
+ snd_net_init(&icmps, &snds);
+
thrpool_init();
if (timer_init() < 0 ||
pkixip_init() < 0 ||
@@ -242,7 +249,8 @@
snd_ssl_init() < 0 ||
snd_cga_init() < 0 ||
snd_params_init() < 0 ||
- (icmps = snd_net_init()) < 0 ||
+ icmps < 0 ||
+ snds < 0 ||
snd_init_cert() < 0 ||
snd_pkixip_config() < 0 ||
snd_proto_init() < 0 ||
==== //depot/projects/soc2009/anchie_send/send_0.2/sendd/sendd_local.h#2 (text+ko) ====
@@ -130,7 +130,8 @@
/* net.c */
extern void snd_icmp_sock_read(void);
-extern int snd_net_init(void);
+extern void snd_sock_read(void);
+extern void snd_net_init(void);
extern struct sbuff *snd_get_buf(void);
extern void snd_put_buf(struct sbuff *);
extern int snd_send_icmp(struct sbuff *, struct sockaddr_in6 *, int);
More information about the p4-projects
mailing list