cloud-init: fix leaking iproutes for GCP provider

The routes in iproutes were leaked (and ownership stolen
in _nmc_mangle_connection(), leaving dangling pointers).

Fix that by using a GPtrArray instead.
This commit is contained in:
Thomas Haller 2023-05-10 12:48:22 +02:00
parent 302a5cebe4
commit 0888ed93f7
No known key found for this signature in database
GPG key ID: 29C2366E4DFC5728
4 changed files with 14 additions and 13 deletions

View file

@ -315,8 +315,9 @@ _nmc_mangle_connection(NMDevice *device,
addrs_new = g_ptr_array_new_full(config_data->ipv4s_len, (GDestroyNotify) nm_ip_address_unref);
rules_new =
g_ptr_array_new_full(config_data->ipv4s_len, (GDestroyNotify) nm_ip_routing_rule_unref);
routes_new = g_ptr_array_new_full(config_data->iproutes_len + !!config_data->ipv4s_len,
(GDestroyNotify) nm_ip_route_unref);
routes_new =
g_ptr_array_new_full(nm_g_ptr_array_len(config_data->iproutes) + !!config_data->ipv4s_len,
(GDestroyNotify) nm_ip_route_unref);
if (remote_s_ip) {
guint len;
@ -422,8 +423,8 @@ _nmc_mangle_connection(NMDevice *device,
}
}
for (i = 0; i < config_data->iproutes_len; ++i)
g_ptr_array_add(routes_new, config_data->iproutes_arr[i]);
for (i = 0; i < nm_g_ptr_array_len(config_data->iproutes); i++)
g_ptr_array_add(routes_new, _nm_ip_route_ref(config_data->iproutes->pdata[i]));
addrs_changed = nmcs_setting_ip_replace_ipv4_addresses(s_ip,
(NMIPAddress **) addrs_new->pdata,

View file

@ -112,7 +112,6 @@ _get_config_fip_cb(GObject *source, GAsyncResult *result, gpointer user_data)
GCPIfaceData *iface_data = user_data;
gs_free_error GError *error = NULL;
gs_free char *ipaddr = NULL;
NMIPRoute **routes_arr;
NMIPRoute *route_new;
nm_http_client_poll_req_finish(NM_HTTP_CLIENT(source), result, NULL, &response, &error);
@ -137,15 +136,14 @@ _get_config_fip_cb(GObject *source, GAsyncResult *result, gpointer user_data)
ipaddr);
iface_get_config = iface_data->iface_get_config;
routes_arr = iface_get_config->iproutes_arr;
route_new = nm_ip_route_new(AF_INET, ipaddr, 32, NULL, 100, &error);
if (error)
goto out_done;
nm_ip_route_set_attribute(route_new, NM_IP_ROUTE_ATTRIBUTE_TYPE, g_variant_new_string("local"));
routes_arr[iface_get_config->iproutes_len] = route_new;
++iface_get_config->iproutes_len;
g_ptr_array_add(iface_get_config->iproutes, route_new);
out_done:
if (!error) {
@ -215,7 +213,8 @@ _get_config_ips_list_cb(GObject *source, GAsyncResult *result, gpointer user_dat
goto out_error;
}
iface_data->iface_get_config->iproutes_arr = g_new(NMIPRoute *, iface_data->n_fips_pending);
iface_data->iface_get_config->iproutes =
g_ptr_array_new_full(iface_data->n_fips_pending, (GDestroyNotify) nm_ip_route_unref);
for (i = 0; i < uri_arr->len; ++i) {
const char *str = uri_arr->pdata[i];

View file

@ -216,7 +216,7 @@ _iface_data_free(gpointer data)
NMCSProviderGetConfigIfaceData *iface_data = data;
g_free(iface_data->ipv4s_arr);
g_free(iface_data->iproutes_arr);
nm_g_ptr_array_unref(iface_data->iproutes);
g_free((char *) iface_data->hwaddr);
nm_g_slice_free(iface_data);

View file

@ -34,8 +34,8 @@ typedef struct {
bool has_cidr : 1;
bool has_gateway : 1;
NMIPRoute **iproutes_arr;
gsize iproutes_len;
/* Array of NMIPRoute (must own/free the entries). */
GPtrArray *iproutes;
/* TRUE, if the configuration was requested via hwaddrs argument to
* nmcs_provider_get_config(). */
@ -59,7 +59,8 @@ static inline gboolean
nmcs_provider_get_config_iface_data_is_valid(const NMCSProviderGetConfigIfaceData *config_data)
{
return config_data && config_data->iface_idx >= 0
&& ((config_data->has_ipv4s && config_data->has_cidr) || config_data->iproutes_len);
&& ((config_data->has_ipv4s && config_data->has_cidr)
|| nm_g_ptr_array_len(config_data->iproutes) > 0);
}
/*****************************************************************************/