diff --git a/src/l2_packet/l2_packet.h b/src/l2_packet/l2_packet.h index f391f3682..7537f93ee 100644 --- a/src/l2_packet/l2_packet.h +++ b/src/l2_packet/l2_packet.h @@ -41,6 +41,7 @@ struct l2_ethhdr { enum l2_packet_filter_type { L2_PACKET_FILTER_DHCP, + L2_PACKET_FILTER_NDISC, }; /** diff --git a/src/l2_packet/l2_packet_linux.c b/src/l2_packet/l2_packet_linux.c index fcbf7e040..7217f8610 100644 --- a/src/l2_packet/l2_packet_linux.c +++ b/src/l2_packet/l2_packet_linux.c @@ -56,6 +56,24 @@ static const struct sock_fprog dhcp_sock_filter = { }; +/* Generated by 'sudo tcpdump -dd -s 150 multicast and ip6[6]=58' */ +static struct sock_filter ndisc_sock_filter_insns[] = { + { 0x30, 0, 0, 0x00000000 }, + { 0x45, 0, 5, 0x00000001 }, + { 0x28, 0, 0, 0x0000000c }, + { 0x15, 0, 3, 0x000086dd }, + { 0x30, 0, 0, 0x00000014 }, + { 0x15, 0, 1, 0x0000003a }, + { 0x6, 0, 0, 0x00000096 }, + { 0x6, 0, 0, 0x00000000 }, +}; + +static const struct sock_fprog ndisc_sock_filter = { + .len = ARRAY_SIZE(ndisc_sock_filter_insns), + .filter = ndisc_sock_filter_insns, +}; + + int l2_packet_get_own_addr(struct l2_packet_data *l2, u8 *addr) { os_memcpy(addr, l2->own_addr, ETH_ALEN); @@ -240,6 +258,9 @@ int l2_packet_set_packet_filter(struct l2_packet_data *l2, case L2_PACKET_FILTER_DHCP: sock_filter = &dhcp_sock_filter; break; + case L2_PACKET_FILTER_NDISC: + sock_filter = &ndisc_sock_filter; + break; default: return -1; }