From 3325a4ad7122acdbfae5360cafc7152b32eefd57 Mon Sep 17 00:00:00 2001
From: Johan Hovold <johan@hovoldconsulting.com>
Date: Tue, 14 Jul 2015 15:43:33 +0200
Subject: [PATCH] greybus: operation: fix operation look-up race

Make sure to fully initialise the operation before adding it to the
active list when sending a request.

The operation should be fully initialised before adding it to the active
list to avoid racing with operation look up when receiving a response,
something which could potentially lead to a match against some earlier
(or intermediate) value of the id field.

Signed-off-by: Johan Hovold <johan@hovoldconsulting.com>
Signed-off-by: Greg Kroah-Hartman <gregkh@google.com>
---
 drivers/staging/greybus/operation.c | 20 +++++++++-----------
 1 file changed, 9 insertions(+), 11 deletions(-)

diff --git a/drivers/staging/greybus/operation.c b/drivers/staging/greybus/operation.c
index 5cd4665c645cf..f7b0aa970bbcd 100644
--- a/drivers/staging/greybus/operation.c
+++ b/drivers/staging/greybus/operation.c
@@ -642,16 +642,6 @@ int gb_operation_request_send(struct gb_operation *operation,
 
 	if (!callback)
 		return -EINVAL;
-
-	/*
-	 * First, get an extra reference on the operation.
-	 * It'll be dropped when the operation completes.
-	 */
-	gb_operation_get(operation);
-	ret = gb_operation_get_active(operation);
-	if (ret)
-		goto err_put;
-
 	/*
 	 * Record the callback function, which is executed in
 	 * non-atomic (workqueue) context when the final result
@@ -668,9 +658,17 @@ int gb_operation_request_send(struct gb_operation *operation,
 	header = operation->request->header;
 	header->operation_id = cpu_to_le16(operation->id);
 
-	/* All set, send the request */
 	gb_operation_result_set(operation, -EINPROGRESS);
 
+	/*
+	 * Get an extra reference on the operation. It'll be dropped when the
+	 * operation completes.
+	 */
+	gb_operation_get(operation);
+	ret = gb_operation_get_active(operation);
+	if (ret)
+		goto err_put;
+
 	ret = gb_message_send(operation->request, gfp);
 	if (ret)
 		goto err_put_active;
-- 
2.30.2