Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 11 Mar 2005 13:20:09 -0600
From:      Alan Cox <alc@cs.rice.edu>
To:        Gavin Atkinson <gavin.atkinson@ury.york.ac.uk>
Cc:        stable@freebsd.org
Subject:   Re: panic: mutex vm object not owned
Message-ID:  <20050311192009.GK28845@cs.rice.edu>
In-Reply-To: <20050311184658.Q63048@ury.york.ac.uk>
References:  <20050311184658.Q63048@ury.york.ac.uk>

next in thread | previous in thread | raw e-mail | index | archive | help

--sm4nu43k4a2Rpi4c
Content-Type: text/plain; charset=us-ascii
Content-Disposition: inline

I'm pretty sure that I understand the cause.  Please apply and test
the attached patch.

Regards,
Alan

--sm4nu43k4a2Rpi4c
Content-Type: text/plain; charset=us-ascii
Content-Disposition: attachment; filename=patch-agp

Index: pci/agp.c
===================================================================
RCS file: /home/ncvs/src/sys/pci/agp.c,v
retrieving revision 1.45
diff -u -r1.45 agp.c
--- pci/agp.c	16 Aug 2004 12:25:48 -0000	1.45
+++ pci/agp.c	11 Mar 2005 19:17:09 -0000
@@ -501,6 +501,7 @@
 	 * because vm_page_grab() used with VM_ALLOC_RETRY may
 	 * block and we can't hold a mutex while blocking.
 	 */
+	VM_OBJECT_LOCK(mem->am_obj);
 	for (i = 0; i < mem->am_size; i += PAGE_SIZE) {
 		/*
 		 * Find a page from the object and wire it
@@ -509,18 +510,18 @@
 		 * AGP_PAGE_SIZE. If this is the first call to bind,
 		 * the pages will be allocated and zeroed.
 		 */
-		VM_OBJECT_LOCK(mem->am_obj);
 		m = vm_page_grab(mem->am_obj, OFF_TO_IDX(i),
 		    VM_ALLOC_WIRED | VM_ALLOC_ZERO | VM_ALLOC_RETRY);
-		VM_OBJECT_UNLOCK(mem->am_obj);
 		AGP_DPF("found page pa=%#x\n", VM_PAGE_TO_PHYS(m));
 	}
+	VM_OBJECT_UNLOCK(mem->am_obj);
 
 	mtx_lock(&sc->as_lock);
 
 	if (mem->am_is_bound) {
 		device_printf(dev, "memory already bound\n");
 		error = EINVAL;
+		VM_OBJECT_LOCK(mem->am_obj);
 		goto bad;
 	}
 	
@@ -532,10 +533,9 @@
 	 * (i.e. use alpha_XXX_dmamap()). I don't have access to any
 	 * alpha AGP hardware to check.
 	 */
+	VM_OBJECT_LOCK(mem->am_obj);
 	for (i = 0; i < mem->am_size; i += PAGE_SIZE) {
-		VM_OBJECT_LOCK(mem->am_obj);
 		m = vm_page_lookup(mem->am_obj, OFF_TO_IDX(i));
-		VM_OBJECT_UNLOCK(mem->am_obj);
 
 		/*
 		 * Install entries in the GATT, making sure that if
@@ -566,6 +566,7 @@
 		vm_page_wakeup(m);
 		vm_page_unlock_queues();
 	}
+	VM_OBJECT_UNLOCK(mem->am_obj);
 
 	/*
 	 * Flush the cpu cache since we are providing a new mapping
@@ -586,7 +587,7 @@
 	return 0;
 bad:
 	mtx_unlock(&sc->as_lock);
-	VM_OBJECT_LOCK(mem->am_obj);
+	VM_OBJECT_LOCK_ASSERT(mem->am_obj, MA_OWNED);
 	for (i = 0; i < mem->am_size; i += PAGE_SIZE) {
 		m = vm_page_lookup(mem->am_obj, OFF_TO_IDX(i));
 		vm_page_lock_queues();
Index: pci/agp_i810.c
===================================================================
RCS file: /home/ncvs/src/sys/pci/agp_i810.c,v
retrieving revision 1.30.2.1
diff -u -r1.30.2.1 agp_i810.c
--- pci/agp_i810.c	1 Mar 2005 08:11:50 -0000	1.30.2.1
+++ pci/agp_i810.c	11 Mar 2005 19:15:45 -0000
@@ -609,13 +609,10 @@
 		vm_page_t m;
 
 		VM_OBJECT_LOCK(mem->am_obj);
-		m = vm_page_grab(mem->am_obj, 0,
+		m = vm_page_grab(mem->am_obj, 0, VM_ALLOC_NOBUSY |
 		    VM_ALLOC_WIRED | VM_ALLOC_ZERO | VM_ALLOC_RETRY);
 		VM_OBJECT_UNLOCK(mem->am_obj);
-		vm_page_lock_queues();
 		mem->am_physical = VM_PAGE_TO_PHYS(m);
-		vm_page_wakeup(m);
-		vm_page_unlock_queues();
 	} else {
 		mem->am_physical = 0;
 	}

--sm4nu43k4a2Rpi4c--



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?20050311192009.GK28845>