mirror of
https://github.com/SCST-project/scst.git
synced 2026-08-18 21:26:31 +00:00
Deeply reworked patch from Mehmet Ali Cer <mehmet.ali.cer@gmail.com> implementing flat LUNs addressing methods required by some operation systems.
git-svn-id: http://svn.code.sf.net/p/scst/svn/trunk@1558 d57e44dd-8a1f-0410-8b47-8ef2f437770f
This commit is contained in:
@@ -2076,6 +2076,8 @@ struct scst_acg {
|
||||
|
||||
struct kobject *luns_kobj;
|
||||
struct kobject *initiators_kobj;
|
||||
|
||||
unsigned int addr_method;
|
||||
};
|
||||
|
||||
/*
|
||||
|
||||
+18
-4
@@ -1107,7 +1107,7 @@ static struct scst_aen *scst_alloc_aen(struct scst_session *sess,
|
||||
aen->sess = sess;
|
||||
scst_sess_get(sess);
|
||||
|
||||
aen->lun = scst_pack_lun(unpacked_lun);
|
||||
aen->lun = scst_pack_lun(unpacked_lun, sess->acg->addr_method);
|
||||
|
||||
out:
|
||||
TRACE_EXIT_HRES((unsigned long)aen);
|
||||
@@ -2162,6 +2162,8 @@ struct scst_acg *scst_alloc_add_acg(struct scst_tgt *tgt,
|
||||
goto out_free;
|
||||
}
|
||||
|
||||
acg->addr_method = SCST_LUN_ADDR_METHOD_PERIPHERAL;
|
||||
|
||||
#ifdef CONFIG_SCST_PROC
|
||||
TRACE_DBG("Adding acg %s to scst_acg_list", acg_name);
|
||||
list_add_tail(&acg->acg_list_entry, &scst_acg_list);
|
||||
@@ -4259,13 +4261,25 @@ out:
|
||||
}
|
||||
EXPORT_SYMBOL(scst_get_cdb_info);
|
||||
|
||||
/* Packs SCST LUN back to SCSI form using peripheral device addressing method */
|
||||
uint64_t scst_pack_lun(const uint64_t lun)
|
||||
/* Packs SCST LUN back to SCSI form */
|
||||
uint64_t scst_pack_lun(const uint64_t lun, unsigned int addr_method)
|
||||
{
|
||||
uint64_t res;
|
||||
|
||||
uint64_t res = 0;
|
||||
uint16_t *p = (uint16_t *)&res;
|
||||
|
||||
res = lun;
|
||||
|
||||
if ((addr_method == SCST_LUN_ADDR_METHOD_FLAT) && (lun != 0)) {
|
||||
/*
|
||||
* Flat space: luns other than 0 should use flat space
|
||||
* addressing method.
|
||||
*/
|
||||
*p = 0x7fff & *p;
|
||||
*p = 0x4000 | *p;
|
||||
}
|
||||
/* Default is to use peripheral device addressing mode */
|
||||
|
||||
*p = cpu_to_be16(*p);
|
||||
|
||||
TRACE_EXIT_HRES((unsigned long)res);
|
||||
|
||||
@@ -125,6 +125,10 @@ extern unsigned long scst_trace_flag;
|
||||
|
||||
#define SCST_TGT_RETRY_TIMEOUT (3/2*HZ)
|
||||
|
||||
/* Definitions of symbolic constants for LUN addressing method */
|
||||
#define SCST_LUN_ADDR_METHOD_PERIPHERAL 0
|
||||
#define SCST_LUN_ADDR_METHOD_FLAT 1
|
||||
|
||||
extern unsigned int scst_max_dev_cmd_mem;
|
||||
|
||||
extern mempool_t *scst_mgmt_mempool;
|
||||
@@ -417,7 +421,7 @@ int scst_alloc_space(struct scst_cmd *cmd);
|
||||
int scst_lib_init(void);
|
||||
void scst_lib_exit(void);
|
||||
|
||||
uint64_t scst_pack_lun(const uint64_t lun);
|
||||
uint64_t scst_pack_lun(const uint64_t lun, unsigned int addr_method);
|
||||
uint64_t scst_unpack_lun(const uint8_t *lun, int len);
|
||||
|
||||
struct scst_mgmt_cmd *scst_alloc_mgmt_cmd(gfp_t gfp_mask);
|
||||
|
||||
+92
-11
@@ -37,7 +37,7 @@
|
||||
static int scst_proc_init_groups(void);
|
||||
static void scst_proc_cleanup_groups(void);
|
||||
static int scst_proc_assign_handler(char *buf);
|
||||
static int scst_proc_group_add(const char *p);
|
||||
static int scst_proc_group_add(const char *p, unsigned int addr_method);
|
||||
static int scst_proc_del_free_acg(struct scst_acg *acg, int remove_proc);
|
||||
|
||||
static struct scst_proc_data scst_version_proc_data;
|
||||
@@ -45,6 +45,7 @@ static struct scst_proc_data scst_help_proc_data;
|
||||
static struct scst_proc_data scst_sgv_proc_data;
|
||||
static struct scst_proc_data scst_groups_names_proc_data;
|
||||
static struct scst_proc_data scst_groups_devices_proc_data;
|
||||
static struct scst_proc_data scst_groups_addr_method_proc_data;
|
||||
static struct scst_proc_data scst_sessions_proc_data;
|
||||
static struct scst_proc_data scst_dev_handler_type_proc_data;
|
||||
static struct scst_proc_data scst_tgt_proc_data;
|
||||
@@ -67,6 +68,7 @@ static struct scst_proc_data scst_dev_handler_proc_data;
|
||||
#define SCST_PROC_GROUPS_ENTRY_NAME "groups"
|
||||
#define SCST_PROC_GROUPS_DEVICES_ENTRY_NAME "devices"
|
||||
#define SCST_PROC_GROUPS_USERS_ENTRY_NAME "names"
|
||||
#define SCST_PROC_GROUPS_ADDR_METHOD_ENTRY_NAME "addr_method"
|
||||
|
||||
#ifdef CONFIG_SCST_MEASURE_LATENCY
|
||||
#define SCST_PROC_LAT_ENTRY_NAME "latency"
|
||||
@@ -127,7 +129,7 @@ static struct scst_trace_log scst_proc_local_trace_tbl[] = {
|
||||
static char *scst_proc_help_string =
|
||||
" echo \"assign H:C:I:L HANDLER_NAME\" >/proc/scsi_tgt/scsi_tgt\n"
|
||||
"\n"
|
||||
" echo \"add_group GROUP_NAME\" >/proc/scsi_tgt/scsi_tgt\n"
|
||||
" echo \"add_group GROUP_NAME [FLAT]\" >/proc/scsi_tgt/scsi_tgt\n"
|
||||
" echo \"del_group GROUP_NAME\" >/proc/scsi_tgt/scsi_tgt\n"
|
||||
" echo \"rename_group OLD_NAME NEW_NAME\" >/proc/scsi_tgt/scsi_tgt\n"
|
||||
"\n"
|
||||
@@ -811,17 +813,30 @@ static int scst_proc_group_add_tree(struct scst_acg *acg, const char *name)
|
||||
goto out;
|
||||
}
|
||||
|
||||
scst_groups_addr_method_proc_data.data = acg;
|
||||
generic = scst_create_proc_entry(acg->acg_proc_root,
|
||||
SCST_PROC_GROUPS_ADDR_METHOD_ENTRY_NAME,
|
||||
&scst_groups_addr_method_proc_data);
|
||||
if (!generic) {
|
||||
PRINT_ERROR("Cannot init /proc/%s/%s/%s/%s",
|
||||
SCST_PROC_ENTRY_NAME,
|
||||
SCST_PROC_GROUPS_ENTRY_NAME,
|
||||
name, SCST_PROC_GROUPS_ADDR_METHOD_ENTRY_NAME);
|
||||
res = -ENOMEM;
|
||||
goto out_remove;
|
||||
}
|
||||
|
||||
scst_groups_devices_proc_data.data = acg;
|
||||
generic = scst_create_proc_entry(acg->acg_proc_root,
|
||||
SCST_PROC_GROUPS_DEVICES_ENTRY_NAME,
|
||||
&scst_groups_devices_proc_data);
|
||||
if (!generic) {
|
||||
PRINT_ERROR("cannot init /proc/%s/%s/%s/%s",
|
||||
PRINT_ERROR("Cannot init /proc/%s/%s/%s/%s",
|
||||
SCST_PROC_ENTRY_NAME,
|
||||
SCST_PROC_GROUPS_ENTRY_NAME,
|
||||
name, SCST_PROC_GROUPS_DEVICES_ENTRY_NAME);
|
||||
res = -ENOMEM;
|
||||
goto out_remove;
|
||||
goto out_remove0;
|
||||
}
|
||||
|
||||
scst_groups_names_proc_data.data = acg;
|
||||
@@ -829,7 +844,7 @@ static int scst_proc_group_add_tree(struct scst_acg *acg, const char *name)
|
||||
SCST_PROC_GROUPS_USERS_ENTRY_NAME,
|
||||
&scst_groups_names_proc_data);
|
||||
if (!generic) {
|
||||
PRINT_ERROR("cannot init /proc/%s/%s/%s/%s",
|
||||
PRINT_ERROR("Cannot init /proc/%s/%s/%s/%s",
|
||||
SCST_PROC_ENTRY_NAME,
|
||||
SCST_PROC_GROUPS_ENTRY_NAME,
|
||||
name, SCST_PROC_GROUPS_USERS_ENTRY_NAME);
|
||||
@@ -845,6 +860,9 @@ out_remove1:
|
||||
remove_proc_entry(SCST_PROC_GROUPS_DEVICES_ENTRY_NAME,
|
||||
acg->acg_proc_root);
|
||||
|
||||
out_remove0:
|
||||
remove_proc_entry(SCST_PROC_GROUPS_ADDR_METHOD_ENTRY_NAME,
|
||||
acg->acg_proc_root);
|
||||
out_remove:
|
||||
remove_proc_entry(name, scst_proc_groups_root);
|
||||
goto out;
|
||||
@@ -855,9 +873,9 @@ static void scst_proc_del_acg_tree(struct proc_dir_entry *acg_proc_root,
|
||||
{
|
||||
TRACE_ENTRY();
|
||||
|
||||
remove_proc_entry(SCST_PROC_GROUPS_ADDR_METHOD_ENTRY_NAME, acg_proc_root);
|
||||
remove_proc_entry(SCST_PROC_GROUPS_USERS_ENTRY_NAME, acg_proc_root);
|
||||
remove_proc_entry(SCST_PROC_GROUPS_DEVICES_ENTRY_NAME,
|
||||
acg_proc_root);
|
||||
remove_proc_entry(SCST_PROC_GROUPS_DEVICES_ENTRY_NAME, acg_proc_root);
|
||||
remove_proc_entry(name, scst_proc_groups_root);
|
||||
|
||||
TRACE_EXIT();
|
||||
@@ -865,7 +883,7 @@ static void scst_proc_del_acg_tree(struct proc_dir_entry *acg_proc_root,
|
||||
}
|
||||
|
||||
/* The activity supposed to be suspended and scst_mutex held */
|
||||
static int scst_proc_group_add(const char *p)
|
||||
static int scst_proc_group_add(const char *p, unsigned int addr_method)
|
||||
{
|
||||
int res = 0, len = strlen(p) + 1;
|
||||
struct scst_acg *acg;
|
||||
@@ -886,6 +904,8 @@ static int scst_proc_group_add(const char *p)
|
||||
goto out_free;
|
||||
}
|
||||
|
||||
acg->addr_method = addr_method;
|
||||
|
||||
res = scst_proc_group_add_tree(acg, p);
|
||||
if (res != 0)
|
||||
goto out_free_acg;
|
||||
@@ -1536,8 +1556,9 @@ static ssize_t scst_proc_scsi_tgt_gen_write(struct file *file,
|
||||
size_t length, loff_t *off)
|
||||
{
|
||||
int res, rc = 0, action;
|
||||
char *buffer, *p, *pp;
|
||||
char *buffer, *p, *pp, *ppp;
|
||||
struct scst_acg *a, *acg = NULL;
|
||||
unsigned int addr_method = SCST_LUN_ADDR_METHOD_PERIPHERAL;
|
||||
|
||||
TRACE_ENTRY();
|
||||
|
||||
@@ -1566,7 +1587,7 @@ static ssize_t scst_proc_scsi_tgt_gen_write(struct file *file,
|
||||
}
|
||||
|
||||
/*
|
||||
* Usage: echo "add_group GROUP_NAME" >/proc/scsi_tgt/scsi_tgt
|
||||
* Usage: echo "add_group GROUP_NAME [FLAT]" >/proc/scsi_tgt/scsi_tgt
|
||||
* or echo "del_group GROUP_NAME" >/proc/scsi_tgt/scsi_tgt
|
||||
* or echo "rename_group OLD_NAME NEW_NAME" >/proc/scsi_tgt/scsi_tgt"
|
||||
* or echo "assign H:C:I:L HANDLER_NAME" >/proc/scsi_tgt/scsi_tgt
|
||||
@@ -1603,6 +1624,9 @@ static ssize_t scst_proc_scsi_tgt_gen_write(struct file *file,
|
||||
|
||||
res = length;
|
||||
|
||||
while (isspace(*p) && *p != '\0')
|
||||
p++;
|
||||
|
||||
switch (action) {
|
||||
case SCST_PROC_ACTION_ADD_GROUP:
|
||||
case SCST_PROC_ACTION_DEL_GROUP:
|
||||
@@ -1618,6 +1642,29 @@ static ssize_t scst_proc_scsi_tgt_gen_write(struct file *file,
|
||||
if (*pp != '\0') {
|
||||
switch (action) {
|
||||
case SCST_PROC_ACTION_ADD_GROUP:
|
||||
ppp = pp;
|
||||
while (!isspace(*ppp) && *ppp != '\0')
|
||||
ppp++;
|
||||
if (*ppp != '\0') {
|
||||
*ppp = '\0';
|
||||
ppp++;
|
||||
while (isspace(*ppp) && *ppp != '\0')
|
||||
ppp++;
|
||||
if (*ppp != '\0') {
|
||||
PRINT_ERROR("%s", "Too many "
|
||||
"arguments");
|
||||
res = -EINVAL;
|
||||
goto out_up_free;
|
||||
}
|
||||
}
|
||||
if (strcasecmp(pp, "FLAT") != 0) {
|
||||
PRINT_ERROR("Unexpected "
|
||||
"argument %s", pp);
|
||||
res = -EINVAL;
|
||||
goto out_up_free;
|
||||
} else
|
||||
addr_method = SCST_LUN_ADDR_METHOD_FLAT;
|
||||
break;
|
||||
case SCST_PROC_ACTION_DEL_GROUP:
|
||||
PRINT_ERROR("%s", "Too many "
|
||||
"arguments");
|
||||
@@ -1650,7 +1697,7 @@ static ssize_t scst_proc_scsi_tgt_gen_write(struct file *file,
|
||||
res = -EINVAL;
|
||||
goto out_up_free;
|
||||
}
|
||||
rc = scst_proc_group_add(p);
|
||||
rc = scst_proc_group_add(p, addr_method);
|
||||
break;
|
||||
case SCST_PROC_ACTION_DEL_GROUP:
|
||||
if (acg == NULL) {
|
||||
@@ -2396,6 +2443,40 @@ static struct scst_proc_data scst_groups_names_proc_data = {
|
||||
.show = scst_groups_names_show,
|
||||
};
|
||||
|
||||
static int scst_groups_addr_method_show(struct seq_file *seq, void *v)
|
||||
{
|
||||
int res = 0;
|
||||
struct scst_acg *acg = (struct scst_acg *)seq->private;
|
||||
|
||||
TRACE_ENTRY();
|
||||
|
||||
if (mutex_lock_interruptible(&scst_mutex) != 0) {
|
||||
res = -EINTR;
|
||||
goto out;
|
||||
}
|
||||
|
||||
switch (acg->addr_method) {
|
||||
case SCST_LUN_ADDR_METHOD_FLAT:
|
||||
seq_printf(seq, "%s\n", "FLAT");
|
||||
break;
|
||||
case SCST_LUN_ADDR_METHOD_PERIPHERAL:
|
||||
seq_printf(seq, "%s\n", "PERIPHERAL");
|
||||
break;
|
||||
default:
|
||||
seq_printf(seq, "%s\n", "UNKNOWN");
|
||||
break;
|
||||
}
|
||||
|
||||
mutex_unlock(&scst_mutex);
|
||||
|
||||
out:
|
||||
TRACE_EXIT_RES(res);
|
||||
return res;
|
||||
}
|
||||
static struct scst_proc_data scst_groups_addr_method_proc_data = {
|
||||
SCST_DEF_RW_SEQ_OP(NULL)
|
||||
.show = scst_groups_addr_method_show,
|
||||
};
|
||||
static int scst_groups_devices_show(struct seq_file *seq, void *v)
|
||||
{
|
||||
int res = 0;
|
||||
|
||||
+126
-4
@@ -106,6 +106,12 @@ static ssize_t scst_luns_mgmt_show(struct kobject *kobj,
|
||||
static ssize_t scst_luns_mgmt_store(struct kobject *kobj,
|
||||
struct kobj_attribute *attr,
|
||||
const char *buf, size_t count);
|
||||
static ssize_t scst_tgt_addr_method_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr,
|
||||
char *buf);
|
||||
static ssize_t scst_tgt_addr_method_store(struct kobject *kobj,
|
||||
struct kobj_attribute *attr,
|
||||
const char *buf, size_t count);
|
||||
static ssize_t scst_ini_group_mgmt_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr,
|
||||
char *buf);
|
||||
@@ -127,6 +133,12 @@ static ssize_t scst_acg_ini_mgmt_show(struct kobject *kobj,
|
||||
static ssize_t scst_acg_ini_mgmt_store(struct kobject *kobj,
|
||||
struct kobj_attribute *attr,
|
||||
const char *buf, size_t count);
|
||||
static ssize_t scst_acg_addr_method_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr,
|
||||
char *buf);
|
||||
static ssize_t scst_acg_addr_method_store(struct kobject *kobj,
|
||||
struct kobj_attribute *attr,
|
||||
const char *buf, size_t count);
|
||||
static ssize_t scst_acn_file_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr, char *buf);
|
||||
|
||||
@@ -513,10 +525,18 @@ static struct kobj_attribute scst_ini_group_mgmt =
|
||||
__ATTR(mgmt, S_IRUGO | S_IWUSR, scst_ini_group_mgmt_show,
|
||||
scst_ini_group_mgmt_store);
|
||||
|
||||
static struct kobj_attribute scst_tgt_addr_method =
|
||||
__ATTR(addr_method, S_IRUGO | S_IWUSR, scst_tgt_addr_method_show,
|
||||
scst_tgt_addr_method_store);
|
||||
|
||||
static struct kobj_attribute scst_rel_tgt_id =
|
||||
__ATTR(rel_tgt_id, S_IRUGO | S_IWUSR, scst_rel_tgt_id_show,
|
||||
scst_rel_tgt_id_store);
|
||||
|
||||
static struct kobj_attribute scst_acg_addr_method =
|
||||
__ATTR(addr_method, S_IRUGO | S_IWUSR, scst_acg_addr_method_show,
|
||||
scst_acg_addr_method_store);
|
||||
|
||||
static ssize_t scst_tgt_enable_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr, char *buf)
|
||||
{
|
||||
@@ -672,6 +692,14 @@ int scst_create_tgt_sysfs(struct scst_tgt *tgt)
|
||||
goto out;
|
||||
}
|
||||
|
||||
retval = sysfs_create_file(&tgt->tgt_kobj,
|
||||
&scst_tgt_addr_method.attr);
|
||||
if (retval != 0) {
|
||||
PRINT_ERROR("Can't add attribute %s for tgt %s",
|
||||
scst_tgt_addr_method.attr.name, tgt->tgt_name);
|
||||
goto out;
|
||||
}
|
||||
|
||||
pattr = tgt->tgtt->tgt_attrs;
|
||||
if (pattr != NULL) {
|
||||
while (*pattr != NULL) {
|
||||
@@ -1652,12 +1680,76 @@ static ssize_t scst_luns_mgmt_store(struct kobject *kobj,
|
||||
|
||||
tgt = container_of(kobj->parent, struct scst_tgt, tgt_kobj);
|
||||
acg = tgt->default_acg;
|
||||
|
||||
res = __scst_luns_mgmt_store(acg, kobj, buf, count);
|
||||
|
||||
TRACE_EXIT_RES(res);
|
||||
return res;
|
||||
}
|
||||
|
||||
static ssize_t __scst_acg_addr_method_show(struct scst_acg *acg, char *buf)
|
||||
{
|
||||
int res;
|
||||
|
||||
switch (acg->addr_method) {
|
||||
case SCST_LUN_ADDR_METHOD_FLAT:
|
||||
res = sprintf(buf, "FLAT\n%s\n", SCST_SYSFS_KEY_MARK);
|
||||
break;
|
||||
case SCST_LUN_ADDR_METHOD_PERIPHERAL:
|
||||
res = sprintf(buf, "PERIPHERAL\n");
|
||||
break;
|
||||
default:
|
||||
res = sprintf(buf, "UNKNOWN\n");
|
||||
break;
|
||||
}
|
||||
|
||||
return res;
|
||||
}
|
||||
|
||||
static ssize_t __scst_acg_addr_method_store(struct scst_acg *acg,
|
||||
const char *buf, size_t count)
|
||||
{
|
||||
int res = count;
|
||||
|
||||
if (strncasecmp(buf, "FLAT", min_t(int, 4, count)) == 0)
|
||||
acg->addr_method = SCST_LUN_ADDR_METHOD_FLAT;
|
||||
else if (strncasecmp(buf, "PERIPHERAL", min_t(int, 10, count)) == 0)
|
||||
acg->addr_method = SCST_LUN_ADDR_METHOD_PERIPHERAL;
|
||||
else {
|
||||
PRINT_ERROR("Unknown address method %s", buf);
|
||||
res = -EINVAL;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
static ssize_t scst_tgt_addr_method_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr, char *buf)
|
||||
{
|
||||
struct scst_acg *acg;
|
||||
struct scst_tgt *tgt;
|
||||
|
||||
tgt = container_of(kobj, struct scst_tgt, tgt_kobj);
|
||||
acg = tgt->default_acg;
|
||||
|
||||
return __scst_acg_addr_method_show(acg, buf);
|
||||
}
|
||||
|
||||
static ssize_t scst_tgt_addr_method_store(struct kobject *kobj,
|
||||
struct kobj_attribute *attr, const char *buf, size_t count)
|
||||
{
|
||||
int res;
|
||||
struct scst_acg *acg;
|
||||
struct scst_tgt *tgt;
|
||||
|
||||
tgt = container_of(kobj, struct scst_tgt, tgt_kobj);
|
||||
acg = tgt->default_acg;
|
||||
|
||||
res = __scst_acg_addr_method_store(acg, buf, count);
|
||||
|
||||
TRACE_EXIT_RES(res);
|
||||
return res;
|
||||
}
|
||||
|
||||
static int scst_create_acg_sysfs(struct scst_tgt *tgt,
|
||||
struct scst_acg *acg)
|
||||
{
|
||||
@@ -1705,6 +1797,14 @@ static int scst_create_acg_sysfs(struct scst_tgt *tgt,
|
||||
scst_acg_ini_mgmt.attr.name, tgt->tgt_name);
|
||||
goto out;
|
||||
}
|
||||
|
||||
retval = sysfs_create_file(&acg->acg_kobj, &scst_acg_addr_method.attr);
|
||||
if (retval != 0) {
|
||||
PRINT_ERROR("Can't add tgt attr %s for tgt %s",
|
||||
scst_acg_addr_method.attr.name,
|
||||
tgt->tgt_name);
|
||||
goto out;
|
||||
}
|
||||
out:
|
||||
TRACE_EXIT_RES(retval);
|
||||
return retval;
|
||||
@@ -1732,13 +1832,35 @@ void scst_acg_sysfs_put(struct scst_acg *acg)
|
||||
return;
|
||||
}
|
||||
|
||||
static ssize_t scst_acg_addr_method_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr, char *buf)
|
||||
{
|
||||
struct scst_acg *acg;
|
||||
|
||||
acg = container_of(kobj, struct scst_acg, acg_kobj);
|
||||
|
||||
return __scst_acg_addr_method_show(acg, buf);
|
||||
}
|
||||
|
||||
static ssize_t scst_acg_addr_method_store(struct kobject *kobj,
|
||||
struct kobj_attribute *attr, const char *buf, size_t count)
|
||||
{
|
||||
int res;
|
||||
struct scst_acg *acg;
|
||||
|
||||
acg = container_of(kobj, struct scst_acg, acg_kobj);
|
||||
|
||||
res = __scst_acg_addr_method_store(acg, buf, count);
|
||||
|
||||
TRACE_EXIT_RES(res);
|
||||
return res;
|
||||
}
|
||||
|
||||
static ssize_t scst_ini_group_mgmt_show(struct kobject *kobj,
|
||||
struct kobj_attribute *attr, char *buf)
|
||||
{
|
||||
static char *help = "Usage: echo \"create GROUP_NAME\" "
|
||||
">mgmt\n"
|
||||
" echo \"del GROUP_NAME\" "
|
||||
">mgmt\n";
|
||||
static char *help = "Usage: echo \"create GROUP_NAME\" >mgmt\n"
|
||||
" echo \"del GROUP_NAME\" >mgmt\n";
|
||||
|
||||
return sprintf(buf, help);
|
||||
}
|
||||
|
||||
@@ -1481,8 +1481,15 @@ static int scst_report_luns_local(struct scst_cmd *cmd)
|
||||
buffer_size);
|
||||
goto out_put_hw_err;
|
||||
}
|
||||
buffer[offs] = (tgt_dev->lun >> 8) & 0xff;
|
||||
buffer[offs+1] = tgt_dev->lun & 0xff;
|
||||
if ((cmd->sess->acg->addr_method == SCST_LUN_ADDR_METHOD_FLAT) &&
|
||||
(tgt_dev->lun != 0)) {
|
||||
buffer[offs] = (tgt_dev->lun >> 8) & 0x3f;
|
||||
buffer[offs] = buffer[offs] | 0x40;
|
||||
buffer[offs+1] = tgt_dev->lun & 0xff;
|
||||
} else {
|
||||
buffer[offs] = (tgt_dev->lun >> 8) & 0xff;
|
||||
buffer[offs+1] = tgt_dev->lun & 0xff;
|
||||
}
|
||||
offs += 8;
|
||||
}
|
||||
inc_dev_cnt:
|
||||
|
||||
Reference in New Issue
Block a user