aboutsummaryrefslogtreecommitdiffstats
path: root/net/bluetooth/bnep
diff options
context:
space:
mode:
authorMarcel Holtmann <marcel@holtmann.org>2006-10-15 11:30:22 -0400
committerDavid S. Miller <davem@sunset.davemloft.net>2006-10-16 02:14:27 -0400
commite9c5702e3c5558dade169949abd730173e87ef9c (patch)
tree58ec8dcd1497b51e1d6a447d8c4a34a0bd2f108d /net/bluetooth/bnep
parent39c850863d5e36e72ecf9bc3537ec717bcce97fd (diff)
[Bluetooth] Fix compat ioctl for BNEP, CMTP and HIDP
There exists no attempt do deal with the fact that a structure with a uint32_t followed by a pointer is going to be different for 32-bit and 64-bit userspace. Any 32-bit process trying to use it will be failing with -EFAULT if it's lucky; suffering from having data dumped at a random address if it's not. Signed-off-by: David Woodhouse <dwmw2@infradead.org> Signed-off-by: Marcel Holtmann <marcel@holtmann.org>
Diffstat (limited to 'net/bluetooth/bnep')
-rw-r--r--net/bluetooth/bnep/sock.c67
1 files changed, 50 insertions, 17 deletions
diff --git a/net/bluetooth/bnep/sock.c b/net/bluetooth/bnep/sock.c
index 28c55835422a..5d9d6f14b310 100644
--- a/net/bluetooth/bnep/sock.c
+++ b/net/bluetooth/bnep/sock.c
@@ -43,6 +43,7 @@
43#include <linux/ioctl.h> 43#include <linux/ioctl.h>
44#include <linux/file.h> 44#include <linux/file.h>
45#include <linux/init.h> 45#include <linux/init.h>
46#include <linux/compat.h>
46#include <net/sock.h> 47#include <net/sock.h>
47 48
48#include <asm/system.h> 49#include <asm/system.h>
@@ -146,24 +147,56 @@ static int bnep_sock_ioctl(struct socket *sock, unsigned int cmd, unsigned long
146 return 0; 147 return 0;
147} 148}
148 149
150#ifdef CONFIG_COMPAT
151static int bnep_sock_compat_ioctl(struct socket *sock, unsigned int cmd, unsigned long arg)
152{
153 if (cmd == BNEPGETCONNLIST) {
154 struct bnep_connlist_req cl;
155 uint32_t uci;
156 int err;
157
158 if (get_user(cl.cnum, (uint32_t __user *) arg) ||
159 get_user(uci, (u32 __user *) (arg + 4)))
160 return -EFAULT;
161
162 cl.ci = compat_ptr(uci);
163
164 if (cl.cnum <= 0)
165 return -EINVAL;
166
167 err = bnep_get_connlist(&cl);
168
169 if (!err && put_user(cl.cnum, (uint32_t __user *) arg))
170 err = -EFAULT;
171
172 return err;
173 }
174
175 return bnep_sock_ioctl(sock, cmd, arg);
176}
177#endif
178
149static const struct proto_ops bnep_sock_ops = { 179static const struct proto_ops bnep_sock_ops = {
150 .family = PF_BLUETOOTH, 180 .family = PF_BLUETOOTH,
151 .owner = THIS_MODULE, 181 .owner = THIS_MODULE,
152 .release = bnep_sock_release, 182 .release = bnep_sock_release,
153 .ioctl = bnep_sock_ioctl, 183 .ioctl = bnep_sock_ioctl,
154 .bind = sock_no_bind, 184#ifdef CONFIG_COMPAT
155 .getname = sock_no_getname, 185 .compat_ioctl = bnep_sock_compat_ioctl,
156 .sendmsg = sock_no_sendmsg, 186#endif
157 .recvmsg = sock_no_recvmsg, 187 .bind = sock_no_bind,
158 .poll = sock_no_poll, 188 .getname = sock_no_getname,
159 .listen = sock_no_listen, 189 .sendmsg = sock_no_sendmsg,
160 .shutdown = sock_no_shutdown, 190 .recvmsg = sock_no_recvmsg,
161 .setsockopt = sock_no_setsockopt, 191 .poll = sock_no_poll,
162 .getsockopt = sock_no_getsockopt, 192 .listen = sock_no_listen,
163 .connect = sock_no_connect, 193 .shutdown = sock_no_shutdown,
164 .socketpair = sock_no_socketpair, 194 .setsockopt = sock_no_setsockopt,
165 .accept = sock_no_accept, 195 .getsockopt = sock_no_getsockopt,
166 .mmap = sock_no_mmap 196 .connect = sock_no_connect,
197 .socketpair = sock_no_socketpair,
198 .accept = sock_no_accept,
199 .mmap = sock_no_mmap
167}; 200};
168 201
169static struct proto bnep_proto = { 202static struct proto bnep_proto = {