Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux

staging: gdm72xx: add userspace data struct

This fixes the sparse warnings about dereferencing a userspace pointer.

Once I updated the sparse annotations, I noticed a bug in
gdm_wimax_ioctl() where we pass a user space pointer to gdm_update_fsm()
which dereferences it. I fixed this.

Signed-off-by: Wim de With <nauxuron@wimdewith.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>

authored by

Wim de With and committed by
Greg Kroah-Hartman
d1052aa5 2bc29a1a

+14 -5
+8 -4
drivers/staging/gdm72xx/gdm_wimax.c
··· 363 363 } 364 364 } 365 365 366 - static int gdm_wimax_ioctl_get_data(struct data_s *dst, struct data_s *src) 366 + static int gdm_wimax_ioctl_get_data(struct udata_s *dst, struct data_s *src) 367 367 { 368 368 int size; 369 369 ··· 379 379 return 0; 380 380 } 381 381 382 - static int gdm_wimax_ioctl_set_data(struct data_s *dst, struct data_s *src) 382 + static int gdm_wimax_ioctl_set_data(struct data_s *dst, struct udata_s *src) 383 383 { 384 384 if (!src->size) { 385 385 dst->size = 0; ··· 455 455 struct wm_req_s *req = (struct wm_req_s *)ifr; 456 456 struct nic *nic = netdev_priv(dev); 457 457 int ret; 458 + struct fsm_s fsm_buf; 458 459 459 460 if (cmd != SIOCWMIOCTL) 460 461 return -EOPNOTSUPP; ··· 478 477 /* NOTE: gdm_update_fsm should be called 479 478 * before gdm_wimax_ioctl_set_data is called. 480 479 */ 481 - gdm_update_fsm(dev, 482 - req->data.buf); 480 + if (copy_from_user(&fsm_buf, req->data.buf, 481 + sizeof(struct fsm_s))) 482 + return -EFAULT; 483 + 484 + gdm_update_fsm(dev, &fsm_buf); 483 485 } 484 486 ret = gdm_wimax_ioctl_set_data( 485 487 &nic->sdk_data[req->data_id], &req->data);
+6 -1
drivers/staging/gdm72xx/wm_ioctl.h
··· 78 78 void *buf; 79 79 }; 80 80 81 + struct udata_s { 82 + int size; 83 + void __user *buf; 84 + }; 85 + 81 86 struct wm_req_s { 82 87 union { 83 88 char ifrn_name[IFNAMSIZ]; 84 89 } ifr_ifrn; 85 90 unsigned short cmd; 86 91 unsigned short data_id; 87 - struct data_s data; 92 + struct udata_s data; 88 93 89 94 /* NOTE: sizeof(struct wm_req_s) must be less than sizeof(struct ifreq). */ 90 95 };