summaryrefslogtreecommitdiff
path: root/sys/kern
diff options
context:
space:
mode:
authorIan Moffett <ian@osmora.org>2025-08-06 22:26:47 -0400
committerIan Moffett <ian@osmora.org>2025-08-06 22:26:47 -0400
commit7ccae7b0e7f5e619c0b8eac6f0bf5807a323ffb4 (patch)
tree410ffc86daeed0d8c259586c80e103edb616d027 /sys/kern
parente21a6f72c66478d9a187d7da86aa152fd868d569 (diff)
kernel: sysctl: Allow 'old*' fields to be NULL
When setting sysctl variables from userspace, the 'old' fields will unused and thus typically be set to NULL. This commit modifies the behaviour of do_sysctl() to enable this. Signed-off-by: Ian Moffett <ian@osmora.org>
Diffstat (limited to 'sys/kern')
-rw-r--r--sys/kern/kern_sysctl.c30
1 files changed, 16 insertions, 14 deletions
diff --git a/sys/kern/kern_sysctl.c b/sys/kern/kern_sysctl.c
index ad90f1a..8b298a7 100644
--- a/sys/kern/kern_sysctl.c
+++ b/sys/kern/kern_sysctl.c
@@ -91,19 +91,17 @@ static int
do_sysctl(struct sysctl_args *args)
{
struct sysctl_args new_args;
- size_t name_len, oldlenp;
+ size_t name_len = 1, oldlenp = 0;
int *name = NULL;
void *oldp = NULL, *newp = NULL;
int retval = 0;
- if (args->oldlenp == NULL) {
- return -EINVAL;
- }
-
- name_len = args->nlen;
- retval = copyin(args->oldlenp, &oldlenp, sizeof(oldlenp));
- if (retval != 0) {
- goto done;
+ if (args->oldlenp != NULL) {
+ name_len = args->nlen;
+ retval = copyin(args->oldlenp, &oldlenp, sizeof(oldlenp));
+ if (retval != 0) {
+ goto done;
+ }
}
/* Copy in newp if it is set */
@@ -124,10 +122,12 @@ do_sysctl(struct sysctl_args *args)
return retval;
}
- oldp = dynalloc(oldlenp);
- retval = copyin(args->oldp, oldp, oldlenp);
- if (retval != 0) {
- return retval;
+ if (oldlenp != 0) {
+ oldp = dynalloc(oldlenp);
+ retval = copyin(args->oldp, oldp, oldlenp);
+ if (retval != 0) {
+ return retval;
+ }
}
/* Prepare the arguments for the sysctl call */
@@ -143,7 +143,9 @@ do_sysctl(struct sysctl_args *args)
goto done;
}
- copyout(oldp, args->oldp, oldlenp);
+ if (oldlenp != 0) {
+ copyout(oldp, args->oldp, oldlenp);
+ }
done:
if (name != NULL)
dynfree(name);