--- linux-2.6.18-339.0.0.0.1.el5.x86_64/drivers/infiniband/ulp/ipoib/ipoib_main.c.orig	2012-09-26 13:25:05.000000000 -0700
+++ linux-2.6.18-339.0.0.0.1.el5.x86_64/drivers/infiniband/ulp/ipoib/ipoib_main.c	2012-09-26 13:31:03.000000000 -0700
@@ -927,6 +927,7 @@
 		return NULL;
 
 	neigh->ah = NULL;
+        neigh_hold(neighbour);
 	neigh->neighbour = neighbour;
 	neigh->dev = dev;
 	memset(&neigh->dgid.raw, 0, sizeof (union ib_gid));
@@ -941,6 +942,7 @@
 void ipoib_neigh_free(struct net_device *dev, struct ipoib_neigh *neigh)
 {
 	struct sk_buff *skb;
+	struct neighbour *neighbour = neigh->neighbour;
 	struct ipoib_dev_priv *priv = netdev_priv(dev);
 	*to_ipoib_neigh(neigh->neighbour) = NULL;
 	while ((skb = __skb_dequeue(&neigh->queue))) {
@@ -950,6 +952,7 @@
 	if (ipoib_cm_get(neigh))
 		ipoib_cm_destroy_tx(ipoib_cm_get(neigh));
 	kfree(neigh);
+	neigh_release(neighbour);
 }
 
 static int ipoib_neigh_setup_dev(struct net_device *dev, struct neigh_parms *parms)
@@ -1506,6 +1509,8 @@
 		goto err_sa;
 	}
 
+	/* we explode on rmmod */
+	__module_get(THIS_MODULE);
 	return 0;
 
 err_sa:
