diff options
Diffstat (limited to 'src/platform/tests')
| -rw-r--r-- | src/platform/tests/test-address.c | 14 | ||||
| -rw-r--r-- | src/platform/tests/test-cleanup.c | 2 | ||||
| -rw-r--r-- | src/platform/tests/test-common.c | 122 | ||||
| -rw-r--r-- | src/platform/tests/test-common.h | 19 | ||||
| -rw-r--r-- | src/platform/tests/test-general.c | 4 | ||||
| -rw-r--r-- | src/platform/tests/test-link.c | 501 | ||||
| -rw-r--r-- | src/platform/tests/test-nmp-object.c | 4 | ||||
| -rw-r--r-- | src/platform/tests/test-route.c | 4 |
8 files changed, 563 insertions, 107 deletions
diff --git a/src/platform/tests/test-address.c b/src/platform/tests/test-address.c index 3b52a7be..83a0bfd3 100644 --- a/src/platform/tests/test-address.c +++ b/src/platform/tests/test-address.c @@ -94,12 +94,12 @@ test_ip4_address_general (void) /* Add address */ g_assert (!nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr)); - nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime, preferred, NULL); + nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime, preferred, 0, NULL); g_assert (nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr)); accept_signal (address_added); /* Add address again (aka update) */ - nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime + 100, preferred + 50, NULL); + nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime + 100, preferred + 50, 0, NULL); accept_signals (address_changed, 0, 1); /* Test address listing */ @@ -197,7 +197,7 @@ test_ip4_address_general_2 (void) g_assert (nm_platform_link_set_up (NM_PLATFORM_GET, DEVICE_IFINDEX, NULL)); /* Add/delete notification */ - nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime, preferred, NULL); + nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime, preferred, 0, NULL); accept_signal (address_added); g_assert (nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr)); nmtstp_ip4_address_del (EX, ifindex, addr, IP4_PLEN, addr); @@ -205,7 +205,7 @@ test_ip4_address_general_2 (void) g_assert (!nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr)); /* Add/delete conflict */ - nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime, preferred, NULL); + nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr, lifetime, preferred, 0, NULL); g_assert (nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr)); accept_signal (address_added); @@ -273,7 +273,7 @@ test_ip4_address_peer (void) accept_signals (address_added, 0, G_MAXINT); /* Add/delete notification */ - nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr_peer, lifetime, preferred, NULL); + nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr_peer, lifetime, preferred, 0, NULL); accept_signal (address_added); a = nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr_peer); g_assert (a); @@ -281,7 +281,7 @@ test_ip4_address_peer (void) nmtstp_ip_address_assert_lifetime ((NMPlatformIPAddress *) a, -1, lifetime, preferred); - nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr_peer2, lifetime, preferred, NULL); + nmtstp_ip4_address_add (EX, ifindex, addr, IP4_PLEN, addr_peer2, lifetime, preferred, 0, NULL); accept_signal (address_added); g_assert (nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr_peer)); a = nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, IP4_PLEN, addr_peer2); @@ -328,7 +328,7 @@ test_ip4_address_peer_zero (void) for (i = 0; i < G_N_ELEMENTS (peers); i++) { g_assert (!nm_platform_ip4_address_get (NM_PLATFORM_GET, ifindex, addr, plen, r_peers[i])); - nmtstp_ip4_address_add (EX, ifindex, addr, plen, r_peers[i], lifetime, preferred, label); + nmtstp_ip4_address_add (EX, ifindex, addr, plen, r_peers[i], lifetime, preferred, 0, label); addrs = nm_platform_ip4_address_get_all (NM_PLATFORM_GET, ifindex); g_assert (addrs); diff --git a/src/platform/tests/test-cleanup.c b/src/platform/tests/test-cleanup.c index 6ad24478..4036daad 100644 --- a/src/platform/tests/test-cleanup.c +++ b/src/platform/tests/test-cleanup.c @@ -63,7 +63,7 @@ test_cleanup_internal (void) g_assert (ifindex > 0); /* Add routes and addresses */ - g_assert (nm_platform_ip4_address_add (NM_PLATFORM_GET, ifindex, addr4, plen4, addr4, lifetime, preferred, NULL)); + g_assert (nm_platform_ip4_address_add (NM_PLATFORM_GET, ifindex, addr4, plen4, addr4, lifetime, preferred, 0, NULL)); g_assert (nm_platform_ip6_address_add (NM_PLATFORM_GET, ifindex, addr6, plen6, in6addr_any, lifetime, preferred, flags)); g_assert (nm_platform_ip4_route_add (NM_PLATFORM_GET, ifindex, NM_IP_CONFIG_SOURCE_USER, gateway4, 32, INADDR_ANY, 0, metric, mss)); g_assert (nm_platform_ip4_route_add (NM_PLATFORM_GET, ifindex, NM_IP_CONFIG_SOURCE_USER, network4, plen4, gateway4, 0, metric, mss)); diff --git a/src/platform/tests/test-common.c b/src/platform/tests/test-common.c index 268a5c92..e9fffe90 100644 --- a/src/platform/tests/test-common.c +++ b/src/platform/tests/test-common.c @@ -338,30 +338,32 @@ _wait_for_signal_timeout (gpointer user_data) } gboolean -nmtstp_wait_for_signal (guint timeout_ms) +nmtstp_wait_for_signal (NMPlatform *platform, guint timeout_ms) { WaitForSignalData data = { 0 }; - gulong id_link, id_ip4_address, id_ip6_address, id_ip4_route, id_ip6_route; + if (!platform) + platform = NM_PLATFORM_GET; + data.loop = g_main_loop_new (NULL, FALSE); - id_link = g_signal_connect (NM_PLATFORM_GET, NM_PLATFORM_SIGNAL_LINK_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); - id_ip4_address = g_signal_connect (NM_PLATFORM_GET, NM_PLATFORM_SIGNAL_IP4_ADDRESS_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); - id_ip6_address = g_signal_connect (NM_PLATFORM_GET, NM_PLATFORM_SIGNAL_IP6_ADDRESS_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); - id_ip4_route = g_signal_connect (NM_PLATFORM_GET, NM_PLATFORM_SIGNAL_IP4_ROUTE_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); - id_ip6_route = g_signal_connect (NM_PLATFORM_GET, NM_PLATFORM_SIGNAL_IP6_ROUTE_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); + id_link = g_signal_connect (platform, NM_PLATFORM_SIGNAL_LINK_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); + id_ip4_address = g_signal_connect (platform, NM_PLATFORM_SIGNAL_IP4_ADDRESS_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); + id_ip6_address = g_signal_connect (platform, NM_PLATFORM_SIGNAL_IP6_ADDRESS_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); + id_ip4_route = g_signal_connect (platform, NM_PLATFORM_SIGNAL_IP4_ROUTE_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); + id_ip6_route = g_signal_connect (platform, NM_PLATFORM_SIGNAL_IP6_ROUTE_CHANGED, G_CALLBACK (_wait_for_signal_cb), &data); if (timeout_ms != 0) data.id = g_timeout_add (timeout_ms, _wait_for_signal_timeout, &data); g_main_loop_run (data.loop); - g_assert (nm_clear_g_signal_handler (NM_PLATFORM_GET, &id_link)); - g_assert (nm_clear_g_signal_handler (NM_PLATFORM_GET, &id_ip4_address)); - g_assert (nm_clear_g_signal_handler (NM_PLATFORM_GET, &id_ip6_address)); - g_assert (nm_clear_g_signal_handler (NM_PLATFORM_GET, &id_ip4_route)); - g_assert (nm_clear_g_signal_handler (NM_PLATFORM_GET, &id_ip6_route)); + g_assert (nm_clear_g_signal_handler (platform, &id_link)); + g_assert (nm_clear_g_signal_handler (platform, &id_ip4_address)); + g_assert (nm_clear_g_signal_handler (platform, &id_ip6_address)); + g_assert (nm_clear_g_signal_handler (platform, &id_ip4_route)); + g_assert (nm_clear_g_signal_handler (platform, &id_ip6_route)); if (nm_clear_g_source (&data.id)) g_assert (timeout_ms != 0 && !data.timeout); @@ -372,7 +374,7 @@ nmtstp_wait_for_signal (guint timeout_ms) } gboolean -nmtstp_wait_for_signal_until (gint64 until_ms) +nmtstp_wait_for_signal_until (NMPlatform *platform, gint64 until_ms) { gint64 now; @@ -382,19 +384,19 @@ nmtstp_wait_for_signal_until (gint64 until_ms) if (until_ms < now) return FALSE; - if (nmtstp_wait_for_signal (MAX (1, until_ms - now))) + if (nmtstp_wait_for_signal (platform, MAX (1, until_ms - now))) return TRUE; } } const NMPlatformLink * -nmtstp_wait_for_link (const char *ifname, NMLinkType expected_link_type, guint timeout_ms) +nmtstp_wait_for_link (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, guint timeout_ms) { - return nmtstp_wait_for_link_until (ifname, expected_link_type, nm_utils_get_monotonic_timestamp_ms () + timeout_ms); + return nmtstp_wait_for_link_until (platform, ifname, expected_link_type, nm_utils_get_monotonic_timestamp_ms () + timeout_ms); } const NMPlatformLink * -nmtstp_wait_for_link_until (const char *ifname, NMLinkType expected_link_type, gint64 until_ms) +nmtstp_wait_for_link_until (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, gint64 until_ms) { const NMPlatformLink *plink; gint64 now; @@ -402,7 +404,7 @@ nmtstp_wait_for_link_until (const char *ifname, NMLinkType expected_link_type, g while (TRUE) { now = nm_utils_get_monotonic_timestamp_ms (); - plink = nm_platform_link_get_by_ifname (NM_PLATFORM_GET, ifname); + plink = nm_platform_link_get_by_ifname (platform ?: NM_PLATFORM_GET, ifname); if ( plink && (expected_link_type == NM_LINK_TYPE_NONE || plink->type == expected_link_type)) return plink; @@ -410,22 +412,22 @@ nmtstp_wait_for_link_until (const char *ifname, NMLinkType expected_link_type, g if (until_ms < now) return NULL; - nmtstp_wait_for_signal (MAX (1, until_ms - now)); + nmtstp_wait_for_signal (platform, MAX (1, until_ms - now)); } } const NMPlatformLink * -nmtstp_assert_wait_for_link (const char *ifname, NMLinkType expected_link_type, guint timeout_ms) +nmtstp_assert_wait_for_link (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, guint timeout_ms) { - return nmtstp_assert_wait_for_link_until (ifname, expected_link_type, nm_utils_get_monotonic_timestamp_ms () + timeout_ms); + return nmtstp_assert_wait_for_link_until (platform, ifname, expected_link_type, nm_utils_get_monotonic_timestamp_ms () + timeout_ms); } const NMPlatformLink * -nmtstp_assert_wait_for_link_until (const char *ifname, NMLinkType expected_link_type, gint64 until_ms) +nmtstp_assert_wait_for_link_until (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, gint64 until_ms) { const NMPlatformLink *plink; - plink = nmtstp_wait_for_link_until (ifname, expected_link_type, until_ms); + plink = nmtstp_wait_for_link_until (platform, ifname, expected_link_type, until_ms); g_assert (plink); return plink; } @@ -563,8 +565,8 @@ _ip_address_add (gboolean external_command, const NMIPAddr *peer_address, guint32 lifetime, guint32 preferred, - const char *label, - guint32 flags) + guint32 flags, + const char *label) { gint64 end_time; @@ -626,7 +628,6 @@ _ip_address_add (gboolean external_command, gboolean success; if (is_v4) { - g_assert (flags == 0); success = nm_platform_ip4_address_add (NM_PLATFORM_GET, ifindex, address->addr4, @@ -634,6 +635,7 @@ _ip_address_add (gboolean external_command, peer_address->addr4, lifetime, preferred, + flags, label); } else { g_assert (label == NULL); @@ -686,20 +688,20 @@ _ip_address_add (gboolean external_command, /* for internal command, we expect not to reach this line.*/ g_assert (external_command); - g_assert (nmtstp_wait_for_signal_until (end_time)); + g_assert (nmtstp_wait_for_signal_until (NM_PLATFORM_GET, end_time)); } while (TRUE); } -#define _assert_pllink(success, pllink, name, type) \ +#define _assert_pllink(platform, success, pllink, name, type) \ G_STMT_START { \ const NMPlatformLink *_pllink = (pllink); \ \ if ((success)) { \ g_assert (_pllink); \ - g_assert (_pllink == nmtstp_link_get_typed (_pllink->ifindex, (name), (type))); \ + g_assert (_pllink == nmtstp_link_get_typed (platform, _pllink->ifindex, (name), (type))); \ } else { \ g_assert (!_pllink); \ - g_assert (!nmtstp_link_get (0, (name))); \ + g_assert (!nmtstp_link_get (platform, 0, (name))); \ } \ } G_STMT_END @@ -718,12 +720,12 @@ nmtstp_link_dummy_add (gboolean external_command, success = !nmtstp_run_command ("ip link add %s type dummy", name); if (success) - pllink = nmtstp_assert_wait_for_link (name, NM_LINK_TYPE_DUMMY, 100); + pllink = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, name, NM_LINK_TYPE_DUMMY, 100); } else success = nm_platform_link_dummy_add (NM_PLATFORM_GET, name, &pllink) == NM_PLATFORM_ERROR_SUCCESS; g_assert (success); - _assert_pllink (success, pllink, name, NM_LINK_TYPE_DUMMY); + _assert_pllink (NM_PLATFORM_GET, success, pllink, name, NM_LINK_TYPE_DUMMY); return pllink; } @@ -755,11 +757,11 @@ nmtstp_link_gre_add (gboolean external_command, lnk->tos, lnk->path_mtu_discovery ? "pmtudisc" : "nopmtudisc"); if (success) - pllink = nmtstp_assert_wait_for_link (name, NM_LINK_TYPE_GRE, 100); + pllink = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, name, NM_LINK_TYPE_GRE, 100); } else success = nm_platform_link_gre_add (NM_PLATFORM_GET, name, lnk, &pllink) == NM_PLATFORM_ERROR_SUCCESS; - _assert_pllink (success, pllink, name, NM_LINK_TYPE_GRE); + _assert_pllink (NM_PLATFORM_GET, success, pllink, name, NM_LINK_TYPE_GRE); return pllink; } @@ -806,11 +808,11 @@ nmtstp_link_ip6tnl_add (gboolean external_command, lnk->encap_limit, lnk->flow_label); if (success) - pllink = nmtstp_assert_wait_for_link (name, NM_LINK_TYPE_IP6TNL, 100); + pllink = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, name, NM_LINK_TYPE_IP6TNL, 100); } else success = nm_platform_link_ip6tnl_add (NM_PLATFORM_GET, name, lnk, &pllink) == NM_PLATFORM_ERROR_SUCCESS; - _assert_pllink (success, pllink, name, NM_LINK_TYPE_IP6TNL); + _assert_pllink (NM_PLATFORM_GET, success, pllink, name, NM_LINK_TYPE_IP6TNL); return pllink; } @@ -843,11 +845,11 @@ nmtstp_link_ipip_add (gboolean external_command, lnk->tos, lnk->path_mtu_discovery ? "pmtudisc" : "nopmtudisc"); if (success) - pllink = nmtstp_assert_wait_for_link (name, NM_LINK_TYPE_IPIP, 100); + pllink = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, name, NM_LINK_TYPE_IPIP, 100); } else success = nm_platform_link_ipip_add (NM_PLATFORM_GET, name, lnk, &pllink) == NM_PLATFORM_ERROR_SUCCESS; - _assert_pllink (success, pllink, name, NM_LINK_TYPE_IPIP); + _assert_pllink (NM_PLATFORM_GET, success, pllink, name, NM_LINK_TYPE_IPIP); return pllink; } @@ -888,11 +890,11 @@ nmtstp_link_macvlan_add (gboolean external_command, modes[lnk->mode], lnk->no_promisc ? "nopromisc" : ""); if (success) - pllink = nmtstp_assert_wait_for_link (name, link_type, 100); + pllink = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, name, link_type, 100); } else success = nm_platform_link_macvlan_add (NM_PLATFORM_GET, name, parent, lnk, &pllink) == NM_PLATFORM_ERROR_SUCCESS; - _assert_pllink (success, pllink, name, link_type); + _assert_pllink (NM_PLATFORM_GET, success, pllink, name, link_type); return pllink; } @@ -930,11 +932,11 @@ nmtstp_link_sit_add (gboolean external_command, lnk->tos, lnk->path_mtu_discovery ? "pmtudisc" : "nopmtudisc"); if (success) - pllink = nmtstp_assert_wait_for_link (name, NM_LINK_TYPE_SIT, 100); + pllink = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, name, NM_LINK_TYPE_SIT, 100); } else success = nm_platform_link_sit_add (NM_PLATFORM_GET, name, lnk, &pllink) == NM_PLATFORM_ERROR_SUCCESS; - _assert_pllink (success, pllink, name, NM_LINK_TYPE_SIT); + _assert_pllink (NM_PLATFORM_GET, success, pllink, name, NM_LINK_TYPE_SIT); return pllink; } @@ -983,7 +985,7 @@ nmtstp_link_vxlan_add (gboolean external_command, /* Older versions of iproute2 don't support adding vxlan devices. * On failure, fallback to using platform code. */ if (err == 0) - pllink = nmtstp_assert_wait_for_link (name, NM_LINK_TYPE_VXLAN, 100); + pllink = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, name, NM_LINK_TYPE_VXLAN, 100); else _LOGI ("Adding vxlan device via iproute2 failed. Assume iproute2 is not up to the task."); } @@ -1006,6 +1008,7 @@ nmtstp_ip4_address_add (gboolean external_command, in_addr_t peer_address, guint32 lifetime, guint32 preferred, + guint32 flags, const char *label) { _ip_address_add (external_command, @@ -1016,8 +1019,8 @@ nmtstp_ip4_address_add (gboolean external_command, (NMIPAddr *) &peer_address, lifetime, preferred, - label, - 0); + flags, + label); } void @@ -1038,8 +1041,8 @@ nmtstp_ip6_address_add (gboolean external_command, (NMIPAddr *) &peer_address, lifetime, preferred, - NULL, - flags); + flags, + NULL); } static void @@ -1127,7 +1130,7 @@ _ip_address_del (gboolean external_command, /* for internal command, we expect not to reach this line.*/ g_assert (external_command); - g_assert (nmtstp_wait_for_signal_until (end_time)); + g_assert (nmtstp_wait_for_signal_until (NM_PLATFORM_GET, end_time)); } while (TRUE); } @@ -1161,14 +1164,18 @@ nmtstp_ip6_address_del (gboolean external_command, } const NMPlatformLink * -nmtstp_link_get_typed (int ifindex, +nmtstp_link_get_typed (NMPlatform *platform, + int ifindex, const char *name, NMLinkType link_type) { const NMPlatformLink *pllink = NULL; + if (!platform) + platform = NM_PLATFORM_GET; + if (ifindex > 0) { - pllink = nm_platform_link_get (NM_PLATFORM_GET, ifindex); + pllink = nm_platform_link_get (platform, ifindex); if (pllink) { g_assert_cmpint (pllink->ifindex, ==, ifindex); @@ -1176,12 +1183,12 @@ nmtstp_link_get_typed (int ifindex, g_assert_cmpstr (name, ==, pllink->name); } else { if (name) - g_assert (!nm_platform_link_get_by_ifname (NM_PLATFORM_GET, name)); + g_assert (!nm_platform_link_get_by_ifname (platform, name)); } } else { g_assert (name); - pllink = nm_platform_link_get_by_ifname (NM_PLATFORM_GET, name); + pllink = nm_platform_link_get_by_ifname (platform, name); if (pllink) g_assert_cmpstr (name, ==, pllink->name); @@ -1196,10 +1203,11 @@ nmtstp_link_get_typed (int ifindex, } const NMPlatformLink * -nmtstp_link_get (int ifindex, +nmtstp_link_get (NMPlatform *platform, + int ifindex, const char *name) { - return nmtstp_link_get_typed (ifindex, name, NM_LINK_TYPE_NONE); + return nmtstp_link_get_typed (platform, ifindex, name, NM_LINK_TYPE_NONE); } void @@ -1212,7 +1220,7 @@ nmtstp_link_del (gboolean external_command, gboolean success; gs_free char *name_copy = NULL; - pllink = nmtstp_link_get (ifindex, name); + pllink = nmtstp_link_get (NM_PLATFORM_GET, ifindex, name); g_assert (pllink); @@ -1242,7 +1250,7 @@ nmtstp_link_del (gboolean external_command, /* for internal command, we expect not to reach this line.*/ g_assert (external_command); - g_assert (nmtstp_wait_for_signal_until (end_time)); + g_assert (nmtstp_wait_for_signal_until (NM_PLATFORM_GET, end_time)); } while (TRUE); } @@ -1288,7 +1296,7 @@ nmtstp_link_set_updown (gboolean external_command, /* for internal command, we expect not to reach this line.*/ g_assert (external_command); - g_assert (nmtstp_wait_for_signal_until (end_time)); + g_assert (nmtstp_wait_for_signal_until (NM_PLATFORM_GET, end_time)); } while (TRUE); } diff --git a/src/platform/tests/test-common.h b/src/platform/tests/test-common.h index 0281d3c5..82561193 100644 --- a/src/platform/tests/test-common.h +++ b/src/platform/tests/test-common.h @@ -91,13 +91,13 @@ void link_callback (NMPlatform *platform, NMPObjectType obj_type, int ifindex, N int nmtstp_run_command (const char *format, ...) __attribute__((__format__ (__printf__, 1, 2))); #define nmtstp_run_command_check(...) do { g_assert_cmpint (nmtstp_run_command (__VA_ARGS__), ==, 0); } while (0) -gboolean nmtstp_wait_for_signal (guint timeout_ms); -gboolean nmtstp_wait_for_signal_until (gint64 until_ms); -const NMPlatformLink *nmtstp_wait_for_link (const char *ifname, NMLinkType expected_link_type, guint timeout_ms); -const NMPlatformLink *nmtstp_wait_for_link_until (const char *ifname, NMLinkType expected_link_type, gint64 until_ms); +gboolean nmtstp_wait_for_signal (NMPlatform *platform, guint timeout_ms); +gboolean nmtstp_wait_for_signal_until (NMPlatform *platform, gint64 until_ms); +const NMPlatformLink *nmtstp_wait_for_link (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, guint timeout_ms); +const NMPlatformLink *nmtstp_wait_for_link_until (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, gint64 until_ms); -const NMPlatformLink *nmtstp_assert_wait_for_link (const char *ifname, NMLinkType expected_link_type, guint timeout_ms); -const NMPlatformLink *nmtstp_assert_wait_for_link_until (const char *ifname, NMLinkType expected_link_type, gint64 until_ms); +const NMPlatformLink *nmtstp_assert_wait_for_link (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, guint timeout_ms); +const NMPlatformLink *nmtstp_assert_wait_for_link_until (NMPlatform *platform, const char *ifname, NMLinkType expected_link_type, gint64 until_ms); int nmtstp_run_command_check_external_global (void); gboolean nmtstp_run_command_check_external (int external_command); @@ -117,6 +117,7 @@ void nmtstp_ip4_address_add (gboolean external_command, in_addr_t peer_address, guint32 lifetime, guint32 preferred, + guint32 flags, const char *label); void nmtstp_ip6_address_add (gboolean external_command, int ifindex, @@ -125,7 +126,7 @@ void nmtstp_ip6_address_add (gboolean external_command, struct in6_addr peer_address, guint32 lifetime, guint32 preferred, - guint flags); + guint32 flags); void nmtstp_ip4_address_del (gboolean external_command, int ifindex, in_addr_t address, @@ -136,8 +137,8 @@ void nmtstp_ip6_address_del (gboolean external_command, struct in6_addr address, int plen); -const NMPlatformLink *nmtstp_link_get_typed (int ifindex, const char *name, NMLinkType link_type); -const NMPlatformLink *nmtstp_link_get (int ifindex, const char *name); +const NMPlatformLink *nmtstp_link_get_typed (NMPlatform *platform, int ifindex, const char *name, NMLinkType link_type); +const NMPlatformLink *nmtstp_link_get (NMPlatform *platform, int ifindex, const char *name); void nmtstp_link_set_updown (gboolean external_command, int ifindex, diff --git a/src/platform/tests/test-general.c b/src/platform/tests/test-general.c index f342e565..66f72fa5 100644 --- a/src/platform/tests/test-general.c +++ b/src/platform/tests/test-general.c @@ -18,12 +18,12 @@ * Copyright (C) 2015 Red Hat, Inc. */ -#include "nm-platform-utils.h" +#include "nm-default.h" #include <linux/rtnetlink.h> +#include "nm-platform-utils.h" #include "nm-linux-platform.h" -#include "nm-default.h" #include "nm-test-utils.h" diff --git a/src/platform/tests/test-link.c b/src/platform/tests/test-link.c index 3fa5ad50..94695edc 100644 --- a/src/platform/tests/test-link.c +++ b/src/platform/tests/test-link.c @@ -21,8 +21,13 @@ #include "nm-default.h" #include <sched.h> +#include <sys/mount.h> +#include <sys/stat.h> +#include <sys/types.h> #include "nmp-object.h" +#include "nmp-netns.h" +#include "nm-platform-utils.h" #include "test-common.h" #include "nm-test-utils.h" @@ -40,6 +45,9 @@ #define VLAN_FLAGS 0 #define MTU 1357 +#define _ADD_DUMMY(platform, name) \ + g_assert_cmpint (nm_platform_link_dummy_add ((platform), (name), NULL), ==, NM_PLATFORM_ERROR_SUCCESS) + static void test_bogus(void) { @@ -52,16 +60,16 @@ test_bogus(void) g_assert (!nm_platform_link_get_type (NM_PLATFORM_GET, BOGUS_IFINDEX)); g_assert (!nm_platform_link_get_type_name (NM_PLATFORM_GET, BOGUS_IFINDEX)); - g_test_expect_message ("NetworkManager", G_LOG_LEVEL_WARNING, "*failure changing link: *"); + g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*failure changing link: *"); g_assert (!nm_platform_link_set_up (NM_PLATFORM_GET, BOGUS_IFINDEX, NULL)); - g_test_expect_message ("NetworkManager", G_LOG_LEVEL_WARNING, "*failure changing link: *"); + g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*failure changing link: *"); g_assert (!nm_platform_link_set_down (NM_PLATFORM_GET, BOGUS_IFINDEX)); - g_test_expect_message ("NetworkManager", G_LOG_LEVEL_WARNING, "*failure changing link: *"); + g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*failure changing link: *"); g_assert (!nm_platform_link_set_arp (NM_PLATFORM_GET, BOGUS_IFINDEX)); - g_test_expect_message ("NetworkManager", G_LOG_LEVEL_WARNING, "*failure changing link: *"); + g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*failure changing link: *"); g_assert (!nm_platform_link_set_noarp (NM_PLATFORM_GET, BOGUS_IFINDEX)); g_assert (!nm_platform_link_is_up (NM_PLATFORM_GET, BOGUS_IFINDEX)); @@ -72,7 +80,7 @@ test_bogus(void) g_assert (!addrlen); g_assert (!nm_platform_link_get_address (NM_PLATFORM_GET, BOGUS_IFINDEX, NULL)); - g_test_expect_message ("NetworkManager", G_LOG_LEVEL_WARNING, "*failure changing link: *"); + g_test_expect_message ("NetworkManager", G_LOG_LEVEL_MESSAGE, "*failure changing link: *"); g_assert (!nm_platform_link_set_mtu (NM_PLATFORM_GET, BOGUS_IFINDEX, MTU)); g_assert (!nm_platform_link_get_mtu (NM_PLATFORM_GET, BOGUS_IFINDEX)); @@ -690,7 +698,7 @@ test_software_detect (gconstpointer user_data) const gboolean ext = test_data->external_command; nmtstp_run_command_check ("ip link add %s type dummy", PARENT_NAME); - ifindex_parent = nmtstp_assert_wait_for_link (PARENT_NAME, NM_LINK_TYPE_DUMMY, 100)->ifindex; + ifindex_parent = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, PARENT_NAME, NM_LINK_TYPE_DUMMY, 100)->ifindex; switch (test_data->link_type) { case NM_LINK_TYPE_GRE: { @@ -852,7 +860,7 @@ test_software_detect (gconstpointer user_data) g_assert_not_reached (); } - ifindex = nmtstp_assert_wait_for_link (DEVICE_NAME, test_data->link_type, 100)->ifindex; + ifindex = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, DEVICE_NAME, test_data->link_type, 100)->ifindex; nmtstp_link_set_updown (-1, ifindex_parent, TRUE); @@ -1137,10 +1145,10 @@ test_vlan_set_xgress (void) int ifindex, ifindex_parent; nmtstp_run_command_check ("ip link add %s type dummy", PARENT_NAME); - ifindex_parent = nmtstp_assert_wait_for_link (PARENT_NAME, NM_LINK_TYPE_DUMMY, 100)->ifindex; + ifindex_parent = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, PARENT_NAME, NM_LINK_TYPE_DUMMY, 100)->ifindex; nmtstp_run_command_check ("ip link add name %s link %s type vlan id 1245", DEVICE_NAME, PARENT_NAME); - ifindex = nmtstp_assert_wait_for_link (DEVICE_NAME, NM_LINK_TYPE_VLAN, 100)->ifindex; + ifindex = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, DEVICE_NAME, NM_LINK_TYPE_VLAN, 100)->ifindex; /* ingress-qos-map */ @@ -1662,7 +1670,7 @@ test_create_many_links (gconstpointer user_data) guint n_devices = GPOINTER_TO_UINT (user_data); if (n_devices > 100 && nmtst_test_quick ()) { - g_print ("Skipping test: don't run long running test %s (NMTST_DEBUG=slow)\n", str_if_set (g_get_prgname (), "test-link-linux")); + g_print ("Skipping test: don't run long running test %s (NMTST_DEBUG=slow)\n", g_get_prgname () ?: "test-link-linux"); g_test_skip ("Skip long running test"); return; } @@ -1685,8 +1693,8 @@ test_nl_bugs_veth (void) /* create veth pair. */ nmtstp_run_command_check ("ip link add dev %s type veth peer name %s", IFACE_VETH0, IFACE_VETH1); - ifindex_veth0 = nmtstp_assert_wait_for_link (IFACE_VETH0, NM_LINK_TYPE_VETH, 100)->ifindex; - ifindex_veth1 = nmtstp_assert_wait_for_link (IFACE_VETH1, NM_LINK_TYPE_VETH, 100)->ifindex; + ifindex_veth0 = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, IFACE_VETH0, NM_LINK_TYPE_VETH, 100)->ifindex; + ifindex_veth1 = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, IFACE_VETH1, NM_LINK_TYPE_VETH, 100)->ifindex; /* assert that nm_platform_link_veth_get_properties() returns the expected peer ifindexes. */ g_assert (nm_platform_link_veth_get_properties (NM_PLATFORM_GET, ifindex_veth0, &i)); @@ -1722,7 +1730,7 @@ test_nl_bugs_veth (void) nmtstp_run_command_check ("ip link set %s netns %ld", IFACE_VETH1, (long) nmtstp_namespace_handle_get_pid (ns_handle)); NMTST_WAIT_ASSERT (100, { - nmtstp_wait_for_signal (50); + nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); nm_platform_process_events (NM_PLATFORM_GET); pllink_veth1 = nm_platform_link_get (NM_PLATFORM_GET, ifindex_veth1); @@ -1736,8 +1744,8 @@ test_nl_bugs_veth (void) out: nmtstp_link_del (-1, ifindex_veth0, IFACE_VETH0); - g_assert (!nmtstp_link_get (ifindex_veth0, IFACE_VETH0)); - g_assert (!nmtstp_link_get (ifindex_veth1, IFACE_VETH1)); + g_assert (!nmtstp_link_get (NM_PLATFORM_GET, ifindex_veth0, IFACE_VETH0)); + g_assert (!nmtstp_link_get (NM_PLATFORM_GET, ifindex_veth1, IFACE_VETH1)); nmtstp_namespace_handle_release (ns_handle); } @@ -1755,16 +1763,16 @@ test_nl_bugs_spuroius_newlink (void) /* see https://bugzilla.redhat.com/show_bug.cgi?id=1285719 */ nmtstp_run_command_check ("ip link add %s type dummy", IFACE_DUMMY0); - ifindex_dummy0 = nmtstp_assert_wait_for_link (IFACE_DUMMY0, NM_LINK_TYPE_DUMMY, 100)->ifindex; + ifindex_dummy0 = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, IFACE_DUMMY0, NM_LINK_TYPE_DUMMY, 100)->ifindex; nmtstp_run_command_check ("ip link add %s type bond", IFACE_BOND0); - ifindex_bond0 = nmtstp_assert_wait_for_link (IFACE_BOND0, NM_LINK_TYPE_BOND, 100)->ifindex; + ifindex_bond0 = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, IFACE_BOND0, NM_LINK_TYPE_BOND, 100)->ifindex; nmtstp_link_set_updown (-1, ifindex_bond0, TRUE); nmtstp_run_command_check ("ip link set %s master %s", IFACE_DUMMY0, IFACE_BOND0); NMTST_WAIT_ASSERT (100, { - nmtstp_wait_for_signal (50); + nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); pllink = nm_platform_link_get (NM_PLATFORM_GET, ifindex_dummy0); g_assert (pllink); @@ -1775,7 +1783,7 @@ test_nl_bugs_spuroius_newlink (void) nmtstp_run_command_check ("ip link del %s", IFACE_BOND0); wait_for_settle = TRUE; - nmtstp_wait_for_signal (50); + nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); again: nm_platform_process_events (NM_PLATFORM_GET); pllink = nm_platform_link_get (NM_PLATFORM_GET, ifindex_bond0); @@ -1783,11 +1791,11 @@ again: if (wait_for_settle) { wait_for_settle = FALSE; - NMTST_WAIT (300, { nmtstp_wait_for_signal (50); }); + NMTST_WAIT (300, { nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); }); goto again; } - g_assert (!nmtstp_link_get (ifindex_bond0, IFACE_BOND0)); + g_assert (!nmtstp_link_get (NM_PLATFORM_GET, ifindex_bond0, IFACE_BOND0)); nmtstp_link_del (-1, ifindex_dummy0, IFACE_DUMMY0); } @@ -1805,16 +1813,16 @@ test_nl_bugs_spuroius_dellink (void) /* see https://bugzilla.redhat.com/show_bug.cgi?id=1285719 */ nmtstp_run_command_check ("ip link add %s type dummy", IFACE_DUMMY0); - ifindex_dummy0 = nmtstp_assert_wait_for_link (IFACE_DUMMY0, NM_LINK_TYPE_DUMMY, 100)->ifindex; + ifindex_dummy0 = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, IFACE_DUMMY0, NM_LINK_TYPE_DUMMY, 100)->ifindex; nmtstp_run_command_check ("ip link add %s type bridge", IFACE_BRIDGE0); - ifindex_bridge0 = nmtstp_assert_wait_for_link (IFACE_BRIDGE0, NM_LINK_TYPE_BRIDGE, 100)->ifindex; + ifindex_bridge0 = nmtstp_assert_wait_for_link (NM_PLATFORM_GET, IFACE_BRIDGE0, NM_LINK_TYPE_BRIDGE, 100)->ifindex; nmtstp_link_set_updown (-1, ifindex_bridge0, TRUE); nmtstp_run_command_check ("ip link set %s master %s", IFACE_DUMMY0, IFACE_BRIDGE0); NMTST_WAIT_ASSERT (100, { - nmtstp_wait_for_signal (50); + nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); pllink = nm_platform_link_get (NM_PLATFORM_GET, ifindex_dummy0); g_assert (pllink); @@ -1827,7 +1835,7 @@ test_nl_bugs_spuroius_dellink (void) nmtstp_run_command_check ("ip link set %s nomaster", IFACE_DUMMY0); wait_for_settle = TRUE; - nmtstp_wait_for_signal (50); + nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); again: nm_platform_process_events (NM_PLATFORM_GET); pllink = nm_platform_link_get (NM_PLATFORM_GET, ifindex_bridge0); @@ -1838,7 +1846,7 @@ again: if (wait_for_settle) { wait_for_settle = FALSE; - NMTST_WAIT (300, { nmtstp_wait_for_signal (50); }); + NMTST_WAIT (300, { nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); }); goto again; } @@ -1846,6 +1854,442 @@ again: nmtstp_link_del (-1, ifindex_dummy0, IFACE_DUMMY0); } +/******************************************************************/ + +static void +_test_netns_setup (gpointer fixture, gconstpointer test_data) +{ + /* the singleton platform instance has netns support disabled. + * Destroy the instance before the test and re-create it afterwards. */ + g_object_unref (nm_platform_get ()); +} + +static void +_test_netns_teardown (gpointer fixture, gconstpointer test_data) +{ + /* re-create platform instance */ + SETUP (); +} + +static NMPlatform * +_test_netns_create_platform (void) +{ + NMPNetns *netns; + NMPlatform *platform; + + netns = nmp_netns_new (); + g_assert (NMP_IS_NETNS (netns)); + + platform = g_object_new (NM_TYPE_LINUX_PLATFORM, NM_PLATFORM_NETNS_SUPPORT, TRUE, NULL); + g_assert (NM_IS_LINUX_PLATFORM (platform)); + + nmp_netns_pop (netns); + g_object_unref (netns); + + return platform; +} + +static gboolean +_test_netns_check_skip (void) +{ + static int support = -1; + static int support_errsv = 0; + NMPNetns *netns; + + netns = nmp_netns_get_current (); + if (!netns) { + g_test_skip ("No netns support"); + return TRUE; + } + + g_assert (nmp_netns_get_fd_net (netns) > 0); + + if (support == -1) { + support = (setns (nmp_netns_get_fd_net (netns), CLONE_NEWNET) == 0); + if (!support) + support_errsv = errno; + } + if (!support) { + _LOGD ("setns() failed with \"%s\". This indicates missing support (valgrind?)", g_strerror (support_errsv)); + g_test_skip ("No netns support (setns failed)"); + return TRUE; + } + return FALSE; +} + +/******************************************************************/ + +static void +test_netns_general (gpointer fixture, gconstpointer test_data) +{ + gs_unref_object NMPlatform *platform_1 = NULL; + gs_unref_object NMPlatform *platform_2 = NULL; + NMPNetns *netns_tmp; + char sbuf[100]; + int i, j, k; + gboolean ethtool_support; + + if (_test_netns_check_skip ()) + return; + + platform_1 = g_object_new (NM_TYPE_LINUX_PLATFORM, NM_PLATFORM_NETNS_SUPPORT, TRUE, NULL); + platform_2 = _test_netns_create_platform (); + + /* add some dummy devices. The "other-*" devices are there to bump the ifindex */ + for (k = 0; k < 2; k++) { + NMPlatform *p = (k == 0 ? platform_1 : platform_2); + const char *id = (k == 0 ? "a" : "b"); + + for (i = 0, j = nmtst_get_rand_int () % 5; i < j; i++) + _ADD_DUMMY (p, nm_sprintf_buf (sbuf, "other-a-%s-%02d", id, i)); + + _ADD_DUMMY (p, "dummy1_"); + + for (i = 0, j = nmtst_get_rand_int () % 5; i < j; i++) + _ADD_DUMMY (p, nm_sprintf_buf (sbuf, "other-b-%s-%02d", id, i)); + + _ADD_DUMMY (p, nm_sprintf_buf (sbuf, "dummy2%s", id)); + + for (i = 0, j = nmtst_get_rand_int () % 5; i < j; i++) + _ADD_DUMMY (p, nm_sprintf_buf (sbuf, "other-c-%s-%02d", id, i)); + } + + g_assert_cmpstr (nm_platform_sysctl_get (platform_1, "/sys/devices/virtual/net/dummy1_/ifindex"), ==, nm_sprintf_buf (sbuf, "%d", nmtstp_link_get_typed (platform_1, 0, "dummy1_", NM_LINK_TYPE_DUMMY)->ifindex)); + g_assert_cmpstr (nm_platform_sysctl_get (platform_1, "/sys/devices/virtual/net/dummy2a/ifindex"), ==, nm_sprintf_buf (sbuf, "%d", nmtstp_link_get_typed (platform_1, 0, "dummy2a", NM_LINK_TYPE_DUMMY)->ifindex)); + g_assert_cmpstr (nm_platform_sysctl_get (platform_1, "/sys/devices/virtual/net/dummy2b/ifindex"), ==, NULL); + + g_assert_cmpstr (nm_platform_sysctl_get (platform_2, "/sys/devices/virtual/net/dummy1_/ifindex"), ==, nm_sprintf_buf (sbuf, "%d", nmtstp_link_get_typed (platform_2, 0, "dummy1_", NM_LINK_TYPE_DUMMY)->ifindex)); + g_assert_cmpstr (nm_platform_sysctl_get (platform_2, "/sys/devices/virtual/net/dummy2a/ifindex"), ==, NULL); + g_assert_cmpstr (nm_platform_sysctl_get (platform_2, "/sys/devices/virtual/net/dummy2b/ifindex"), ==, nm_sprintf_buf (sbuf, "%d", nmtstp_link_get_typed (platform_2, 0, "dummy2b", NM_LINK_TYPE_DUMMY)->ifindex)); + + for (i = 0; i < 10; i++) { + NMPlatform *pl; + const char *path; + + j = nmtst_get_rand_int () % 2; + + if (nmtst_get_rand_int () % 2) { + pl = platform_1; + if (nmtst_get_rand_int () % 2) + path = "/proc/sys/net/ipv6/conf/dummy1_/disable_ipv6"; + else + path = "/proc/sys/net/ipv6/conf/dummy2a/disable_ipv6"; + } else { + pl = platform_2; + if (nmtst_get_rand_int () % 2) + path = "/proc/sys/net/ipv6/conf/dummy1_/disable_ipv6"; + else + path = "/proc/sys/net/ipv6/conf/dummy2b/disable_ipv6"; + } + g_assert (nm_platform_sysctl_set (pl, path, nm_sprintf_buf (sbuf, "%d", j))); + g_assert_cmpstr (nm_platform_sysctl_get (pl, path), ==, nm_sprintf_buf (sbuf, "%d", j)); + } + g_assert_cmpstr (nm_platform_sysctl_get (platform_1, "/proc/sys/net/ipv6/conf/dummy2b/disable_ipv6"), ==, NULL); + g_assert_cmpstr (nm_platform_sysctl_get (platform_2, "/proc/sys/net/ipv6/conf/dummy2a/disable_ipv6"), ==, NULL); + + /* older kernels (Ubuntu 12.04) don't support ethtool -i for dummy devices. Work around that and + * skip asserts that are known to fail. */ + ethtool_support = nmtstp_run_command ("ethtool -i dummy1_ > /dev/null") == 0; + if (ethtool_support) { + g_assert ( nmp_utils_ethtool_get_driver_info ("dummy1_", NULL, NULL, NULL)); + g_assert ( nmp_utils_ethtool_get_driver_info ("dummy2a", NULL, NULL, NULL)); + g_assert (!nmp_utils_ethtool_get_driver_info ("dummy2b", NULL, NULL, NULL)); + g_assert_cmpint (nmtstp_run_command ("ethtool -i dummy1_ > /dev/null"), ==, 0); + g_assert_cmpint (nmtstp_run_command ("ethtool -i dummy2a > /dev/null"), ==, 0); + g_assert_cmpint (nmtstp_run_command ("ethtool -i dummy2b 2> /dev/null"), !=, 0); + } + + g_assert (nm_platform_netns_push (platform_2, &netns_tmp)); + + if (ethtool_support) { + g_assert ( nmp_utils_ethtool_get_driver_info ("dummy1_", NULL, NULL, NULL)); + g_assert (!nmp_utils_ethtool_get_driver_info ("dummy2a", NULL, NULL, NULL)); + g_assert ( nmp_utils_ethtool_get_driver_info ("dummy2b", NULL, NULL, NULL)); + g_assert_cmpint (nmtstp_run_command ("ethtool -i dummy1_ > /dev/null"), ==, 0); + g_assert_cmpint (nmtstp_run_command ("ethtool -i dummy2a 2> /dev/null"), !=, 0); + g_assert_cmpint (nmtstp_run_command ("ethtool -i dummy2b > /dev/null"), ==, 0); + } + + nmp_netns_pop (netns_tmp); +} + +/*****************************************************************************/ + +static void +test_netns_set_netns (gpointer fixture, gconstpointer test_data) +{ + NMPlatform *platforms[3]; + gs_unref_object NMPlatform *platform_0 = NULL; + gs_unref_object NMPlatform *platform_1 = NULL; + gs_unref_object NMPlatform *platform_2 = NULL; + nm_auto_pop_netns NMPNetns *netns_pop = NULL; + int i; + + if (_test_netns_check_skip ()) + return; + + platforms[0] = platform_0 = g_object_new (NM_TYPE_LINUX_PLATFORM, NM_PLATFORM_NETNS_SUPPORT, TRUE, NULL); + platforms[1] = platform_1 = _test_netns_create_platform (); + platforms[2] = platform_2 = _test_netns_create_platform (); + + i = nmtst_get_rand_int () % 4; + if (i != 3) + g_assert (nm_platform_netns_push (platforms[i], &netns_pop)); + +#define LINK_MOVE_NAME "link-move" + g_assert (!nm_platform_link_get_by_ifname (platform_1, LINK_MOVE_NAME)); + g_assert (!nm_platform_link_get_by_ifname (platform_2, LINK_MOVE_NAME)); + _ADD_DUMMY (platform_1, LINK_MOVE_NAME); + g_assert ( nm_platform_link_get_by_ifname (platform_1, LINK_MOVE_NAME)); + g_assert (!nm_platform_link_get_by_ifname (platform_2, LINK_MOVE_NAME)); + g_assert (nm_platform_link_set_netns (platform_1, + nm_platform_link_get_by_ifname (platform_1, LINK_MOVE_NAME)->ifindex, + nmp_netns_get_fd_net (nm_platform_netns_get (platform_2)))); + g_assert (!nm_platform_link_get_by_ifname (platform_1, LINK_MOVE_NAME)); + g_assert (!nm_platform_link_get_by_ifname (platform_2, LINK_MOVE_NAME)); + nmtstp_assert_wait_for_link (platform_2, LINK_MOVE_NAME, NM_LINK_TYPE_DUMMY, 100); + g_assert (!nm_platform_link_get_by_ifname (platform_1, LINK_MOVE_NAME)); + g_assert ( nm_platform_link_get_by_ifname (platform_2, LINK_MOVE_NAME)); +} + +/*****************************************************************************/ + +static char * +_get_current_namespace_id (int ns_type) +{ + const char *p; + GError *error = NULL; + char *id; + + switch (ns_type) { + case CLONE_NEWNET: + p = "/proc/self/ns/net"; + break; + case CLONE_NEWNS: + p = "/proc/self/ns/mnt"; + break; + default: + g_assert_not_reached (); + } + + id = g_file_read_link (p, &error); + g_assert_no_error (error); + g_assert (id); + return id; +} + +static char * +_get_sysctl_value (const char *path) +{ + char *data = NULL; + gs_free_error GError *error = NULL; + + if (!g_file_get_contents (path, &data, NULL, &error)) { + nmtst_assert_error (error, G_FILE_ERROR, G_FILE_ERROR_NOENT, NULL); + g_assert (!data); + } else { + g_assert_no_error (error); + g_assert (data); + g_strstrip (data); + } + return data; +} + +static void +test_netns_push (gpointer fixture, gconstpointer test_data) +{ + gs_unref_object NMPlatform *platform_0 = NULL; + gs_unref_object NMPlatform *platform_1 = NULL; + gs_unref_object NMPlatform *platform_2 = NULL; + nm_auto_pop_netns NMPNetns *netns_pop = NULL; + gs_unref_ptrarray GPtrArray *device_names = g_ptr_array_new_with_free_func (g_free); + int i, j; + const int ns_types_list[] = { CLONE_NEWNET, CLONE_NEWNS, CLONE_NEWNET | CLONE_NEWNS }; + const int ns_types_test[] = { CLONE_NEWNET, CLONE_NEWNS }; + typedef struct { + NMPlatform *platform; + const char *device_name; + const char *sysctl_path; + const char *sysctl_value; + const char *ns_net; + const char *ns_mnt; + } PlatformData; + PlatformData pl[3] = { }; + PlatformData *pl_base; + struct { + PlatformData *pl; + int ns_types; + } stack[6] = { }; + int nstack; + + if (_test_netns_check_skip ()) + return; + + pl[0].platform = platform_0 = g_object_new (NM_TYPE_LINUX_PLATFORM, NM_PLATFORM_NETNS_SUPPORT, TRUE, NULL); + pl[1].platform = platform_1 = _test_netns_create_platform (); + pl[2].platform = platform_2 = _test_netns_create_platform (); + + pl_base = &pl[0]; + i = nmtst_get_rand_int () % (G_N_ELEMENTS (pl) + 1); + if (i < G_N_ELEMENTS (pl)) { + pl_base = &pl[i]; + g_assert (nm_platform_netns_push (pl[i].platform, &netns_pop)); + } + + for (i = 0; i < G_N_ELEMENTS (pl); i++) { + nm_auto_pop_netns NMPNetns *netns_free = NULL; + char *tmp; + + g_assert (nm_platform_netns_push (pl[i].platform, &netns_free)); + + tmp = g_strdup_printf ("nmtst-dev-%d", i); + g_ptr_array_add (device_names, tmp); + pl[i].device_name = tmp; + + tmp = g_strdup_printf ("/proc/sys/net/ipv6/conf/%s/disable_ipv6", pl[i].device_name); + g_ptr_array_add (device_names, tmp); + pl[i].sysctl_path = tmp; + + pl[i].sysctl_value = nmtst_get_rand_int () % 2 ? "1" : "0"; + + _ADD_DUMMY (pl[i].platform, pl[i].device_name); + + g_assert (nm_platform_sysctl_set (pl[i].platform, pl[i].sysctl_path, pl[i].sysctl_value)); + + tmp = _get_current_namespace_id (CLONE_NEWNET); + g_ptr_array_add (device_names, tmp); + pl[i].ns_net = tmp; + + tmp = _get_current_namespace_id (CLONE_NEWNS); + g_ptr_array_add (device_names, tmp); + pl[i].ns_mnt = tmp; + } + + nstack = nmtst_get_rand_int () % (G_N_ELEMENTS (stack) + 1); + for (i = 0; i < nstack; i++) { + stack[i].pl = &pl[nmtst_get_rand_int () % G_N_ELEMENTS (pl)]; + stack[i].ns_types = ns_types_list[nmtst_get_rand_int () % G_N_ELEMENTS (ns_types_list)]; + + nmp_netns_push_type (nm_platform_netns_get (stack[i].pl->platform), stack[i].ns_types); + } + + /* pop some again. */ + for (i = nmtst_get_rand_int () % (nstack + 1); i > 0; i--) { + g_assert (nstack > 0); + nstack--; + nmp_netns_pop (nm_platform_netns_get (stack[nstack].pl->platform)); + } + + for (i = 0; i < G_N_ELEMENTS (ns_types_test); i++) { + int ns_type = ns_types_test[i]; + PlatformData *p; + gs_free char *current_namespace_id = NULL; + + p = pl_base; + for (j = nstack; j >= 1; ) { + j--; + if (NM_FLAGS_HAS (stack[j].ns_types, ns_type)) { + p = stack[j].pl; + break; + } + } + + current_namespace_id = _get_current_namespace_id (ns_type); + + if (ns_type == CLONE_NEWNET) { + g_assert_cmpstr (current_namespace_id, ==, p->ns_net); + for (j = 0; j < G_N_ELEMENTS (pl); j++) { + gs_free char *data = NULL; + + if (p == &pl[j]) + g_assert_cmpint (nmtstp_run_command ("ip link show %s 1>/dev/null", pl[j].device_name), ==, 0); + else + g_assert_cmpint (nmtstp_run_command ("ip link show %s 2>/dev/null", pl[j].device_name), !=, 0); + + data = _get_sysctl_value (pl[j].sysctl_path); + if (p == &pl[j]) + g_assert_cmpstr (data, ==, pl[j].sysctl_value); + else + g_assert (!data); + } + } else if (ns_type == CLONE_NEWNS) { + g_assert_cmpstr (current_namespace_id, ==, p->ns_mnt); + for (j = 0; j < G_N_ELEMENTS (pl); j++) { + char path[600]; + gs_free char *data = NULL; + + nm_sprintf_buf (path, "/sys/devices/virtual/net/%s/ifindex", pl[j].device_name); + + data = _get_sysctl_value (path); + if (p == &pl[j]) + g_assert_cmpstr (data, ==, nm_sprintf_buf (path, "%d", nmtstp_link_get_typed (p->platform, 0, p->device_name, NM_LINK_TYPE_DUMMY)->ifindex)); + else + g_assert (!data); + } + } else + g_assert_not_reached (); + } + + + for (i = nstack; i >= 1; ) { + i--; + nmp_netns_pop (nm_platform_netns_get (stack[i].pl->platform)); + } +} + +/*****************************************************************************/ + +static void +test_netns_bind_to_path (gpointer fixture, gconstpointer test_data) +{ +#define P_VAR_RUN "/var/run" +#define P_VAR_RUN_NETNS "/var/run/netns" +#define P_VAR_RUN_NETNS_BINDNAME "/var/run/netns/"P_NETNS_BINDNAME +#define P_NETNS_BINDNAME "nmtst-iproute2-netns" + gs_unref_object NMPlatform *platform_0 = NULL; + gs_unref_object NMPlatform *platform_1 = NULL; + gs_unref_object NMPlatform *platform_2 = NULL; + nm_auto_pop_netns NMPNetns *netns_pop = NULL; + NMPlatform *platforms[3]; + NMPNetns *netns; + int i; + + if (_test_netns_check_skip ()) + return; + + platforms[0] = platform_0 = g_object_new (NM_TYPE_LINUX_PLATFORM, NM_PLATFORM_NETNS_SUPPORT, TRUE, NULL); + platforms[1] = platform_1 = _test_netns_create_platform (); + platforms[2] = platform_2 = _test_netns_create_platform (); + + i = nmtst_get_rand_int () % 4; + if (i != 3) + g_assert (nm_platform_netns_push (platforms[i], &netns_pop)); + + g_assert_cmpint (mount ("tmpfs", P_VAR_RUN, "tmpfs", MS_NOATIME | MS_NODEV | MS_NOSUID, "mode=0755,size=32K"), ==, 0); + g_assert_cmpint (mkdir (P_VAR_RUN_NETNS, 755), ==, 0); + + i = (nmtst_get_rand_int () % 2) + 1; + netns = nm_platform_netns_get (platforms[i]); + + _ADD_DUMMY (platforms[i], "dummy2b"); + + g_assert (!g_file_test (P_VAR_RUN_NETNS_BINDNAME, G_FILE_TEST_EXISTS)); + g_assert_cmpint (nmtstp_run_command ("ip netns exec "P_NETNS_BINDNAME" true 2>/dev/null"), !=, 0); + + g_assert (nmp_netns_bind_to_path (netns, P_VAR_RUN_NETNS_BINDNAME, NULL)); + + g_assert (g_file_test (P_VAR_RUN_NETNS_BINDNAME, G_FILE_TEST_EXISTS)); + g_assert_cmpint (nmtstp_run_command ("ip netns exec "P_NETNS_BINDNAME" true"), ==, 0); + g_assert_cmpint (nmtstp_run_command ("ip netns exec "P_NETNS_BINDNAME" ip link show dummy2b 1>/dev/null"), ==, 0); + + g_assert (nmp_netns_bind_to_path_destroy (netns, P_VAR_RUN_NETNS_BINDNAME)); + + g_assert (!g_file_test (P_VAR_RUN_NETNS_BINDNAME, G_FILE_TEST_EXISTS)); + g_assert_cmpint (nmtstp_run_command ("ip netns exec "P_NETNS_BINDNAME" true 2>/dev/null"), !=, 0); + + g_assert_cmpint (umount (P_VAR_RUN), ==, 0); +} + /*****************************************************************************/ void @@ -1894,5 +2338,10 @@ setup_tests (void) g_test_add_func ("/link/nl-bugs/veth", test_nl_bugs_veth); g_test_add_func ("/link/nl-bugs/spurious-newlink", test_nl_bugs_spuroius_newlink); g_test_add_func ("/link/nl-bugs/spurious-dellink", test_nl_bugs_spuroius_dellink); + + g_test_add_vtable ("/general/netns/general", 0, NULL, _test_netns_setup, test_netns_general, _test_netns_teardown); + g_test_add_vtable ("/general/netns/set-netns", 0, NULL, _test_netns_setup, test_netns_set_netns, _test_netns_teardown); + g_test_add_vtable ("/general/netns/push", 0, NULL, _test_netns_setup, test_netns_push, _test_netns_teardown); + g_test_add_vtable ("/general/netns/bind-to-path", 0, NULL, _test_netns_setup, test_netns_bind_to_path, _test_netns_teardown); } } diff --git a/src/platform/tests/test-nmp-object.c b/src/platform/tests/test-nmp-object.c index 3b44abb8..d77170b3 100644 --- a/src/platform/tests/test-nmp-object.c +++ b/src/platform/tests/test-nmp-object.c @@ -223,9 +223,7 @@ test_cache_link (void) GUdevDevice *udev_device_3 = g_list_nth_data (global.udev_devices, 0); NMPCacheOpsType ops_type; - cache = nmp_cache_new (); - - nmp_cache_use_udev_set (cache, g_rand_int_range (nmtst_get_rand (), 0, 2)); + cache = nmp_cache_new (nmtst_get_rand_int () % 2); /* if we have a link, and don't set is_in_netlink, adding it has no effect. */ obj1 = nmp_object_new (NMP_OBJECT_TYPE_LINK, (NMPlatformObject *) &pl_link_2); diff --git a/src/platform/tests/test-route.c b/src/platform/tests/test-route.c index f5fa024b..85851854 100644 --- a/src/platform/tests/test-route.c +++ b/src/platform/tests/test-route.c @@ -314,7 +314,7 @@ test_ip4_zero_gateway (void) nmtstp_run_command_check ("ip route add 1.2.3.2/32 dev %s", DEVICE_NAME); NMTST_WAIT_ASSERT (100, { - nmtstp_wait_for_signal (10); + nmtstp_wait_for_signal (NM_PLATFORM_GET, 10); if ( nm_platform_ip4_route_get (NM_PLATFORM_GET, ifindex, nmtst_inet4_from_string ("1.2.3.1"), 32, 0) && nm_platform_ip4_route_get (NM_PLATFORM_GET, ifindex, nmtst_inet4_from_string ("1.2.3.2"), 32, 0)) break; @@ -322,7 +322,7 @@ test_ip4_zero_gateway (void) nmtstp_run_command_check ("ip route flush dev %s", DEVICE_NAME); - nmtstp_wait_for_signal (50); + nmtstp_wait_for_signal (NM_PLATFORM_GET, 50); nm_platform_process_events (NM_PLATFORM_GET); } |