[Devel] [PATCH RH9 02/16] ve/sysctl: implement virtualized methods
Pavel Tikhomirov
ptikhomirov at virtuozzo.com
Tue Sep 28 15:40:52 MSK 2021
From: Stanislav Kinsburskiy <skinsbursky at virtuozzo.com>
add new helpers for sysctl virtualization:
proc_dointvec_virtual() (it maps data pointer from ve0 to current exec env,
will be extedned to work with other nemspaces/cgroups)
proc_dointvec_immutable() (ignores writes from container)
proc_dostring_immutable()
Signed-off-by: Konstantin Khlebnikov <khlebnikov at openvz.org>
+++
VE: use ve environtment for sysctl restrictions
https://jira.sw.ru/browse/PSBM-18032
https://jira.sw.ru/browse/PSBM-18030
https://jira.sw.ru/browse/PSBM-29017
https://jira.sw.ru/browse/PSBM-43596
Signed-off-by: Konstantin Khlebnikov <khlebnikov at openvz.org>
Signed-off-by: Andrey Ryabinin <aryabinin at odin.com>
Signed-off-by: Pavel Tikhomirov <ptikhomirov at virtuozzo.com>
(cherry picked from commit 9d020b764ccc1872bae8241228c13265bf1d5c33)
Signed-off-by: Konstantin Khorenko <khorenko at virtuozzo.com>
(cherry-picked from vz8 commit cf90b2bfb592e389c3704842d7043a52313377ae)
Signed-off-by: Pavel Tikhomirov <ptikhomirov at virtuozzo.com>
---
include/linux/sysctl.h | 11 +++++++++
kernel/sysctl.c | 55 ++++++++++++++++++++++++++++++++++++++++++
2 files changed, 66 insertions(+)
diff --git a/include/linux/sysctl.h b/include/linux/sysctl.h
index d99ca99837de..4c9efe69e435 100644
--- a/include/linux/sysctl.h
+++ b/include/linux/sysctl.h
@@ -67,6 +67,17 @@ int proc_do_large_bitmap(struct ctl_table *, int, void *, size_t *, loff_t *);
int proc_do_static_key(struct ctl_table *table, int write, void *buffer,
size_t *lenp, loff_t *ppos);
+extern int proc_dointvec_virtual(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos);
+extern int proc_doulongvec_minmax_virtual(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos);
+extern int proc_dointvec_immutable(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos);
+extern int proc_dostring_immutable(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos);
+extern int proc_dointvec_minmax_immutable(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos);
+
/*
* Register a set of sysctl names by calling register_sysctl_table
* with an initialised array of struct ctl_table's. An entry with
diff --git a/kernel/sysctl.c b/kernel/sysctl.c
index 081e42171745..1b203142e645 100644
--- a/kernel/sysctl.c
+++ b/kernel/sysctl.c
@@ -155,6 +155,17 @@ static unsigned long hung_task_timeout_max = (LONG_MAX/HZ);
#include <linux/fanotify.h>
#endif
+static bool virtual_ptr(void **ptr, void *base, size_t size, void *cur);
+#define sysctl_virtual(sysctl) \
+int sysctl ## _virtual(struct ctl_table *table, int write, \
+ void __user *buffer, size_t *lenp, loff_t *ppos) \
+{ \
+ struct ctl_table tmp = *table; \
+ if (virtual_ptr(&tmp.data, &ve0, sizeof(ve0), get_exec_env())) \
+ return sysctl(&tmp, write, buffer, lenp, ppos); \
+ return -EINVAL; \
+}
+
#ifdef CONFIG_PROC_SYSCTL
/**
@@ -1628,6 +1639,50 @@ int proc_do_large_bitmap(struct ctl_table *table, int write,
return err;
}
+static bool virtual_ptr(void **ptr, void *base, size_t size, void *cur)
+{
+ unsigned long addr = (unsigned long)*ptr;
+ unsigned long base_addr = (unsigned long)base;
+
+ if (addr >= base_addr && addr < base_addr + size) {
+ *ptr = (char *)cur + (addr - base_addr);
+ return true;
+ }
+ return false;
+}
+
+sysctl_virtual(proc_dointvec);
+sysctl_virtual(proc_doulongvec_minmax);
+
+static inline bool sysctl_in_container(void)
+{
+ return !ve_is_super(get_exec_env());
+}
+
+int proc_dointvec_immutable(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos)
+{
+ if (write && sysctl_in_container())
+ return 0;
+ return proc_dointvec(table, write, buffer, lenp, ppos);
+}
+
+int proc_dostring_immutable(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos)
+{
+ if (write && sysctl_in_container())
+ return 0;
+ return proc_dostring(table, write, buffer, lenp, ppos);
+}
+
+int proc_dointvec_minmax_immutable(struct ctl_table *table, int write,
+ void __user *buffer, size_t *lenp, loff_t *ppos)
+{
+ if (write && sysctl_in_container())
+ return 0;
+ return proc_dointvec_minmax(table, write, buffer, lenp, ppos);
+}
+
#else /* CONFIG_PROC_SYSCTL */
int proc_dostring(struct ctl_table *table, int write,
--
2.31.1
More information about the Devel
mailing list