static void broadcast_check(void) { struct { int version; char const *str; uint32_t netmask; bool is_broadcast; } tests[] = { { 4, "1.0.0.0", 0xff000000U, false }, { 4, "127.0.0.1", 0xff000000U, false }, { 4, "128.10.5.255", 0xffff0000U, false }, { 4, "192.168.10.9", 0xffffff00U, false }, { 4, "10.255.255.255", 0xff000000U, true }, { 4, "127.0.255.255", 0xff000000U, false }, { 4, "128.0.255.255", 0xffff0000U, true }, { 4, "192.168.10.255", 0xffffff00U, true }, { 6, "ff02::1", 0, true }, { 6, "1:2:3:4::", 0, false }, }; for (unsigned t = 0; t < NB_ELEMS(tests); t++) { struct ip_addr addr; ip_addr_ctor_from_str(&addr, tests[t].str, strlen(tests[t].str), tests[t].version); if (addr.family == AF_INET) { assert(netmask_of_address(addr.u.v4) == tests[t].netmask); } assert(ip_addr_is_broadcast(&addr) == tests[t].is_broadcast); } }
bool ip_addr_is_broadcast(struct ip_addr const *addr) { if (ip_addr_is_v6(addr)) { static uint8_t all_nodes[16] = { 0xff, 0x02, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, }; ASSERT_COMPILE(sizeof(all_nodes) == sizeof(addr->u.v6.s6_addr)); return 0 == memcmp(addr->u.v6.s6_addr, all_nodes, sizeof(all_nodes)); } else { uint32_t netmask = netmask_of_address(addr->u.v4); return (netmask | ntohl(addr->u.v4.s_addr)) == 0xffffffffU; } }