proc_sysctl: move helper which creates required subdirectories

Move the code which creates the subdirectories for a ctl table
into a helper routine so to make it easier to review. Document
the goal.

This creates no functional changes.

Reviewed-by: John Johansen <john.johansen@canonical.com>
Signed-off-by: Luis Chamberlain <mcgrof@kernel.org>
This commit is contained in:
Luis Chamberlain 2023-03-02 12:28:17 -08:00
parent 67ff32289a
commit b2f56e5574

View File

@ -1283,6 +1283,35 @@ out:
return err; return err;
} }
/* Find the directory for the ctl_table. If one is not found create it. */
static struct ctl_dir *sysctl_mkdir_p(struct ctl_dir *dir, const char *path)
{
const char *name, *nextname;
for (name = path; name; name = nextname) {
int namelen;
nextname = strchr(name, '/');
if (nextname) {
namelen = nextname - name;
nextname++;
} else {
namelen = strlen(name);
}
if (namelen == 0)
continue;
/*
* namelen ensures if name is "foo/bar/yay" only foo is
* registered first. We traverse as if using mkdir -p and
* return a ctl_dir for the last directory entry.
*/
dir = get_subdir(dir, name, namelen);
if (IS_ERR(dir))
break;
}
return dir;
}
/** /**
* __register_sysctl_table - register a leaf sysctl table * __register_sysctl_table - register a leaf sysctl table
* @set: Sysctl tree to register on * @set: Sysctl tree to register on
@ -1334,7 +1363,6 @@ struct ctl_table_header *__register_sysctl_table(
{ {
struct ctl_table_root *root = set->dir.header.root; struct ctl_table_root *root = set->dir.header.root;
struct ctl_table_header *header; struct ctl_table_header *header;
const char *name, *nextname;
struct ctl_dir *dir; struct ctl_dir *dir;
struct ctl_table *entry; struct ctl_table *entry;
struct ctl_node *node; struct ctl_node *node;
@ -1359,29 +1387,9 @@ struct ctl_table_header *__register_sysctl_table(
dir->header.nreg++; dir->header.nreg++;
spin_unlock(&sysctl_lock); spin_unlock(&sysctl_lock);
/* Find the directory for the ctl_table */ dir = sysctl_mkdir_p(dir, path);
for (name = path; name; name = nextname) {
int namelen;
nextname = strchr(name, '/');
if (nextname) {
namelen = nextname - name;
nextname++;
} else {
namelen = strlen(name);
}
if (namelen == 0)
continue;
/*
* namelen ensures if name is "foo/bar/yay" only foo is
* registered first. We traverse as if using mkdir -p and
* return a ctl_dir for the last directory entry.
*/
dir = get_subdir(dir, name, namelen);
if (IS_ERR(dir)) if (IS_ERR(dir))
goto fail; goto fail;
}
spin_lock(&sysctl_lock); spin_lock(&sysctl_lock);
if (insert_header(dir, header)) if (insert_header(dir, header))
goto fail_put_dir_locked; goto fail_put_dir_locked;