Hi Dave,

> >  > >  > How do you produce these oopses, because I've never seen them.
> >  > > http://people.redhat.com/davej/sfuzz.c
> >  > > (it ran for a few hours before it caused the oopses)
> >  > 
> >  > Any options to make it appear faster? 
> > 
> > I just ran it with no arguments.
> 
> I was able to reproduce the hci_sock_getname() oops, but I have actually
> no idea how we can have a NULL pointer dereference in that code. Need to
> find a way to reproduce this faster. Took me at least 20 minutes before
> the oops appeared.

after modifying Ilja's tool, I was capable of reproducing these oopses
very fast, but it took me some time to understand why both are ending up
in a NULL pointer dereference. However here is a patch for them. The
sfuzz on AF_BLUETOOTH only is now running for over half an hour without
any oops. I will send this upstream as soon as possible.

Regards

Marcel

diff --git a/net/bluetooth/hci_sock.c b/net/bluetooth/hci_sock.c
index bdb6458..97bdec7 100644
--- a/net/bluetooth/hci_sock.c
+++ b/net/bluetooth/hci_sock.c
@@ -143,13 +143,15 @@ void hci_send_to_sock(struct hci_dev *hd
 static int hci_sock_release(struct socket *sock)
 {
 	struct sock *sk = sock->sk;
-	struct hci_dev *hdev = hci_pi(sk)->hdev;
+	struct hci_dev *hdev;
 
 	BT_DBG("sock %p sk %p", sock, sk);
 
 	if (!sk)
 		return 0;
 
+	hdev = hci_pi(sk)->hdev;
+
 	bt_sock_unlink(&hci_sk_list, sk);
 
 	if (hdev) {
@@ -311,14 +313,18 @@ static int hci_sock_getname(struct socke
 {
 	struct sockaddr_hci *haddr = (struct sockaddr_hci *) addr;
 	struct sock *sk = sock->sk;
+	struct hci_dev *hdev = hci_pi(sk)->hdev;
 
 	BT_DBG("sock %p sk %p", sock, sk);
 
+	if (!hdev)
+		return -EBADFD;
+
 	lock_sock(sk);
 
 	*addr_len = sizeof(*haddr);
 	haddr->hci_family = AF_BLUETOOTH;
-	haddr->hci_dev    = hci_pi(sk)->hdev->id;
+	haddr->hci_dev    = hdev->id;
 
 	release_sock(sk);
 	return 0;

Reply via email to