Add required sysctl name length checks to various handlers

Reported by:	KMSAN
MFC after:	1 week
Sponsored by:	The FreeBSD Foundation
This commit is contained in:
Mark Johnston 2021-07-23 10:37:11 -04:00
parent cae3f9dd01
commit 0dcef81de9
3 changed files with 39 additions and 2 deletions

View File

@ -4092,8 +4092,13 @@ sysctl_kern_proc_nfds(SYSCTL_HANDLER_ARGS)
{
NDSLOTTYPE *map;
struct filedesc *fdp;
u_int namelen;
int count, off, minoff;
namelen = arg2;
if (namelen != 1)
return (EINVAL);
if (*(int *)arg1 != 0)
return (EINVAL);
@ -4482,8 +4487,13 @@ sysctl_kern_proc_filedesc(SYSCTL_HANDLER_ARGS)
struct sbuf sb;
struct proc *p;
ssize_t maxlen;
u_int namelen;
int error, error2, *name;
namelen = arg2;
if (namelen != 1)
return (EINVAL);
name = (int *)arg1;
sbuf_new_for_sysctl(&sb, NULL, FILEDESC_SBUF_SIZE, req);
@ -4561,10 +4571,15 @@ sysctl_kern_proc_ofiledesc(SYSCTL_HANDLER_ARGS)
struct filedesc *fdp;
struct pwddesc *pdp;
struct pwd *pwd;
u_int namelen;
int error, i, lastfile, *name;
struct file *fp;
struct proc *p;
namelen = arg2;
if (namelen != 1)
return (EINVAL);
name = (int *)arg1;
error = pget((pid_t)name[0], PGET_CANDEBUG | PGET_NOTWEXIT, &p);
if (error != 0)
@ -4706,8 +4721,13 @@ sysctl_kern_proc_cwd(SYSCTL_HANDLER_ARGS)
struct sbuf sb;
struct proc *p;
ssize_t maxlen;
u_int namelen;
int error, error2, *name;
namelen = arg2;
if (namelen != 1)
return (EINVAL);
name = (int *)arg1;
sbuf_new_for_sysctl(&sb, NULL, sizeof(struct kinfo_file), req);

View File

@ -2297,7 +2297,7 @@ static int
sysctl_kern_proc_ovmmap(SYSCTL_HANDLER_ARGS)
{
vm_map_entry_t entry, tmp_entry;
unsigned int last_timestamp;
unsigned int last_timestamp, namelen;
char *fullpath, *freepath;
struct kinfo_ovmentry *kve;
struct vattr va;
@ -2308,6 +2308,10 @@ sysctl_kern_proc_ovmmap(SYSCTL_HANDLER_ARGS)
vm_map_t map;
struct vmspace *vm;
namelen = arg2;
if (namelen != 1)
return (EINVAL);
name = (int *)arg1;
error = pget((pid_t)name[0], PGET_WANTREAD, &p);
if (error != 0)
@ -2678,8 +2682,13 @@ sysctl_kern_proc_vmmap(SYSCTL_HANDLER_ARGS)
{
struct proc *p;
struct sbuf sb;
u_int namelen;
int error, error2, *name;
namelen = arg2;
if (namelen != 1)
return (EINVAL);
name = (int *)arg1;
sbuf_new_for_sysctl(&sb, NULL, sizeof(struct kinfo_vmentry), req);
sbuf_clear_flags(&sb, SBUF_INCLUDENUL);
@ -2705,6 +2714,11 @@ sysctl_kern_proc_kstack(SYSCTL_HANDLER_ARGS)
struct stack *st;
struct sbuf sb;
struct proc *p;
u_int namelen;
namelen = arg2;
if (namelen != 1)
return (EINVAL);
name = (int *)arg1;
error = pget((pid_t)name[0], PGET_NOTINEXEC | PGET_WANTREAD, &p);

View File

@ -2567,7 +2567,10 @@ sysctl_rtsock(SYSCTL_HANDLER_ARGS)
u_char af;
struct walkarg w;
name ++;
if (namelen < 3)
return (EINVAL);
name++;
namelen--;
if (req->newptr)
return (EPERM);