mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
synced 2026-09-18 22:19:30 +02:00
net: enforce net sysctl registration
Replace the warning and file permission change with an error when an "unsafe" net sysctl registration is detected. One of the barriers preventing the const qualification of the ctl_tables in the net directory is the permission (->mode) change in ensure_safe_net_sysctl. This prep commit removes that barrier and ensures that the received ctl_table pointer to the net ctl_table register function is const. Signed-off-by: Joel Granados <joel.granados@kernel.org> Link: https://patch.msgid.link/20260810-jag-net_const_qualify-v4-1-77e888237c69@kernel.org Reviewed-by: Simon Horman <horms@kernel.org> Signed-off-by: Paolo Abeni <pabeni@redhat.com>
This commit is contained in:
committed by
Paolo Abeni
parent
68b3d4dbaf
commit
ef6cb145e2
@@ -525,12 +525,13 @@ struct ctl_table;
|
||||
#ifdef CONFIG_SYSCTL
|
||||
int net_sysctl_init(void);
|
||||
struct ctl_table_header *register_net_sysctl_sz(struct net *net, const char *path,
|
||||
struct ctl_table *table, size_t table_size);
|
||||
const struct ctl_table *table,
|
||||
size_t table_size);
|
||||
void unregister_net_sysctl_table(struct ctl_table_header *header);
|
||||
#else
|
||||
static inline int net_sysctl_init(void) { return 0; }
|
||||
static inline struct ctl_table_header *register_net_sysctl_sz(struct net *net,
|
||||
const char *path, struct ctl_table *table, size_t table_size)
|
||||
const char *path, const struct ctl_table *table, size_t table_size)
|
||||
{
|
||||
return NULL;
|
||||
}
|
||||
|
||||
+12
-11
@@ -114,16 +114,17 @@ out1:
|
||||
goto out;
|
||||
}
|
||||
|
||||
/* Verify that sysctls for non-init netns are safe by either:
|
||||
/* Return error when sysctls for non-init netns are unsafe by verifying:
|
||||
* 1) being read-only, or
|
||||
* 2) having a data pointer which points outside of the global kernel/module
|
||||
* data segment, and rather into the heap where a per-net object was
|
||||
* allocated.
|
||||
*/
|
||||
static void ensure_safe_net_sysctl(struct net *net, const char *path,
|
||||
struct ctl_table *table, size_t table_size)
|
||||
static int ensure_safe_net_sysctl(struct net *net, const char *path,
|
||||
const struct ctl_table *table,
|
||||
size_t table_size)
|
||||
{
|
||||
struct ctl_table *ent;
|
||||
const struct ctl_table *ent;
|
||||
|
||||
pr_debug("Registering net sysctl (net %p): %s\n", net, path);
|
||||
ent = table;
|
||||
@@ -149,24 +150,24 @@ static void ensure_safe_net_sysctl(struct net *net, const char *path,
|
||||
else
|
||||
continue;
|
||||
|
||||
/* If it is writable and points to kernel/module global
|
||||
* data, then it's probably a netns leak.
|
||||
*/
|
||||
/* Warn on netns leak. */
|
||||
WARN(1, "sysctl %s/%s: data points to %s global data: %ps\n",
|
||||
path, ent->procname, where, ent->data);
|
||||
|
||||
/* Make it "safe" by dropping writable perms */
|
||||
ent->mode &= ~0222;
|
||||
return -EACCES;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
struct ctl_table_header *register_net_sysctl_sz(struct net *net,
|
||||
const char *path,
|
||||
struct ctl_table *table,
|
||||
const struct ctl_table *table,
|
||||
size_t table_size)
|
||||
{
|
||||
if (!net_eq(net, &init_net))
|
||||
ensure_safe_net_sysctl(net, path, table, table_size);
|
||||
if (ensure_safe_net_sysctl(net, path, table, table_size))
|
||||
return NULL;
|
||||
|
||||
return __register_sysctl_table(&net->sysctls, path, table, table_size);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user