Commit 6e01238a authored by Thomas Haller's avatar Thomas Haller
Browse files

core: don't use static buffer for nm_utils_ip4_property_path()

and nm_utils_ip6_property_path(). The API with static buffers
looks a bit nicer. But I think they are dangerous, because
we tend to pass the buffer down several layers of the stack, and
it's not immediately clear, that we don't overwrite the static
buffer again (which we probably did not, but it's hard to verify
that there is no bug there).
parent b27a10bd
......@@ -852,26 +852,29 @@ nm_device_ipv4_sysctl_set (NMDevice *self, const char *property, const char *val
NMPlatform *platform = nm_device_get_platform (self);
gs_free char *value_to_free = NULL;
const char *value_to_set;
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
if (value) {
value_to_set = value;
} else {
/* Set to a default value when we've got a NULL @value. */
value_to_free = nm_platform_sysctl_get (platform,
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path ("default", property)));
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path (buf, "default", property)));
value_to_set = value_to_free;
}
return nm_platform_sysctl_set (platform,
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path (nm_device_get_ip_iface (self), property)),
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path (buf, nm_device_get_ip_iface (self), property)),
value_to_set);
}
static guint32
nm_device_ipv4_sysctl_get_uint32 (NMDevice *self, const char *property, guint32 fallback)
{
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
return nm_platform_sysctl_get_int_checked (nm_device_get_platform (self),
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path (nm_device_get_ip_iface (self), property)),
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path (buf, nm_device_get_ip_iface (self), property)),
10,
0,
G_MAXUINT32,
......@@ -881,14 +884,18 @@ nm_device_ipv4_sysctl_get_uint32 (NMDevice *self, const char *property, guint32
gboolean
nm_device_ipv6_sysctl_set (NMDevice *self, const char *property, const char *value)
{
return nm_platform_sysctl_set (nm_device_get_platform (self), NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (nm_device_get_ip_iface (self), property)), value);
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
return nm_platform_sysctl_set (nm_device_get_platform (self), NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (buf, nm_device_get_ip_iface (self), property)), value);
}
static guint32
nm_device_ipv6_sysctl_get_uint32 (NMDevice *self, const char *property, guint32 fallback)
{
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
return nm_platform_sysctl_get_int_checked (nm_device_get_platform (self),
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (nm_device_get_ip_iface (self), property)),
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (buf, nm_device_get_ip_iface (self), property)),
10,
0,
G_MAXUINT32,
......@@ -7678,7 +7685,9 @@ save_ip6_properties (NMDevice *self)
g_hash_table_remove_all (priv->ip6_saved_properties);
for (i = 0; i < G_N_ELEMENTS (ip6_properties_to_save); i++) {
value = nm_platform_sysctl_get (nm_device_get_platform (self), NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (ifname, ip6_properties_to_save[i])));
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
value = nm_platform_sysctl_get (nm_device_get_platform (self), NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (buf, ifname, ip6_properties_to_save[i])));
if (value) {
g_hash_table_insert (priv->ip6_saved_properties,
(char *) ip6_properties_to_save[i],
......@@ -7738,9 +7747,11 @@ set_nm_ipv6ll (NMDevice *self, gboolean enable)
}
if (enable) {
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
/* Bounce IPv6 to ensure the kernel stops IPv6LL address generation */
value = nm_platform_sysctl_get (nm_device_get_platform (self),
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (nm_device_get_ip_iface (self), "disable_ipv6")));
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (buf, nm_device_get_ip_iface (self), "disable_ipv6")));
if (g_strcmp0 (value, "0") == 0)
nm_device_ipv6_sysctl_set (self, "disable_ipv6", "1");
g_free (value);
......
......@@ -531,8 +531,10 @@ start (NMNDisc *ndisc)
static inline int
ipv6_sysctl_get (NMPlatform *platform, const char *ifname, const char *property, int min, int max, int defval)
{
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
return (int) nm_platform_sysctl_get_int_checked (platform,
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (ifname, property)),
NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (buf, ifname, property)),
10,
min,
max,
......
......@@ -2525,55 +2525,63 @@ nm_utils_monotonic_timestamp_as_boottime (gint64 timestamp, gint64 timestamp_ns_
#define IPV6_PROPERTY_DIR "/proc/sys/net/ipv6/conf/"
#define IPV4_PROPERTY_DIR "/proc/sys/net/ipv4/conf/"
G_STATIC_ASSERT (sizeof (IPV4_PROPERTY_DIR) == sizeof (IPV6_PROPERTY_DIR));
G_STATIC_ASSERT (NM_STRLEN (IPV6_PROPERTY_DIR) + IFNAMSIZ + 60 == NM_UTILS_IP_PROPERTY_PATH_BUFSIZE);
static const char *
_get_property_path (const char *ifname,
_get_property_path (char *buf,
const char *ifname,
const char *property,
gboolean ipv6)
{
static char path[sizeof (IPV6_PROPERTY_DIR) + IFNAMSIZ + 32];
int len;
nm_assert (buf);
ifname = NM_ASSERT_VALID_PATH_COMPONENT (ifname);
property = NM_ASSERT_VALID_PATH_COMPONENT (property);
len = g_snprintf (path,
sizeof (path),
len = g_snprintf (buf,
NM_UTILS_IP_PROPERTY_PATH_BUFSIZE,
"%s%s/%s",
ipv6 ? IPV6_PROPERTY_DIR : IPV4_PROPERTY_DIR,
ifname,
property);
g_assert (len < sizeof (path) - 1);
return path;
g_assert (len < NM_UTILS_IP_PROPERTY_PATH_BUFSIZE - 1);
return buf;
}
/**
* nm_utils_ip6_property_path:
* @buf: the output buffer where to write the path. It
* must be at least NM_UTILS_IP_PROPERTY_PATH_BUFSIZE bytes
* long.
* @ifname: an interface name
* @property: a property name
*
* Returns the path to IPv6 property @property on @ifname. Note that
* this uses a static buffer.
* Returns: the path to IPv6 property @property on @ifname. Note that
* this returns the input argument @buf.
*/
const char *
nm_utils_ip6_property_path (const char *ifname, const char *property)
nm_utils_ip6_property_path (char *buf, const char *ifname, const char *property)
{
return _get_property_path (ifname, property, TRUE);
return _get_property_path (buf, ifname, property, TRUE);
}
/**
* nm_utils_ip4_property_path:
* @buf: the output buffer where to write the path. It
* must be at least NM_UTILS_IP_PROPERTY_PATH_BUFSIZE bytes
* long.
* @ifname: an interface name
* @property: a property name
*
* Returns the path to IPv4 property @property on @ifname. Note that
* this uses a static buffer.
* Returns: the path to IPv6 property @property on @ifname. Note that
* this returns the input argument @buf.
*/
const char *
nm_utils_ip4_property_path (const char *ifname, const char *property)
nm_utils_ip4_property_path (char *buf, const char *ifname, const char *property)
{
return _get_property_path (ifname, property, FALSE);
return _get_property_path (buf, ifname, property, FALSE);
}
gboolean
......
......@@ -248,8 +248,11 @@ gint64 nm_utils_monotonic_timestamp_as_boottime (gint64 timestamp, gint64 timest
gboolean nm_utils_is_valid_path_component (const char *name);
const char *NM_ASSERT_VALID_PATH_COMPONENT (const char *name);
const char *nm_utils_ip6_property_path (const char *ifname, const char *property);
const char *nm_utils_ip4_property_path (const char *ifname, const char *property);
#define NM_UTILS_IP_PROPERTY_PATH_BUFSIZE 100
const char *nm_utils_ip6_property_path (char *buf, const char *ifname, const char *property);
const char *nm_utils_ip4_property_path (char *buf, const char *ifname, const char *property);
gboolean nm_utils_is_specific_hostname (const char *name);
......
......@@ -222,9 +222,10 @@ ndisc_config_changed (NMNDisc *ndisc, const NMNDiscData *rdata, guint changed_in
if (changed & NM_NDISC_CONFIG_MTU) {
char val[16];
char sysctl_path_buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
g_snprintf (val, sizeof (val), "%d", rdata->mtu);
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (global_opt.ifname, "mtu")), val);
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (sysctl_path_buf, global_opt.ifname, "mtu")), val);
}
nm_ip6_config_merge (existing, ndisc_config, NM_IP_CONFIG_MERGE_DEFAULT, 0);
......@@ -344,6 +345,7 @@ main (int argc, char *argv[])
gconstpointer tmp;
gs_free NMUtilsIPv6IfaceId *iid = NULL;
guint sd_id;
char sysctl_path_buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
nm_g_type_init ();
......@@ -448,7 +450,7 @@ main (int argc, char *argv[])
}
if (global_opt.dhcp4_address) {
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path (global_opt.ifname, "promote_secondaries")), "1");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip4_property_path (sysctl_path_buf, global_opt.ifname, "promote_secondaries")), "1");
dhcp4_client = nm_dhcp_manager_start_ip4 (nm_dhcp_manager_get (),
nm_platform_get_multi_idx (NM_PLATFORM_GET),
......@@ -497,10 +499,10 @@ main (int argc, char *argv[])
if (iid)
nm_ndisc_set_iid (ndisc, *iid);
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (global_opt.ifname, "accept_ra")), "1");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (global_opt.ifname, "accept_ra_defrtr")), "0");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (global_opt.ifname, "accept_ra_pinfo")), "0");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (global_opt.ifname, "accept_ra_rtr_pref")), "0");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (sysctl_path_buf, global_opt.ifname, "accept_ra")), "1");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (sysctl_path_buf, global_opt.ifname, "accept_ra_defrtr")), "0");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (sysctl_path_buf, global_opt.ifname, "accept_ra_pinfo")), "0");
nm_platform_sysctl_set (NM_PLATFORM_GET, NMP_SYSCTL_PATHID_ABSOLUTE (nm_utils_ip6_property_path (sysctl_path_buf, global_opt.ifname, "accept_ra_rtr_pref")), "0");
g_signal_connect (NM_PLATFORM_GET,
NM_PLATFORM_SIGNAL_IP6_ADDRESS_CHANGED,
......
......@@ -414,6 +414,7 @@ nm_platform_sysctl_set_ip6_hop_limit_safe (NMPlatform *self, const char *iface,
{
const char *path;
gint64 cur;
char buf[NM_UTILS_IP_PROPERTY_PATH_BUFSIZE];
_CHECK_SELF (self, klass, FALSE);
......@@ -425,7 +426,7 @@ nm_platform_sysctl_set_ip6_hop_limit_safe (NMPlatform *self, const char *iface,
if (value < 10)
return FALSE;
path = nm_utils_ip6_property_path (iface, "hop_limit");
path = nm_utils_ip6_property_path (buf, iface, "hop_limit");
cur = nm_platform_sysctl_get_int_checked (self, NMP_SYSCTL_PATHID_ABSOLUTE (path), 10, 1, G_MAXINT32, -1);
/* only allow increasing the hop-limit to avoid DOS by an attacker
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment