changeset 7793:4dbbc0a3f135

6755897 recursive mutex enter in spa_vdev_enter when running test suite
author Jeff Bonwick <Jeff.Bonwick@Sun.COM>
date Thu, 09 Oct 2008 18:07:16 -0700
parents 052836d32b27
children be12a49f5895
files usr/src/cmd/ztest/ztest.c usr/src/uts/common/fs/zfs/spa.c
diffstat 2 files changed, 19 insertions(+), 1 deletions(-) [+]
line wrap: on
line diff
--- a/usr/src/cmd/ztest/ztest.c	Thu Oct 09 17:28:15 2008 -0700
+++ b/usr/src/cmd/ztest/ztest.c	Thu Oct 09 18:07:16 2008 -0700
@@ -984,6 +984,7 @@
 	size_t oldsize, newsize;
 	char oldpath[MAXPATHLEN], newpath[MAXPATHLEN];
 	int replacing;
+	int oldvd_has_siblings = B_FALSE;
 	int newvd_is_spare = B_FALSE;
 	int oldvd_is_log;
 	int error, expected_error;
@@ -1021,6 +1022,7 @@
 	 * mirror vdev -- in which case, pick a random child.
 	 */
 	while (oldvd->vdev_children != 0) {
+		oldvd_has_siblings = B_TRUE;
 		ASSERT(oldvd->vdev_children == 2);
 		oldvd = oldvd->vdev_child[ztest_random(2)];
 	}
@@ -1032,6 +1034,19 @@
 	pvd = oldvd->vdev_parent;
 
 	/*
+	 * If oldvd has siblings, then half of the time, detach it.
+	 */
+	if (oldvd_has_siblings && ztest_random(2) == 0) {
+		spa_config_exit(spa, SCL_VDEV, FTAG);
+		error = spa_vdev_detach(spa, oldguid, B_FALSE);
+		if (error != 0 && error != ENODEV && error != EBUSY)
+			fatal(0, "detach (%s) returned %d",
+			    oldpath, error);
+		(void) mutex_unlock(&ztest_shared->zs_vdev_lock);
+		return;
+	}
+
+	/*
 	 * For the new vdev, choose with equal probability between the two
 	 * standard paths (ending in either 'a' or 'b') or a random hot spare.
 	 */
--- a/usr/src/uts/common/fs/zfs/spa.c	Thu Oct 09 17:28:15 2008 -0700
+++ b/usr/src/uts/common/fs/zfs/spa.c	Thu Oct 09 18:07:16 2008 -0700
@@ -3184,8 +3184,11 @@
 		while ((spa = spa_next(spa)) != NULL) {
 			if (spa->spa_state != POOL_STATE_ACTIVE)
 				continue;
-
+			spa_open_ref(spa, FTAG);
+			mutex_exit(&spa_namespace_lock);
 			(void) spa_vdev_remove(spa, unspare_guid, B_TRUE);
+			mutex_enter(&spa_namespace_lock);
+			spa_close(spa, FTAG);
 		}
 		mutex_exit(&spa_namespace_lock);
 	}