linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table
@ 2022-03-01 11:53 Meng Tang
  2022-03-01 11:53 ` [PATCH v2 2/2] fs/proc: sysctl: optimize register single " Meng Tang
                   ` (4 more replies)
  0 siblings, 5 replies; 6+ messages in thread
From: Meng Tang @ 2022-03-01 11:53 UTC (permalink / raw)
  To: mcgrof, keescook, yzaikin, ebiederm, willy
  Cc: nixiaoming, nizhen, zhanglianjie, sujiaxun, linux-kernel,
	linux-fsdevel, Meng Tang

Sysctls are being moved out of kernel/sysctl.c and out to
their own respective subsystems / users to help with easier
maintance and avoid merge conflicts. But when we move just
one entry and to its own new file the last entry for this
new file must be empty, so we are essentialy bloating the
kernel one extra empty entry per each newly moved sysctl.

To help with this, this adds support for registering just
one ctl_table, therefore not bloating the kernel when we
move a single ctl_table to its own file.

Suggested-by: Matthew Wilcox <willy@infradead.org>
Signed-off-by: Meng Tang <tangmeng@uniontech.com>
---
 fs/proc/proc_sysctl.c  | 346 +++++++++++++++++++++++++++++++++++++++++
 include/linux/sysctl.h |   3 +
 2 files changed, 349 insertions(+)

diff --git a/fs/proc/proc_sysctl.c b/fs/proc/proc_sysctl.c
index 6c87c99f0856..28c54e494c6a 100644
--- a/fs/proc/proc_sysctl.c
+++ b/fs/proc/proc_sysctl.c
@@ -101,7 +101,9 @@ static void drop_sysctl_table(struct ctl_table_header *header);
 static int sysctl_follow_link(struct ctl_table_header **phead,
 	struct ctl_table **pentry);
 static int insert_links(struct ctl_table_header *head);
+static int insert_links_single(struct ctl_table_header *head);
 static void put_links(struct ctl_table_header *header);
+static void put_links_single(struct ctl_table_header *header);
 
 static void sysctl_print_dir(struct ctl_dir *dir)
 {
@@ -198,6 +200,25 @@ static void erase_entry(struct ctl_table_header *head, struct ctl_table *entry)
 	rb_erase(node, &head->parent->root);
 }
 
+static void init_header_single(struct ctl_table_header *head,
+	struct ctl_table_root *root, struct ctl_table_set *set,
+	struct ctl_node *node, struct ctl_table *table)
+{
+	head->ctl_table = table;
+	head->ctl_table_arg = table;
+	head->used = 0;
+	head->count = 1;
+	head->nreg = 1;
+	head->unregistering = NULL;
+	head->root = root;
+	head->set = set;
+	head->parent = NULL;
+	head->node = node;
+	INIT_HLIST_HEAD(&head->inodes);
+	if (node)
+		node->header = head;
+}
+
 static void init_header(struct ctl_table_header *head,
 	struct ctl_table_root *root, struct ctl_table_set *set,
 	struct ctl_node *node, struct ctl_table *table)
@@ -227,6 +248,42 @@ static void erase_header(struct ctl_table_header *head)
 		erase_entry(head, entry);
 }
 
+static int insert_header_single(struct ctl_dir *dir, struct ctl_table_header *header)
+{
+	int err;
+
+	/* Is this a permanently empty directory? */
+	if (is_empty_dir(&dir->header))
+		return -EROFS;
+
+	/* Am I creating a permanently empty directory? */
+	if (header->ctl_table == sysctl_mount_point) {
+		if (!RB_EMPTY_ROOT(&dir->root))
+			return -EINVAL;
+		set_empty_dir(dir);
+	}
+
+	dir->header.nreg++;
+	header->parent = dir;
+	err = insert_links_single(header);
+	if (err)
+		goto fail_links;
+
+	err = insert_entry(header, header->ctl_table);
+	if (err)
+		goto fail;
+
+	return 0;
+fail:
+	erase_entry(header, header->ctl_table);
+	put_links_single(header);
+fail_links:
+	if (header->ctl_table == sysctl_mount_point)
+		clear_empty_dir(dir);
+	header->parent = NULL;
+	drop_sysctl_table(&dir->header);
+	return err;
+}
 static int insert_header(struct ctl_dir *dir, struct ctl_table_header *header)
 {
 	struct ctl_table *entry;
@@ -1128,6 +1185,40 @@ static int sysctl_check_table_array(const char *path, struct ctl_table *table)
 	return err;
 }
 
+static int sysctl_check_table_single(const char *path, struct ctl_table *table)
+{
+	int err = 0;
+
+	if (table->child)
+		err |= sysctl_err(path, table, "Not a file");
+
+	if ((table->proc_handler == proc_dostring) ||
+	    (table->proc_handler == proc_dointvec) ||
+	    (table->proc_handler == proc_douintvec) ||
+	    (table->proc_handler == proc_douintvec_minmax) ||
+	    (table->proc_handler == proc_dointvec_minmax) ||
+	    (table->proc_handler == proc_dou8vec_minmax) ||
+	    (table->proc_handler == proc_dointvec_jiffies) ||
+	    (table->proc_handler == proc_dointvec_userhz_jiffies) ||
+	    (table->proc_handler == proc_dointvec_ms_jiffies) ||
+	    (table->proc_handler == proc_doulongvec_minmax) ||
+	    (table->proc_handler == proc_doulongvec_ms_jiffies_minmax)) {
+		if (!table->data)
+			err |= sysctl_err(path, table, "No data");
+		if (!table->maxlen)
+			err |= sysctl_err(path, table, "No maxlen");
+		else
+			err |= sysctl_check_table_array(path, table);
+	}
+	if (!table->proc_handler)
+		err |= sysctl_err(path, table, "No proc_handler");
+
+	if ((table->mode & (S_IRUGO|S_IWUGO)) != table->mode)
+		err |= sysctl_err(path, table, "bogus .mode 0%o",
+			table->mode);
+	return err;
+}
+
 static int sysctl_check_table(const char *path, struct ctl_table *table)
 {
 	int err = 0;
@@ -1163,6 +1254,43 @@ static int sysctl_check_table(const char *path, struct ctl_table *table)
 	return err;
 }
 
+static struct ctl_table_header *new_links_single(struct ctl_dir *dir, struct ctl_table *table,
+	struct ctl_table_root *link_root)
+{
+	struct ctl_table *link_table;
+	struct ctl_table_header *links;
+	struct ctl_node *node;
+	char *link_name;
+	int name_bytes = 0;
+
+	name_bytes += strlen(table->procname) + 1;
+
+	links = kzalloc(sizeof(struct ctl_table_header) +
+			sizeof(struct ctl_node) +
+			sizeof(struct ctl_table)*2 +
+			name_bytes,
+			GFP_KERNEL);
+
+	if (!links)
+		return NULL;
+
+	node = (struct ctl_node *)(links + 1);
+	link_table = (struct ctl_table *)(node + 1);
+	link_name = (char *)&link_table[2];
+
+	int len = strlen(table->procname) + 1;
+
+	memcpy(link_name, table->procname, len);
+	link_table->procname = link_name;
+	link_table->mode = S_IFLNK|S_IRWXUGO;
+	link_table->data = link_root;
+	link_name += len;
+
+	init_header_single(links, dir->header.root, dir->header.set, node, link_table);
+	links->nreg = 1;
+
+	return links;
+}
 static struct ctl_table_header *new_links(struct ctl_dir *dir, struct ctl_table *table,
 	struct ctl_table_root *link_root)
 {
@@ -1206,6 +1334,27 @@ static struct ctl_table_header *new_links(struct ctl_dir *dir, struct ctl_table
 	return links;
 }
 
+static bool get_links_single(struct ctl_dir *dir,
+	struct ctl_table *table, struct ctl_table_root *link_root)
+{
+	struct ctl_table_header *head;
+	struct ctl_table *link;
+
+	/* Is there link available for table? */
+	const char *procname = table->procname;
+
+	link = find_entry(&head, dir, procname, strlen(procname));
+	if (!link)
+		return false;
+	if ((S_ISDIR(link->mode) && S_ISDIR(table->mode)) ||
+	    (S_ISLNK(link->mode) && (link->data == link_root))) {
+		head->nreg++;
+		return true;
+	}
+
+	return false;
+}
+
 static bool get_links(struct ctl_dir *dir,
 	struct ctl_table *table, struct ctl_table_root *link_root)
 {
@@ -1234,6 +1383,47 @@ static bool get_links(struct ctl_dir *dir,
 	return true;
 }
 
+static int insert_links_single(struct ctl_table_header *head)
+{
+	struct ctl_table_set *root_set = &sysctl_table_root.default_set;
+	struct ctl_dir *core_parent = NULL;
+	struct ctl_table_header *links;
+	int err;
+
+	if (head->set == root_set)
+		return 0;
+
+	core_parent = xlate_dir(root_set, head->parent);
+	if (IS_ERR(core_parent))
+		return 0;
+
+	if (get_links_single(core_parent, head->ctl_table, head->root))
+		return 0;
+
+	core_parent->header.nreg++;
+	spin_unlock(&sysctl_lock);
+
+	links = new_links_single(core_parent, head->ctl_table, head->root);
+
+	spin_lock(&sysctl_lock);
+	err = -ENOMEM;
+	if (!links)
+		goto out;
+
+	err = 0;
+	if (get_links_single(core_parent, head->ctl_table, head->root)) {
+		kfree(links);
+		goto out;
+	}
+
+	err = insert_header_single(core_parent, links);
+	if (err)
+		kfree(links);
+out:
+	drop_sysctl_table(&core_parent->header);
+	return err;
+}
+
 static int insert_links(struct ctl_table_header *head)
 {
 	struct ctl_table_set *root_set = &sysctl_table_root.default_set;
@@ -1401,6 +1591,132 @@ struct ctl_table_header *register_sysctl(const char *path, struct ctl_table *tab
 }
 EXPORT_SYMBOL(register_sysctl);
 
+/**
+ * __register_sysctl_table_single - register a leaf sysctl table
+ * @set: Sysctl tree to register on
+ * @path: The path to the directory the sysctl table is in.
+ * @table: the top-level table structure
+ *
+ * Register extraly one sysctl table. @table should be a filled in extraly one
+ * ctl_table. If ctl_table which need to register have child or is not single,
+ * we should use register_sysctl_init or register_sysctl instead of
+ * register_sysctl_single.
+ *
+ * The members of the &struct ctl_table structure are used as follows:
+ *
+ * procname - the name of the sysctl file under /proc/sys. Set to %NULL to not
+ *            enter a sysctl file
+ *
+ * data - a pointer to data for use by proc_handler
+ *
+ * maxlen - the maximum size in bytes of the data
+ *
+ * mode - the file permissions for the /proc/sys file
+ *
+ * child - must be %NULL.
+ *
+ * proc_handler - the text handler routine (described below)
+ *
+ * extra1, extra2 - extra pointers usable by the proc handler routines
+ *
+ * Leaf nodes in the sysctl tree will be represented by a single file
+ * under /proc; non-leaf nodes will be represented by directories.
+ *
+ * There must be a proc_handler routine for any terminal nodes.
+ * Several default handlers are available to cover common cases -
+ *
+ * proc_dostring(), proc_dointvec(), proc_dointvec_jiffies(),
+ * proc_dointvec_userhz_jiffies(), proc_dointvec_minmax(),
+ * proc_doulongvec_ms_jiffies_minmax(), proc_doulongvec_minmax()
+ *
+ * It is the handler's job to read the input buffer from user memory
+ * and process it. The handler should return 0 on success.
+ *
+ * This routine returns %NULL on a failure to register, and a pointer
+ * to the table header on success.
+ */
+struct ctl_table_header *__register_sysctl_table_single(
+	struct ctl_table_set *set,
+	const char *path, struct ctl_table *table)
+{
+	struct ctl_table_root *root = set->dir.header.root;
+	struct ctl_table_header *header;
+	const char *name, *nextname;
+	struct ctl_dir *dir;
+	struct ctl_node *node;
+
+	header = kzalloc(sizeof(struct ctl_table_header) +
+			 sizeof(struct ctl_node), GFP_KERNEL);
+	if (!header)
+		return NULL;
+
+	node = (struct ctl_node *)(header + 1);
+	init_header_single(header, root, set, node, table);
+	if (sysctl_check_table_single(path, table))
+		goto fail;
+
+	spin_lock(&sysctl_lock);
+	dir = &set->dir;
+	/* Reference moved down the diretory tree get_subdir */
+	dir->header.nreg++;
+	spin_unlock(&sysctl_lock);
+
+	/* Find the directory for the ctl_table */
+	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;
+
+		dir = get_subdir(dir, name, namelen);
+		if (IS_ERR(dir))
+			goto fail;
+	}
+
+	spin_lock(&sysctl_lock);
+	if (insert_header_single(dir, header))
+		goto fail_put_dir_locked;
+
+	drop_sysctl_table(&dir->header);
+	spin_unlock(&sysctl_lock);
+
+	return header;
+
+fail_put_dir_locked:
+	drop_sysctl_table(&dir->header);
+	spin_unlock(&sysctl_lock);
+fail:
+	kfree(header);
+	dump_stack();
+	return NULL;
+}
+
+/**
+ * __register_sysctl_single - register extraly one sysctl table
+ * @path: The path to the directory the sysctl table is in.
+ * @table: the table structure
+ *
+ * Register extraly one sysctl table. @table should be a filled in extraly one
+ * ctl_table. If ctl_table which need to register have child or is not single,
+ * we should use register_sysctl_init or register_sysctl instead of
+ * register_sysctl_single.
+ *
+ * See __register_sysctl_table_single for more details.
+ */
+struct ctl_table_header *__register_sysctl_single(const char *path, struct ctl_table *table)
+{
+	return __register_sysctl_table_single(&sysctl_table_root.default_set,
+					path, table);
+}
+EXPORT_SYMBOL(__register_sysctl_single);
+
 /**
  * __register_sysctl_init() - register sysctl table to path
  * @path: path name for sysctl base
@@ -1655,6 +1971,36 @@ int __register_sysctl_base(struct ctl_table *base_table)
 	return 0;
 }
 
+static void put_links_single(struct ctl_table_header *header)
+{
+	struct ctl_table_set *root_set = &sysctl_table_root.default_set;
+	struct ctl_table_root *root = header->root;
+	struct ctl_dir *parent = header->parent;
+	struct ctl_dir *core_parent;
+
+	if (header->set == root_set)
+		return;
+
+	core_parent = xlate_dir(root_set, parent);
+	if (IS_ERR(core_parent))
+		return;
+
+	struct ctl_table_header *link_head;
+	struct ctl_table *link;
+	const char *name = header->ctl_table->procname;
+
+	link = find_entry(&link_head, core_parent, name, strlen(name));
+	if (link &&
+	    ((S_ISDIR(link->mode) && S_ISDIR(header->ctl_table->mode)) ||
+	     (S_ISLNK(link->mode) && (link->data == root)))) {
+		drop_sysctl_table(link_head);
+	} else {
+		pr_err("sysctl link missing during unregister: ");
+		sysctl_print_dir(parent);
+		pr_cont("%s\n", name);
+	}
+}
+
 static void put_links(struct ctl_table_header *header)
 {
 	struct ctl_table_set *root_set = &sysctl_table_root.default_set;
diff --git a/include/linux/sysctl.h b/include/linux/sysctl.h
index 644fd53ad5f1..a7a5c3f25da9 100644
--- a/include/linux/sysctl.h
+++ b/include/linux/sysctl.h
@@ -235,6 +235,9 @@ extern int sysctl_init_bases(void);
 extern void __register_sysctl_init(const char *path, struct ctl_table *table,
 				 const char *table_name);
 #define register_sysctl_init(path, table) __register_sysctl_init(path, table, #table)
+extern struct ctl_table_header *__register_sysctl_single(const char *path,
+		struct ctl_table *table);
+#define register_sysctl_single(path, table) __register_sysctl_single(path, table)
 extern struct ctl_table_header *register_sysctl_mount_point(const char *path);
 
 void do_sysctl_args(void);
-- 
2.20.1




^ permalink raw reply related	[flat|nested] 6+ messages in thread

* [PATCH v2 2/2] fs/proc: sysctl: optimize register single one ctl_table
  2022-03-01 11:53 [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table Meng Tang
@ 2022-03-01 11:53 ` Meng Tang
  2022-03-01 16:06 ` [PATCH v2 1/2] fs/proc: optimize exactly register " kernel test robot
                   ` (3 subsequent siblings)
  4 siblings, 0 replies; 6+ messages in thread
From: Meng Tang @ 2022-03-01 11:53 UTC (permalink / raw)
  To: mcgrof, keescook, yzaikin, ebiederm, willy
  Cc: nixiaoming, nizhen, zhanglianjie, sujiaxun, linux-kernel,
	linux-fsdevel, Meng Tang

Sysctls are being moved out of kernel/sysctl.c and out to
their own respective subsystems / users to help with easier
maintance and avoid merge conflicts. But when we move just
one entry and to its own new file the last entry for this
new file must be empty, so we are essentialy bloating the
kernel one extra empty entry per each newly moved sysctl.

To help with this, I have added support for registering just
one ctl_table, therefore not bloating the kernel when we
move a single ctl_table to its own file.

The optimization has been implemented in the previous patch,
here use register_sysctl_single() to register single one
ctl_table.

In this modification, I counted the size changes of each
object file during the compilation process.

When there is no strip, size changes are as follows:
 			    before    now    save space
fs/dcache.o                  904936  904760   176bytes
fs/exec.o                    883584  883440   144bytes
fs/namespace.o              1614776 1614616   160bytes
fs/notify/dnotify/dnotify.o  255992  255872   120bytes
init/do_mounts_initrd.o      296552  296392   160bytes
kernel/acct.o                459184  459032   152bytes
kernel/delayacct.o           208680  208536   144bytes
kernel/kprobes.o             794968  794936    32bytes
kernel/panic.o               367696  367560   136bytes

When there is exec with 'strip -d', size changes are as follows:
     			    before    now    save space
fs/dcache.o                  79040   78952     88bytes
fs/exec.o                    57960   57864     96bytes
fs/namespace.o              111904  111824     80bytes
fs/notify/dnotify/dnotify.o   8816    8736     80bytes
init/do_mounts_initrd.o       4872    4760    112bytes
kernel/acct.o                18104   18000    104bytes
kernel/delayacct.o            8768    8664    104bytes
kernel/kprobes.o             63192   63104     88bytes
kernel/panic.o               26760   26672     88bytes

Suggested-by: Matthew Wilcox <willy@infradead.org>
Signed-off-by: Meng Tang <tangmeng@uniontech.com>
---
 fs/dcache.c                 | 5 ++---
 fs/exec.c                   | 5 ++---
 fs/namespace.c              | 5 ++---
 fs/notify/dnotify/dnotify.c | 5 ++---
 init/do_mounts_initrd.c     | 5 ++---
 kernel/acct.c               | 5 ++---
 kernel/delayacct.c          | 5 ++---
 kernel/kprobes.c            | 5 ++---
 kernel/panic.c              | 5 ++---
 9 files changed, 18 insertions(+), 27 deletions(-)

diff --git a/fs/dcache.c b/fs/dcache.c
index c84269c6e8bf..29fed2df79d1 100644
--- a/fs/dcache.c
+++ b/fs/dcache.c
@@ -190,13 +190,12 @@ static struct ctl_table fs_dcache_sysctls[] = {
 		.maxlen		= 6*sizeof(long),
 		.mode		= 0444,
 		.proc_handler	= proc_nr_dentry,
-	},
-	{ }
+	}
 };
 
 static int __init init_fs_dcache_sysctls(void)
 {
-	register_sysctl_init("fs", fs_dcache_sysctls);
+	register_sysctl_single("fs", fs_dcache_sysctls);
 	return 0;
 }
 fs_initcall(init_fs_dcache_sysctls);
diff --git a/fs/exec.c b/fs/exec.c
index c2586b791b87..58e9e50b9d98 100644
--- a/fs/exec.c
+++ b/fs/exec.c
@@ -2140,13 +2140,12 @@ static struct ctl_table fs_exec_sysctls[] = {
 		.proc_handler	= proc_dointvec_minmax_coredump,
 		.extra1		= SYSCTL_ZERO,
 		.extra2		= SYSCTL_TWO,
-	},
-	{ }
+	}
 };
 
 static int __init init_fs_exec_sysctls(void)
 {
-	register_sysctl_init("fs", fs_exec_sysctls);
+	register_sysctl_single("fs", fs_exec_sysctls);
 	return 0;
 }
 
diff --git a/fs/namespace.c b/fs/namespace.c
index df172818e1f8..1384fa7f8c79 100644
--- a/fs/namespace.c
+++ b/fs/namespace.c
@@ -4673,13 +4673,12 @@ static struct ctl_table fs_namespace_sysctls[] = {
 		.mode		= 0644,
 		.proc_handler	= proc_dointvec_minmax,
 		.extra1		= SYSCTL_ONE,
-	},
-	{ }
+	}
 };
 
 static int __init init_fs_namespace_sysctls(void)
 {
-	register_sysctl_init("fs", fs_namespace_sysctls);
+	register_sysctl_single("fs", fs_namespace_sysctls);
 	return 0;
 }
 fs_initcall(init_fs_namespace_sysctls);
diff --git a/fs/notify/dnotify/dnotify.c b/fs/notify/dnotify/dnotify.c
index 829dd4a61b66..813a22825be5 100644
--- a/fs/notify/dnotify/dnotify.c
+++ b/fs/notify/dnotify/dnotify.c
@@ -28,12 +28,11 @@ static struct ctl_table dnotify_sysctls[] = {
 		.maxlen		= sizeof(int),
 		.mode		= 0644,
 		.proc_handler	= proc_dointvec,
-	},
-	{}
+	}
 };
 static void __init dnotify_sysctl_init(void)
 {
-	register_sysctl_init("fs", dnotify_sysctls);
+	register_sysctl_single("fs", dnotify_sysctls);
 }
 #else
 #define dnotify_sysctl_init() do { } while (0)
diff --git a/init/do_mounts_initrd.c b/init/do_mounts_initrd.c
index 327962ea354c..d37f24959aa3 100644
--- a/init/do_mounts_initrd.c
+++ b/init/do_mounts_initrd.c
@@ -28,13 +28,12 @@ static struct ctl_table kern_do_mounts_initrd_table[] = {
 		.maxlen         = sizeof(int),
 		.mode           = 0644,
 		.proc_handler   = proc_dointvec,
-	},
-	{ }
+	}
 };
 
 static __init int kernel_do_mounts_initrd_sysctls_init(void)
 {
-	register_sysctl_init("kernel", kern_do_mounts_initrd_table);
+	register_sysctl_single("kernel", kern_do_mounts_initrd_table);
 	return 0;
 }
 late_initcall(kernel_do_mounts_initrd_sysctls_init);
diff --git a/kernel/acct.c b/kernel/acct.c
index 62200d799b9b..c628808c9213 100644
--- a/kernel/acct.c
+++ b/kernel/acct.c
@@ -83,13 +83,12 @@ static struct ctl_table kern_acct_table[] = {
 		.maxlen         = 3*sizeof(int),
 		.mode           = 0644,
 		.proc_handler   = proc_dointvec,
-	},
-	{ }
+	}
 };
 
 static __init int kernel_acct_sysctls_init(void)
 {
-	register_sysctl_init("kernel", kern_acct_table);
+	register_sysctl_single("kernel", kern_acct_table);
 	return 0;
 }
 late_initcall(kernel_acct_sysctls_init);
diff --git a/kernel/delayacct.c b/kernel/delayacct.c
index 2c1e18f7c5cf..6b776cbcb559 100644
--- a/kernel/delayacct.c
+++ b/kernel/delayacct.c
@@ -73,13 +73,12 @@ static struct ctl_table kern_delayacct_table[] = {
 		.proc_handler   = sysctl_delayacct,
 		.extra1         = SYSCTL_ZERO,
 		.extra2         = SYSCTL_ONE,
-	},
-	{ }
+	}
 };
 
 static __init int kernel_delayacct_sysctls_init(void)
 {
-	register_sysctl_init("kernel", kern_delayacct_table);
+	register_sysctl_single("kernel", kern_delayacct_table);
 	return 0;
 }
 late_initcall(kernel_delayacct_sysctls_init);
diff --git a/kernel/kprobes.c b/kernel/kprobes.c
index 94cab8c9ce56..1cf54662e2ed 100644
--- a/kernel/kprobes.c
+++ b/kernel/kprobes.c
@@ -970,13 +970,12 @@ static struct ctl_table kprobe_sysctls[] = {
 		.proc_handler	= proc_kprobes_optimization_handler,
 		.extra1		= SYSCTL_ZERO,
 		.extra2		= SYSCTL_ONE,
-	},
-	{}
+	}
 };
 
 static void __init kprobe_sysctls_init(void)
 {
-	register_sysctl_init("debug", kprobe_sysctls);
+	register_sysctl_single("debug", kprobe_sysctls);
 }
 #endif /* CONFIG_SYSCTL */
 
diff --git a/kernel/panic.c b/kernel/panic.c
index ae5c0ca86016..90f1a0f25139 100644
--- a/kernel/panic.c
+++ b/kernel/panic.c
@@ -85,13 +85,12 @@ static struct ctl_table kern_panic_table[] = {
 		.proc_handler   = proc_dointvec_minmax,
 		.extra1         = SYSCTL_ZERO,
 		.extra2         = SYSCTL_ONE,
-	},
-	{ }
+	}
 };
 
 static __init int kernel_panic_sysctls_init(void)
 {
-	register_sysctl_init("kernel", kern_panic_table);
+	register_sysctl_single("kernel", kern_panic_table);
 	return 0;
 }
 late_initcall(kernel_panic_sysctls_init);
-- 
2.20.1




^ permalink raw reply related	[flat|nested] 6+ messages in thread

* Re: [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table
  2022-03-01 11:53 [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table Meng Tang
  2022-03-01 11:53 ` [PATCH v2 2/2] fs/proc: sysctl: optimize register single " Meng Tang
@ 2022-03-01 16:06 ` kernel test robot
  2022-03-01 16:06 ` kernel test robot
                   ` (2 subsequent siblings)
  4 siblings, 0 replies; 6+ messages in thread
From: kernel test robot @ 2022-03-01 16:06 UTC (permalink / raw)
  To: Meng Tang, mcgrof, keescook, yzaikin, ebiederm, willy
  Cc: kbuild-all, nixiaoming, nizhen, zhanglianjie, sujiaxun,
	linux-kernel, linux-fsdevel, Meng Tang

Hi Meng,

Thank you for the patch! Perhaps something to improve:

[auto build test WARNING on mcgrof/sysctl-next]
[also build test WARNING on jack-fs/fsnotify rostedt-trace/for-next linus/master v5.17-rc6 next-20220301]
[cannot apply to kees/for-next/pstore]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch]

url:    https://github.com/0day-ci/linux/commits/Meng-Tang/fs-proc-optimize-exactly-register-one-ctl_table/20220301-195515
base:   https://git.kernel.org/pub/scm/linux/kernel/git/mcgrof/linux.git sysctl-next
config: nds32-allnoconfig (https://download.01.org/0day-ci/archive/20220301/202203012347.yd56xhtd-lkp@intel.com/config)
compiler: nds32le-linux-gcc (GCC) 11.2.0
reproduce (this is a W=1 build):
        wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross
        chmod +x ~/bin/make.cross
        # https://github.com/0day-ci/linux/commit/d9e9a410cf46b383390d668770fff70540e27528
        git remote add linux-review https://github.com/0day-ci/linux
        git fetch --no-tags linux-review Meng-Tang/fs-proc-optimize-exactly-register-one-ctl_table/20220301-195515
        git checkout d9e9a410cf46b383390d668770fff70540e27528
        # save the config file to linux build tree
        mkdir build_dir
        COMPILER_INSTALL_PATH=$HOME/0day COMPILER=gcc-11.2.0 make.cross O=build_dir ARCH=nds32 SHELL=/bin/bash fs/proc/

If you fix the issue, kindly add following tag as appropriate
Reported-by: kernel test robot <lkp@intel.com>

All warnings (new ones prefixed by >>):

   fs/proc/proc_sysctl.c: In function 'new_links_single':
>> fs/proc/proc_sysctl.c:1281:9: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement]
    1281 |         int len = strlen(table->procname) + 1;
         |         ^~~
   fs/proc/proc_sysctl.c: At top level:
>> fs/proc/proc_sysctl.c:1638:26: warning: no previous prototype for '__register_sysctl_table_single' [-Wmissing-prototypes]
    1638 | struct ctl_table_header *__register_sysctl_table_single(
         |                          ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   fs/proc/proc_sysctl.c: In function 'put_links_single':
   fs/proc/proc_sysctl.c:1988:9: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement]
    1988 |         struct ctl_table_header *link_head;
         |         ^~~~~~


vim +1281 fs/proc/proc_sysctl.c

  1256	
  1257	static struct ctl_table_header *new_links_single(struct ctl_dir *dir, struct ctl_table *table,
  1258		struct ctl_table_root *link_root)
  1259	{
  1260		struct ctl_table *link_table;
  1261		struct ctl_table_header *links;
  1262		struct ctl_node *node;
  1263		char *link_name;
  1264		int name_bytes = 0;
  1265	
  1266		name_bytes += strlen(table->procname) + 1;
  1267	
  1268		links = kzalloc(sizeof(struct ctl_table_header) +
  1269				sizeof(struct ctl_node) +
  1270				sizeof(struct ctl_table)*2 +
  1271				name_bytes,
  1272				GFP_KERNEL);
  1273	
  1274		if (!links)
  1275			return NULL;
  1276	
  1277		node = (struct ctl_node *)(links + 1);
  1278		link_table = (struct ctl_table *)(node + 1);
  1279		link_name = (char *)&link_table[2];
  1280	
> 1281		int len = strlen(table->procname) + 1;
  1282	
  1283		memcpy(link_name, table->procname, len);
  1284		link_table->procname = link_name;
  1285		link_table->mode = S_IFLNK|S_IRWXUGO;
  1286		link_table->data = link_root;
  1287		link_name += len;
  1288	
  1289		init_header_single(links, dir->header.root, dir->header.set, node, link_table);
  1290		links->nreg = 1;
  1291	
  1292		return links;
  1293	}
  1294	static struct ctl_table_header *new_links(struct ctl_dir *dir, struct ctl_table *table,
  1295		struct ctl_table_root *link_root)
  1296	{
  1297		struct ctl_table *link_table, *entry, *link;
  1298		struct ctl_table_header *links;
  1299		struct ctl_node *node;
  1300		char *link_name;
  1301		int nr_entries, name_bytes;
  1302	
  1303		name_bytes = 0;
  1304		nr_entries = 0;
  1305		for (entry = table; entry->procname; entry++) {
  1306			nr_entries++;
  1307			name_bytes += strlen(entry->procname) + 1;
  1308		}
  1309	
  1310		links = kzalloc(sizeof(struct ctl_table_header) +
  1311				sizeof(struct ctl_node)*nr_entries +
  1312				sizeof(struct ctl_table)*(nr_entries + 1) +
  1313				name_bytes,
  1314				GFP_KERNEL);
  1315	
  1316		if (!links)
  1317			return NULL;
  1318	
  1319		node = (struct ctl_node *)(links + 1);
  1320		link_table = (struct ctl_table *)(node + nr_entries);
  1321		link_name = (char *)&link_table[nr_entries + 1];
  1322	
  1323		for (link = link_table, entry = table; entry->procname; link++, entry++) {
  1324			int len = strlen(entry->procname) + 1;
  1325			memcpy(link_name, entry->procname, len);
  1326			link->procname = link_name;
  1327			link->mode = S_IFLNK|S_IRWXUGO;
  1328			link->data = link_root;
  1329			link_name += len;
  1330		}
  1331		init_header(links, dir->header.root, dir->header.set, node, link_table);
  1332		links->nreg = nr_entries;
  1333	
  1334		return links;
  1335	}
  1336	

---
0-DAY CI Kernel Test Service, Intel Corporation
https://lists.01.org/hyperkitty/list/kbuild-all@lists.01.org

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table
  2022-03-01 11:53 [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table Meng Tang
  2022-03-01 11:53 ` [PATCH v2 2/2] fs/proc: sysctl: optimize register single " Meng Tang
  2022-03-01 16:06 ` [PATCH v2 1/2] fs/proc: optimize exactly register " kernel test robot
@ 2022-03-01 16:06 ` kernel test robot
  2022-03-01 16:06 ` kernel test robot
  2022-03-01 17:44 ` Luis Chamberlain
  4 siblings, 0 replies; 6+ messages in thread
From: kernel test robot @ 2022-03-01 16:06 UTC (permalink / raw)
  To: Meng Tang, mcgrof, keescook, yzaikin, ebiederm, willy
  Cc: llvm, kbuild-all, nixiaoming, nizhen, zhanglianjie, sujiaxun,
	linux-kernel, linux-fsdevel, Meng Tang

Hi Meng,

Thank you for the patch! Perhaps something to improve:

[auto build test WARNING on mcgrof/sysctl-next]
[also build test WARNING on jack-fs/fsnotify rostedt-trace/for-next linus/master v5.17-rc6 next-20220301]
[cannot apply to kees/for-next/pstore]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch]

url:    https://github.com/0day-ci/linux/commits/Meng-Tang/fs-proc-optimize-exactly-register-one-ctl_table/20220301-195515
base:   https://git.kernel.org/pub/scm/linux/kernel/git/mcgrof/linux.git sysctl-next
config: hexagon-randconfig-r045-20220301 (https://download.01.org/0day-ci/archive/20220301/202203012340.8d5kZylK-lkp@intel.com/config)
compiler: clang version 15.0.0 (https://github.com/llvm/llvm-project d271fc04d5b97b12e6b797c6067d3c96a8d7470e)
reproduce (this is a W=1 build):
        wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross
        chmod +x ~/bin/make.cross
        # https://github.com/0day-ci/linux/commit/d9e9a410cf46b383390d668770fff70540e27528
        git remote add linux-review https://github.com/0day-ci/linux
        git fetch --no-tags linux-review Meng-Tang/fs-proc-optimize-exactly-register-one-ctl_table/20220301-195515
        git checkout d9e9a410cf46b383390d668770fff70540e27528
        # save the config file to linux build tree
        mkdir build_dir
        COMPILER_INSTALL_PATH=$HOME/0day COMPILER=clang make.cross W=1 O=build_dir ARCH=hexagon SHELL=/bin/bash fs/proc/

If you fix the issue, kindly add following tag as appropriate
Reported-by: kernel test robot <lkp@intel.com>

All warnings (new ones prefixed by >>):

>> fs/proc/proc_sysctl.c:1281:6: warning: mixing declarations and code is a C99 extension [-Wdeclaration-after-statement]
           int len = strlen(table->procname) + 1;
               ^
   fs/proc/proc_sysctl.c:1638:26: warning: no previous prototype for function '__register_sysctl_table_single' [-Wmissing-prototypes]
   struct ctl_table_header *__register_sysctl_table_single(
                            ^
   fs/proc/proc_sysctl.c:1638:1: note: declare 'static' if the function is not intended to be used outside of this translation unit
   struct ctl_table_header *__register_sysctl_table_single(
   ^
   static 
   fs/proc/proc_sysctl.c:1988:27: warning: mixing declarations and code is a C99 extension [-Wdeclaration-after-statement]
           struct ctl_table_header *link_head;
                                    ^
   3 warnings generated.


vim +1281 fs/proc/proc_sysctl.c

  1256	
  1257	static struct ctl_table_header *new_links_single(struct ctl_dir *dir, struct ctl_table *table,
  1258		struct ctl_table_root *link_root)
  1259	{
  1260		struct ctl_table *link_table;
  1261		struct ctl_table_header *links;
  1262		struct ctl_node *node;
  1263		char *link_name;
  1264		int name_bytes = 0;
  1265	
  1266		name_bytes += strlen(table->procname) + 1;
  1267	
  1268		links = kzalloc(sizeof(struct ctl_table_header) +
  1269				sizeof(struct ctl_node) +
  1270				sizeof(struct ctl_table)*2 +
  1271				name_bytes,
  1272				GFP_KERNEL);
  1273	
  1274		if (!links)
  1275			return NULL;
  1276	
  1277		node = (struct ctl_node *)(links + 1);
  1278		link_table = (struct ctl_table *)(node + 1);
  1279		link_name = (char *)&link_table[2];
  1280	
> 1281		int len = strlen(table->procname) + 1;
  1282	
  1283		memcpy(link_name, table->procname, len);
  1284		link_table->procname = link_name;
  1285		link_table->mode = S_IFLNK|S_IRWXUGO;
  1286		link_table->data = link_root;
  1287		link_name += len;
  1288	
  1289		init_header_single(links, dir->header.root, dir->header.set, node, link_table);
  1290		links->nreg = 1;
  1291	
  1292		return links;
  1293	}
  1294	static struct ctl_table_header *new_links(struct ctl_dir *dir, struct ctl_table *table,
  1295		struct ctl_table_root *link_root)
  1296	{
  1297		struct ctl_table *link_table, *entry, *link;
  1298		struct ctl_table_header *links;
  1299		struct ctl_node *node;
  1300		char *link_name;
  1301		int nr_entries, name_bytes;
  1302	
  1303		name_bytes = 0;
  1304		nr_entries = 0;
  1305		for (entry = table; entry->procname; entry++) {
  1306			nr_entries++;
  1307			name_bytes += strlen(entry->procname) + 1;
  1308		}
  1309	
  1310		links = kzalloc(sizeof(struct ctl_table_header) +
  1311				sizeof(struct ctl_node)*nr_entries +
  1312				sizeof(struct ctl_table)*(nr_entries + 1) +
  1313				name_bytes,
  1314				GFP_KERNEL);
  1315	
  1316		if (!links)
  1317			return NULL;
  1318	
  1319		node = (struct ctl_node *)(links + 1);
  1320		link_table = (struct ctl_table *)(node + nr_entries);
  1321		link_name = (char *)&link_table[nr_entries + 1];
  1322	
  1323		for (link = link_table, entry = table; entry->procname; link++, entry++) {
  1324			int len = strlen(entry->procname) + 1;
  1325			memcpy(link_name, entry->procname, len);
  1326			link->procname = link_name;
  1327			link->mode = S_IFLNK|S_IRWXUGO;
  1328			link->data = link_root;
  1329			link_name += len;
  1330		}
  1331		init_header(links, dir->header.root, dir->header.set, node, link_table);
  1332		links->nreg = nr_entries;
  1333	
  1334		return links;
  1335	}
  1336	

---
0-DAY CI Kernel Test Service, Intel Corporation
https://lists.01.org/hyperkitty/list/kbuild-all@lists.01.org

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table
  2022-03-01 11:53 [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table Meng Tang
                   ` (2 preceding siblings ...)
  2022-03-01 16:06 ` kernel test robot
@ 2022-03-01 16:06 ` kernel test robot
  2022-03-01 17:44 ` Luis Chamberlain
  4 siblings, 0 replies; 6+ messages in thread
From: kernel test robot @ 2022-03-01 16:06 UTC (permalink / raw)
  To: Meng Tang, mcgrof, keescook, yzaikin, ebiederm, willy
  Cc: kbuild-all, nixiaoming, nizhen, zhanglianjie, sujiaxun,
	linux-kernel, linux-fsdevel, Meng Tang

Hi Meng,

Thank you for the patch! Perhaps something to improve:

[auto build test WARNING on mcgrof/sysctl-next]
[also build test WARNING on jack-fs/fsnotify rostedt-trace/for-next linus/master v5.17-rc6 next-20220301]
[cannot apply to kees/for-next/pstore]
[If your patch is applied to the wrong git tree, kindly drop us a note.
And when submitting patch, we suggest to use '--base' as documented in
https://git-scm.com/docs/git-format-patch]

url:    https://github.com/0day-ci/linux/commits/Meng-Tang/fs-proc-optimize-exactly-register-one-ctl_table/20220301-195515
base:   https://git.kernel.org/pub/scm/linux/kernel/git/mcgrof/linux.git sysctl-next
config: alpha-buildonly-randconfig-r001-20220301 (https://download.01.org/0day-ci/archive/20220302/202203020000.IeIVyxMv-lkp@intel.com/config)
compiler: alpha-linux-gcc (GCC) 11.2.0
reproduce (this is a W=1 build):
        wget https://raw.githubusercontent.com/intel/lkp-tests/master/sbin/make.cross -O ~/bin/make.cross
        chmod +x ~/bin/make.cross
        # https://github.com/0day-ci/linux/commit/d9e9a410cf46b383390d668770fff70540e27528
        git remote add linux-review https://github.com/0day-ci/linux
        git fetch --no-tags linux-review Meng-Tang/fs-proc-optimize-exactly-register-one-ctl_table/20220301-195515
        git checkout d9e9a410cf46b383390d668770fff70540e27528
        # save the config file to linux build tree
        mkdir build_dir
        COMPILER_INSTALL_PATH=$HOME/0day COMPILER=gcc-11.2.0 make.cross O=build_dir ARCH=alpha SHELL=/bin/bash fs/proc/

If you fix the issue, kindly add following tag as appropriate
Reported-by: kernel test robot <lkp@intel.com>

All warnings (new ones prefixed by >>):

   fs/proc/proc_sysctl.c: In function 'new_links_single':
>> fs/proc/proc_sysctl.c:1281:9: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement]
    1281 |         int len = strlen(table->procname) + 1;
         |         ^~~
   fs/proc/proc_sysctl.c: At top level:
>> fs/proc/proc_sysctl.c:1638:26: warning: no previous prototype for '__register_sysctl_table_single' [-Wmissing-prototypes]
    1638 | struct ctl_table_header *__register_sysctl_table_single(
         |                          ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
   fs/proc/proc_sysctl.c: In function 'put_links_single':
   fs/proc/proc_sysctl.c:1988:9: warning: ISO C90 forbids mixed declarations and code [-Wdeclaration-after-statement]
    1988 |         struct ctl_table_header *link_head;
         |         ^~~~~~


vim +1281 fs/proc/proc_sysctl.c

  1256	
  1257	static struct ctl_table_header *new_links_single(struct ctl_dir *dir, struct ctl_table *table,
  1258		struct ctl_table_root *link_root)
  1259	{
  1260		struct ctl_table *link_table;
  1261		struct ctl_table_header *links;
  1262		struct ctl_node *node;
  1263		char *link_name;
  1264		int name_bytes = 0;
  1265	
  1266		name_bytes += strlen(table->procname) + 1;
  1267	
  1268		links = kzalloc(sizeof(struct ctl_table_header) +
  1269				sizeof(struct ctl_node) +
  1270				sizeof(struct ctl_table)*2 +
  1271				name_bytes,
  1272				GFP_KERNEL);
  1273	
  1274		if (!links)
  1275			return NULL;
  1276	
  1277		node = (struct ctl_node *)(links + 1);
  1278		link_table = (struct ctl_table *)(node + 1);
  1279		link_name = (char *)&link_table[2];
  1280	
> 1281		int len = strlen(table->procname) + 1;
  1282	
  1283		memcpy(link_name, table->procname, len);
  1284		link_table->procname = link_name;
  1285		link_table->mode = S_IFLNK|S_IRWXUGO;
  1286		link_table->data = link_root;
  1287		link_name += len;
  1288	
  1289		init_header_single(links, dir->header.root, dir->header.set, node, link_table);
  1290		links->nreg = 1;
  1291	
  1292		return links;
  1293	}
  1294	static struct ctl_table_header *new_links(struct ctl_dir *dir, struct ctl_table *table,
  1295		struct ctl_table_root *link_root)
  1296	{
  1297		struct ctl_table *link_table, *entry, *link;
  1298		struct ctl_table_header *links;
  1299		struct ctl_node *node;
  1300		char *link_name;
  1301		int nr_entries, name_bytes;
  1302	
  1303		name_bytes = 0;
  1304		nr_entries = 0;
  1305		for (entry = table; entry->procname; entry++) {
  1306			nr_entries++;
  1307			name_bytes += strlen(entry->procname) + 1;
  1308		}
  1309	
  1310		links = kzalloc(sizeof(struct ctl_table_header) +
  1311				sizeof(struct ctl_node)*nr_entries +
  1312				sizeof(struct ctl_table)*(nr_entries + 1) +
  1313				name_bytes,
  1314				GFP_KERNEL);
  1315	
  1316		if (!links)
  1317			return NULL;
  1318	
  1319		node = (struct ctl_node *)(links + 1);
  1320		link_table = (struct ctl_table *)(node + nr_entries);
  1321		link_name = (char *)&link_table[nr_entries + 1];
  1322	
  1323		for (link = link_table, entry = table; entry->procname; link++, entry++) {
  1324			int len = strlen(entry->procname) + 1;
  1325			memcpy(link_name, entry->procname, len);
  1326			link->procname = link_name;
  1327			link->mode = S_IFLNK|S_IRWXUGO;
  1328			link->data = link_root;
  1329			link_name += len;
  1330		}
  1331		init_header(links, dir->header.root, dir->header.set, node, link_table);
  1332		links->nreg = nr_entries;
  1333	
  1334		return links;
  1335	}
  1336	

---
0-DAY CI Kernel Test Service, Intel Corporation
https://lists.01.org/hyperkitty/list/kbuild-all@lists.01.org

^ permalink raw reply	[flat|nested] 6+ messages in thread

* Re: [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table
  2022-03-01 11:53 [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table Meng Tang
                   ` (3 preceding siblings ...)
  2022-03-01 16:06 ` kernel test robot
@ 2022-03-01 17:44 ` Luis Chamberlain
  4 siblings, 0 replies; 6+ messages in thread
From: Luis Chamberlain @ 2022-03-01 17:44 UTC (permalink / raw)
  To: Meng Tang
  Cc: keescook, yzaikin, ebiederm, willy, nixiaoming, nizhen,
	zhanglianjie, sujiaxun, linux-kernel, linux-fsdevel

On Tue, Mar 01, 2022 at 07:53:40PM +0800, Meng Tang wrote:
> Sysctls are being moved out of kernel/sysctl.c and out to
> their own respective subsystems / users to help with easier
> maintance and avoid merge conflicts. But when we move just
> one entry and to its own new file the last entry for this
> new file must be empty, so we are essentialy bloating the
> kernel one extra empty entry per each newly moved sysctl.
> 
> To help with this, this adds support for registering just
> one ctl_table, therefore not bloating the kernel when we
> move a single ctl_table to its own file.
> 
> Suggested-by: Matthew Wilcox <willy@infradead.org>
> Signed-off-by: Meng Tang <tangmeng@uniontech.com>

Please extend the commit log to justify why we have to add
so much code, you mentioned it to me before, now just please
write that in the commit log.

Can you really not add helpers first so that these helpers
are used by both paths?

  Luis

^ permalink raw reply	[flat|nested] 6+ messages in thread

end of thread, other threads:[~2022-03-01 17:44 UTC | newest]

Thread overview: 6+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2022-03-01 11:53 [PATCH v2 1/2] fs/proc: optimize exactly register one ctl_table Meng Tang
2022-03-01 11:53 ` [PATCH v2 2/2] fs/proc: sysctl: optimize register single " Meng Tang
2022-03-01 16:06 ` [PATCH v2 1/2] fs/proc: optimize exactly register " kernel test robot
2022-03-01 16:06 ` kernel test robot
2022-03-01 16:06 ` kernel test robot
2022-03-01 17:44 ` Luis Chamberlain

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).