summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorThomas Haller <thaller@redhat.com>2020-06-07 18:15:15 +0200
committerThomas Haller <thaller@redhat.com>2020-06-11 16:51:50 +0200
commitae0da6dd6084622d25de33c436f4694038ed99e7 (patch)
treeea9d351fc624724674502af139ed4ac42b2ba202
parentcf4763207f426e7d97f6be9684ead30a2077152c (diff)
downloadNetworkManager-ae0da6dd6084622d25de33c436f4694038ed99e7.tar.gz
lldp: use GVariantBuilder instead of GVariantDict
GVariantDict is basically a GHashTable, and during g_variant_dict_end() it uses a GVariantBuilder to create the variant. This is totally unnecessary in this case. It's probably unnecessary in most use cases, because commonly we construct variants in a determined series of steps and don't need to add/remove keys. Aside the overhead, GHashTable also does not give a stable sort order, which seems a pretty bad property in this case. Note that the code changes the order in which we call g_variant_builder_add() for the fields in code, to preserve the previous order that GVariantDict actually created (at least, with my version of glib).
-rw-r--r--src/devices/nm-lldp-listener.c96
1 files changed, 49 insertions, 47 deletions
diff --git a/src/devices/nm-lldp-listener.c b/src/devices/nm-lldp-listener.c
index 3323125c7e..5d9bb42158 100644
--- a/src/devices/nm-lldp-listener.c
+++ b/src/devices/nm-lldp-listener.c
@@ -224,11 +224,17 @@ lldp_neighbor_equal (LldpNeighbor *a, LldpNeighbor *b)
}
static GVariant *
-parse_management_address_tlv (uint8_t *data, gsize len)
+parse_management_address_tlv (const uint8_t *data, gsize len)
{
- GVariantDict dict;
- GVariant *variant;
- gsize addr_len, oid_len;
+ GVariantBuilder builder;
+ gsize addr_len;
+ const guint8 *v_object_id_arr;
+ gsize v_object_id_len;
+ const guint8 *v_address_arr;
+ gsize v_address_len;
+ guint32 v_interface_number;
+ guint32 v_interface_number_subtype;
+ guint32 v_address_subtype;
/* 802.1AB-2009 - Figure 8-11
*
@@ -243,7 +249,7 @@ parse_management_address_tlv (uint8_t *data, gsize len)
*/
if (len < 11)
- goto err;
+ return NULL;
nm_assert ((data[0] >> 1) == SD_LLDP_TYPE_MGMT_ADDRESS);
nm_assert ((((data[0] & 1) << 8) + data[1]) + 2 == len);
@@ -253,43 +259,42 @@ parse_management_address_tlv (uint8_t *data, gsize len)
addr_len = *data; /* length of (address subtype + address) */
if (addr_len < 2 || addr_len > 32)
- goto err;
+ return NULL;
if (len < ( 1 /* address stringth length */
+ addr_len /* address subtype + address */
+ 5 /* interface */
+ 1)) /* oid */
- goto err;
-
- g_variant_dict_init (&dict, NULL);
+ return NULL;
data++;
len--;
- g_variant_dict_insert (&dict, "address-subtype", "u", (guint32) *data);
- variant = g_variant_new_fixed_array (G_VARIANT_TYPE_BYTE, data + 1, addr_len - 1, 1);
- g_variant_dict_insert_value (&dict, "address", variant);
+ v_address_subtype = *data;
+ v_address_arr = &data[1];
+ v_address_len = addr_len - 1;
data += addr_len;
len -= addr_len;
- g_variant_dict_insert (&dict, "interface-number-subtype", "u", (guint32) *data);
+ v_interface_number_subtype = *data;
data++;
len--;
- g_variant_dict_insert (&dict, "interface-number", "u", unaligned_read_be32 (data));
+ v_interface_number = unaligned_read_be32 (data);
data += 4;
len -= 4;
- oid_len = *data;
-
- if (len < (1 + oid_len))
- goto err;
-
+ v_object_id_len = *data;
+ if (len < (1 + v_object_id_len))
+ return NULL;
data++;
- variant = g_variant_new_fixed_array (G_VARIANT_TYPE_BYTE, data, oid_len, 1);
- g_variant_dict_insert_value (&dict, "object-id", variant);
- return g_variant_dict_end (&dict);
-err:
- g_variant_dict_clear (&dict);
- return NULL;
+ v_object_id_arr = data;
+
+ g_variant_builder_init (&builder, G_VARIANT_TYPE ("a{sv}"));
+ nm_g_variant_builder_add_sv_uint32 (&builder, "address-subtype", v_address_subtype);
+ nm_g_variant_builder_add_sv_bytearray (&builder, "object-id", v_object_id_arr, v_object_id_len);
+ nm_g_variant_builder_add_sv_uint32 (&builder, "interface-number", v_interface_number);
+ nm_g_variant_builder_add_sv_bytearray (&builder, "address", v_address_arr, v_address_len);
+ nm_g_variant_builder_add_sv_uint32 (&builder, "interface-number-subtype", v_interface_number_subtype);
+ return g_variant_builder_end (&builder);
}
static LldpNeighbor *
@@ -448,6 +453,7 @@ lldp_neighbor_to_variant (LldpNeighbor *neigh)
GVariant *v_ieee_802_3_mac_phy_conf = NULL;
GVariant *v_ieee_802_3_power_via_mdi = NULL;
GVariant *v_ieee_802_3_max_frame_size = NULL;
+ GVariantBuilder tmp_builder;
GVariant *tmp_variant;
do {
@@ -511,8 +517,6 @@ lldp_neighbor_to_variant (LldpNeighbor *neigh)
len -= 6;
if (memcmp (oui, SD_LLDP_OUI_802_1, sizeof (oui)) == 0) {
- GVariantDict dict;
-
switch (subtype) {
case SD_LLDP_OUI_802_1_SUBTYPE_PORT_VLAN_ID:
if (len != 2)
@@ -528,10 +532,10 @@ lldp_neighbor_to_variant (LldpNeighbor *neigh)
v_ieee_802_1_ppvid = g_variant_new_uint32 (unaligned_read_be16 (&data8[1]));
g_variant_builder_init (&v_ieee_802_1_ppvids, G_VARIANT_TYPE ("aa{sv}"));
}
- g_variant_dict_init (&dict, NULL);
- g_variant_dict_insert (&dict, "ppvid", "u", (guint32) unaligned_read_be16 (&data8[1]));
- g_variant_dict_insert (&dict, "flags", "u", (guint32) data8[0]);
- g_variant_builder_add_value (&v_ieee_802_1_ppvids, g_variant_dict_end (&dict));
+ g_variant_builder_init (&tmp_builder, G_VARIANT_TYPE ("a{sv}"));
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "flags", data8[0]);
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "ppvid", unaligned_read_be16 (&data8[1]));
+ g_variant_builder_add_value (&v_ieee_802_1_ppvids, g_variant_builder_end (&tmp_builder));
break;
case SD_LLDP_OUI_802_1_SUBTYPE_VLAN_NAME: {
gs_free char *name_to_free = NULL;
@@ -556,29 +560,27 @@ lldp_neighbor_to_variant (LldpNeighbor *neigh)
v_ieee_802_1_vlan_name = g_variant_new_string (name);
g_variant_builder_init (&v_ieee_802_1_vlans, G_VARIANT_TYPE ("aa{sv}"));
}
- g_variant_dict_init (&dict, NULL);
- g_variant_dict_insert (&dict, "vid", "u", vid);
- g_variant_dict_insert (&dict, "name", "s", name);
- g_variant_builder_add_value (&v_ieee_802_1_vlans, g_variant_dict_end (&dict));
+ g_variant_builder_init (&tmp_builder, G_VARIANT_TYPE ("a{sv}"));
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "vid", vid);
+ nm_g_variant_builder_add_sv_str (&tmp_builder, "name", name);
+ g_variant_builder_add_value (&v_ieee_802_1_vlans, g_variant_builder_end (&tmp_builder));
break;
}
default:
continue;
}
} else if (memcmp (oui, SD_LLDP_OUI_802_3, sizeof (oui)) == 0) {
- GVariantDict dict;
-
switch (subtype) {
case SD_LLDP_OUI_802_3_SUBTYPE_MAC_PHY_CONFIG_STATUS:
if (len != 5)
continue;
if (!v_ieee_802_3_mac_phy_conf) {
- g_variant_dict_init (&dict, NULL);
- g_variant_dict_insert (&dict, "autoneg", "u", (guint32) data8[0]);
- g_variant_dict_insert (&dict, "pmd-autoneg-cap", "u", (guint32) unaligned_read_be16 (&data8[1]));
- g_variant_dict_insert (&dict, "operational-mau-type", "u", (guint32) unaligned_read_be16 (&data8[3]));
- v_ieee_802_3_mac_phy_conf = g_variant_dict_end (&dict);
+ g_variant_builder_init (&tmp_builder, G_VARIANT_TYPE ("a{sv}"));
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "operational-mau-type", unaligned_read_be16 (&data8[3]));
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "autoneg", data8[0]);
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "pmd-autoneg-cap", unaligned_read_be16 (&data8[1]));
+ v_ieee_802_3_mac_phy_conf = g_variant_builder_end (&tmp_builder);
}
break;
case SD_LLDP_OUI_802_3_SUBTYPE_POWER_VIA_MDI:
@@ -586,11 +588,11 @@ lldp_neighbor_to_variant (LldpNeighbor *neigh)
continue;
if (!v_ieee_802_3_power_via_mdi) {
- g_variant_dict_init (&dict, NULL);
- g_variant_dict_insert (&dict, "mdi-power-support", "u", (guint32) data8[0]);
- g_variant_dict_insert (&dict, "pse-power-pair", "u", (guint32) data8[1]);
- g_variant_dict_insert (&dict, "power-class", "u", (guint32) data8[2]);
- v_ieee_802_3_power_via_mdi = g_variant_dict_end (&dict);
+ g_variant_builder_init (&tmp_builder, G_VARIANT_TYPE ("a{sv}"));
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "pse-power-pair", data8[1]);
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "mdi-power-support", data8[0]);
+ nm_g_variant_builder_add_sv_uint32 (&tmp_builder, "power-class", data8[2]);
+ v_ieee_802_3_power_via_mdi = g_variant_builder_end (&tmp_builder);
}
break;
case SD_LLDP_OUI_802_3_SUBTYPE_MAXIMUM_FRAME_SIZE: