123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263 |
- From 249ccc9a345b7641aaf276867a375cd50f41627d Mon Sep 17 00:00:00 2001
- From: Phil Elwell <phil@raspberrypi.org>
- Date: Thu, 21 Apr 2016 13:49:32 +0100
- Subject: [PATCH] vchiq_arm: Add completion records under the mutex
- An issue was observed when flushing openmax components
- which generate a large number of messages returning
- buffers to host.
- We occasionally found a duplicate message from 16
- messages prior, resulting in a buffer returned twice.
- While only one thread adds completions, without the
- mutex you don't get the protection of the automatic
- memory barrier you get with synchronisation objects.
- Signed-off-by: Phil Elwell <phil@raspberrypi.org>
- ---
- drivers/misc/vc04_services/interface/vchiq_arm/vchiq_arm.c | 13 ++++++++++++-
- 1 file changed, 12 insertions(+), 1 deletion(-)
- --- a/drivers/misc/vc04_services/interface/vchiq_arm/vchiq_arm.c
- +++ b/drivers/misc/vc04_services/interface/vchiq_arm/vchiq_arm.c
- @@ -210,6 +210,8 @@ add_completion(VCHIQ_INSTANCE_T instance
- VCHIQ_COMPLETION_DATA_T *completion;
- DEBUG_INITIALISE(g_state.local)
-
- + mutex_lock(&instance->completion_mutex);
- +
- while (instance->completion_insert ==
- (instance->completion_remove + MAX_COMPLETIONS)) {
- /* Out of space - wait for the client */
- @@ -217,11 +219,17 @@ add_completion(VCHIQ_INSTANCE_T instance
- vchiq_log_trace(vchiq_arm_log_level,
- "add_completion - completion queue full");
- DEBUG_COUNT(COMPLETION_QUEUE_FULL_COUNT);
- +
- + mutex_unlock(&instance->completion_mutex);
- if (down_interruptible(&instance->remove_event) != 0) {
- vchiq_log_info(vchiq_arm_log_level,
- "service_callback interrupted");
- return VCHIQ_RETRY;
- - } else if (instance->closing) {
- + }
- +
- + mutex_lock(&instance->completion_mutex);
- + if (instance->closing) {
- + mutex_unlock(&instance->completion_mutex);
- vchiq_log_info(vchiq_arm_log_level,
- "service_callback closing");
- return VCHIQ_SUCCESS;
- @@ -254,8 +262,11 @@ add_completion(VCHIQ_INSTANCE_T instance
- if (reason == VCHIQ_MESSAGE_AVAILABLE)
- user_service->message_available_pos =
- instance->completion_insert;
- +
- instance->completion_insert++;
-
- + mutex_unlock(&instance->completion_mutex);
- +
- up(&instance->insert_event);
-
- return VCHIQ_SUCCESS;
|