Commit b0355c02 authored by Ben Walker's avatar Ben Walker
Browse files

test/blobfs: Use a lock instead of volatiles



Thread sanitizer detected a number of race conditions in this
test. Use a simple lock to pass messages between threads instead
because that's easier to get right.

Change-Id: Ia1f905f7b3787b4e89cf5ca1d16a1f24e0a562f9
Signed-off-by: default avatarBen Walker <benjamin.walker@intel.com>
Reviewed-on: https://review.gerrithub.io/362437


Reviewed-by: default avatarJim Harris <james.r.harris@intel.com>
Tested-by: default avatarSPDK Automated Test System <sys_sgsw@intel.com>
parent 830912e2
Loading
Loading
Loading
Loading
+23 −16
Original line number Diff line number Diff line
@@ -58,8 +58,8 @@ struct ut_request {
	int from_ut;
};

volatile struct ut_request *g_req = NULL;
volatile int g_phase = 0;
static struct ut_request *g_req = NULL;
static pthread_mutex_t g_mutex = PTHREAD_MUTEX_INITIALIZER;

static void
send_request(fs_request_fn fn, void *arg)
@@ -72,10 +72,10 @@ send_request(fs_request_fn fn, void *arg)
	req->arg = arg;
	req->done = 0;
	req->from_ut = 0;

	pthread_mutex_lock(&g_mutex);
	g_req = req;
	spdk_mb();
	g_phase = !g_phase;
	spdk_mb();
	pthread_mutex_unlock(&g_mutex);
}

static void
@@ -87,12 +87,19 @@ ut_send_request(fs_request_fn fn, void *arg)
	req.arg = arg;
	req.done = 0;
	req.from_ut = 1;

	pthread_mutex_lock(&g_mutex);
	g_req = &req;
	spdk_mb();
	g_phase = !g_phase;
	spdk_mb();
	while (req.done == 0)
		;
	pthread_mutex_unlock(&g_mutex);

	while (1) {
		pthread_mutex_lock(&g_mutex);
		if (req.done == 1) {
			pthread_mutex_unlock(&g_mutex);
			break;
		}
		pthread_mutex_unlock(&g_mutex);
	}
}

static void
@@ -248,21 +255,21 @@ static void *
spdk_thread(void *arg)
{
	struct ut_request *req;
	int phase = 0;

	spdk_allocate_thread();

	while (1) {
		spdk_mb();
		if (phase != g_phase) {
			req = (void *)g_req;
		pthread_mutex_lock(&g_mutex);
		if (g_req != NULL) {
			req = g_req;
			req->fn(req->arg);
			req->done = 1;
			spdk_mb();
			if (!req->from_ut) {
				free(req);
			}
			phase = !phase;
			g_req = NULL;
		}
		pthread_mutex_unlock(&g_mutex);
	}

	return NULL;