[stgt] [PATCH 12/12] Add a mutex and protect nexus_list
Chandra Seetharaman
sekharan at us.ibm.com
Mon Sep 27 07:21:33 CEST 2010
Serialize the access of it_nexus_list by protecting it by a mutex.
Signed-off-by: Chandra Seetharaman <sekharan at us.ibm.com>
---
usr/target.c | 34 ++++++++++++++++++++++++++++++++--
usr/target.h | 2 ++
2 files changed, 34 insertions(+), 2 deletions(-)
Index: tgt-1.0.8.4/usr/target.h
===================================================================
--- tgt-1.0.8.4.orig/usr/target.h
+++ tgt-1.0.8.4/usr/target.h
@@ -34,6 +34,8 @@ struct target {
struct list_head it_nexus_list;
+ pthread_mutex_t it_nexus_lock;
+
struct backingstore_template *bst;
struct list_head acl_list;
Index: tgt-1.0.8.4/usr/target.c
===================================================================
--- tgt-1.0.8.4.orig/usr/target.c
+++ tgt-1.0.8.4/usr/target.c
@@ -27,6 +27,7 @@
#include <string.h>
#include <time.h>
#include <unistd.h>
+#include <pthread.h>
#include <sys/socket.h>
#include <sys/time.h>
@@ -90,10 +91,14 @@ static struct it_nexus *it_nexus_lookup(
if (!target)
return NULL;
+ pthread_mutex_lock(&target->it_nexus_lock);
list_for_each_entry(itn, &target->it_nexus_list, nexus_siblings) {
- if (itn->itn_id == itn_id)
+ if (itn->itn_id == itn_id) {
+ pthread_mutex_unlock(&target->it_nexus_lock);
return itn;
+ }
}
+ pthread_mutex_unlock(&target->it_nexus_lock);
return NULL;
}
@@ -215,6 +220,7 @@ void ua_sense_add_other_it_nexus(uint64_
struct it_nexus_lu_info *itn_lu;
int ret;
+ pthread_mutex_lock(&lu->tgt->it_nexus_lock);
list_for_each_entry(itn, &lu->tgt->it_nexus_list, nexus_siblings) {
if (itn->itn_id == itn_id)
@@ -232,6 +238,7 @@ void ua_sense_add_other_it_nexus(uint64_
lu->lun, itn_id);
}
}
+ pthread_mutex_unlock(&lu->tgt->it_nexus_lock);
}
int it_nexus_create(int tid, uint64_t itn_id, int host_no, char *info)
@@ -284,7 +291,9 @@ int it_nexus_create(int tid, uint64_t it
for (i = 0; i < ARRAY_SIZE(itn->cmd_hash_list); i++)
INIT_LIST_HEAD(&itn->cmd_hash_list[i]);
+ pthread_mutex_lock(&target->it_nexus_lock);
list_add_tail(&itn->nexus_siblings, &target->it_nexus_list);
+ pthread_mutex_unlock(&target->it_nexus_lock);
return 0;
out:
@@ -313,7 +322,9 @@ int it_nexus_destroy(int tid, uint64_t i
it_nexus_del_lu_info(itn);
+ pthread_mutex_lock(&itn->nexus_target->it_nexus_lock);
list_del(&itn->nexus_siblings);
+ pthread_mutex_unlock(&itn->nexus_target->it_nexus_lock);
free(itn);
return 0;
}
@@ -570,6 +581,7 @@ int tgt_device_create(int tid, int dev_t
}
list_add_tail(&lu->device_siblings, &pos->device_siblings);
+ pthread_mutex_lock(&target->it_nexus_lock);
list_for_each_entry(itn, &target->it_nexus_list, nexus_siblings) {
itn_lu = zalloc(sizeof(*itn_lu));
if (!itn_lu)
@@ -589,6 +601,7 @@ int tgt_device_create(int tid, int dev_t
ASC_REPORTED_LUNS_DATA_HAS_CHANGED);
}
}
+ pthread_mutex_unlock(&target->it_nexus_lock);
if (backing && !path)
lu->dev_type_template.lu_offline(lu);
@@ -645,6 +658,7 @@ int tgt_device_destroy(int tid, uint64_t
if (lu->bst->bs_exit)
lu->bst->bs_exit(lu);
+ pthread_mutex_lock(&target->it_nexus_lock);
list_for_each_entry(itn, &target->it_nexus_list, nexus_siblings) {
list_for_each_entry_safe(itn_lu, next, &itn->it_nexus_lu_info_list,
lu_info_siblings) {
@@ -654,6 +668,7 @@ int tgt_device_destroy(int tid, uint64_t
}
}
}
+ pthread_mutex_unlock(&target->it_nexus_lock);
list_del(&lu->device_siblings);
@@ -664,6 +679,7 @@ int tgt_device_destroy(int tid, uint64_t
free(lu);
+ pthread_mutex_lock(&target->it_nexus_lock);
list_for_each_entry(itn, &target->it_nexus_list, nexus_siblings) {
list_for_each_entry(itn_lu, &itn->it_nexus_lu_info_list,
lu_info_siblings) {
@@ -672,6 +688,7 @@ int tgt_device_destroy(int tid, uint64_t
ASC_REPORTED_LUNS_DATA_HAS_CHANGED);
}
}
+ pthread_mutex_unlock(&target->it_nexus_lock);
return 0;
}
@@ -1095,6 +1112,7 @@ static int abort_task_set(struct mgmt_re
eprintf("found %" PRIx64 " %d\n", tag, all);
+ pthread_mutex_lock(&target->it_nexus_lock);
list_for_each_entry(itn, &target->it_nexus_list, nexus_siblings) {
for (i = 0; i < ARRAY_SIZE(itn->cmd_hash_list); i++) {
struct list_head *list = &itn->cmd_hash_list[i];
@@ -1110,6 +1128,7 @@ static int abort_task_set(struct mgmt_re
}
}
}
+ pthread_mutex_unlock(&target->it_nexus_lock);
return count;
}
@@ -1167,6 +1186,7 @@ enum mgmt_req_result target_mgmt_request
if (mreq->busy)
send = 0;
+ pthread_mutex_lock(&target->it_nexus_lock);
list_for_each_entry(itn, &target->it_nexus_list, nexus_siblings) {
list_for_each_entry(itn_lu, &itn->it_nexus_lu_info_list,
lu_info_siblings) {
@@ -1181,6 +1201,7 @@ enum mgmt_req_result target_mgmt_request
}
}
}
+ pthread_mutex_unlock(&target->it_nexus_lock);
break;
case LOGICAL_UNIT_RESET:
lun = scsi_get_devid(target->lid, lun_buf);
@@ -1189,6 +1210,7 @@ enum mgmt_req_result target_mgmt_request
if (mreq->busy)
send = 0;
+ pthread_mutex_lock(&target->it_nexus_lock);
list_for_each_entry(itn, &target->it_nexus_list, nexus_siblings) {
list_for_each_entry(itn_lu, &itn->it_nexus_lu_info_list,
lu_info_siblings) {
@@ -1198,6 +1220,7 @@ enum mgmt_req_result target_mgmt_request
}
}
}
+ pthread_mutex_unlock(&target->it_nexus_lock);
break;
default:
err = -EINVAL;
@@ -1685,7 +1708,7 @@ static char *print_type(int type)
int tgt_target_show_all(char *buf, int rest)
{
- int total = 0, max = rest;
+ int total = 0, max = rest, mutex_held = 0;
char strflags[128];
struct target *target;
struct scsi_lu *lu;
@@ -1705,12 +1728,16 @@ int tgt_target_show_all(char *buf, int r
shprintf(total, buf, rest, _TAB1 "I_T nexus information:\n");
+ pthread_mutex_lock(&target->it_nexus_lock);
+ mutex_held = 1;
list_for_each_entry(nexus, &target->it_nexus_list, nexus_siblings) {
shprintf(total, buf, rest, _TAB2 "I_T nexus: %" PRIu64 "\n",
nexus->itn_id);
if (nexus->info)
shprintf(total, buf, rest, "%s", nexus->info);
}
+ mutex_held = 0;
+ pthread_mutex_unlock(&target->it_nexus_lock);
shprintf(total, buf, rest, _TAB1 "LUN information:\n");
list_for_each_entry(lu, &target->device_list, device_siblings)
@@ -1762,6 +1789,8 @@ int tgt_target_show_all(char *buf, int r
}
return total;
overflow:
+ if (mutex_held)
+ pthread_mutex_unlock(&target->it_nexus_lock);
return max;
}
@@ -1857,6 +1886,7 @@ int tgt_target_create(int lld, int tid,
INIT_LIST_HEAD(&target->acl_list);
INIT_LIST_HEAD(&target->it_nexus_list);
+ pthread_mutex_init(&target->it_nexus_lock, NULL);
tgt_device_create(tid, TYPE_RAID, 0, NULL, 0);
--
To unsubscribe from this list: send the line "unsubscribe stgt" in
the body of a message to majordomo at vger.kernel.org
More majordomo info at http://vger.kernel.org/majordomo-info.html
More information about the stgt
mailing list