diff options
author | Boaz Harrosh <bharrosh@panasas.com> | 2010-10-19 08:20:31 -0400 |
---|---|---|
committer | James Bottomley <James.Bottomley@suse.de> | 2010-10-26 11:42:30 -0400 |
commit | ec6a0a41b57feb54b3830918a8fb07147c2ee778 (patch) | |
tree | a0c3620b4ca600faee6270985c84ef054cbb6a58 /drivers/scsi/osd | |
parent | 391cbf46f25ccbeb1a0ffd76c76765ffc9a6fb22 (diff) |
[SCSI] libosd: Fix bug in attr_page handling
The _osd_req_finalize_attr_page was off by a mile, when trying to
append the enc_get_attr segment instead of the proper set_attr segment.
Also properly support when we don't have any attribute to set while
getting a full page. And when clearing an attribute by setting it's
size to zero.
Reported-by: John Chandy <john.chandy@uconn.edu>
Signed-off-by: Boaz Harrosh <bharrosh@panasas.com>
Signed-off-by: James Bottomley <James.Bottomley@suse.de>
Diffstat (limited to 'drivers/scsi/osd')
-rw-r--r-- | drivers/scsi/osd/osd_initiator.c | 16 |
1 files changed, 10 insertions, 6 deletions
diff --git a/drivers/scsi/osd/osd_initiator.c b/drivers/scsi/osd/osd_initiator.c index e88bbdde49c5..771ab121acc7 100644 --- a/drivers/scsi/osd/osd_initiator.c +++ b/drivers/scsi/osd/osd_initiator.c | |||
@@ -1218,17 +1218,18 @@ int osd_req_add_get_attr_page(struct osd_request *or, | |||
1218 | or->get_attr.buff = attar_page; | 1218 | or->get_attr.buff = attar_page; |
1219 | or->get_attr.total_bytes = max_page_len; | 1219 | or->get_attr.total_bytes = max_page_len; |
1220 | 1220 | ||
1221 | or->set_attr.buff = set_one_attr->val_ptr; | ||
1222 | or->set_attr.total_bytes = set_one_attr->len; | ||
1223 | |||
1224 | cdbh->attrs_page.get_attr_page = cpu_to_be32(page_id); | 1221 | cdbh->attrs_page.get_attr_page = cpu_to_be32(page_id); |
1225 | cdbh->attrs_page.get_attr_alloc_length = cpu_to_be32(max_page_len); | 1222 | cdbh->attrs_page.get_attr_alloc_length = cpu_to_be32(max_page_len); |
1226 | /* ocdb->attrs_page.get_attr_offset; */ | 1223 | |
1224 | if (!set_one_attr || !set_one_attr->attr_page) | ||
1225 | return 0; /* The set is optional */ | ||
1226 | |||
1227 | or->set_attr.buff = set_one_attr->val_ptr; | ||
1228 | or->set_attr.total_bytes = set_one_attr->len; | ||
1227 | 1229 | ||
1228 | cdbh->attrs_page.set_attr_page = cpu_to_be32(set_one_attr->attr_page); | 1230 | cdbh->attrs_page.set_attr_page = cpu_to_be32(set_one_attr->attr_page); |
1229 | cdbh->attrs_page.set_attr_id = cpu_to_be32(set_one_attr->attr_id); | 1231 | cdbh->attrs_page.set_attr_id = cpu_to_be32(set_one_attr->attr_id); |
1230 | cdbh->attrs_page.set_attr_length = cpu_to_be32(set_one_attr->len); | 1232 | cdbh->attrs_page.set_attr_length = cpu_to_be32(set_one_attr->len); |
1231 | /* ocdb->attrs_page.set_attr_offset; */ | ||
1232 | return 0; | 1233 | return 0; |
1233 | } | 1234 | } |
1234 | EXPORT_SYMBOL(osd_req_add_get_attr_page); | 1235 | EXPORT_SYMBOL(osd_req_add_get_attr_page); |
@@ -1248,11 +1249,14 @@ static int _osd_req_finalize_attr_page(struct osd_request *or) | |||
1248 | if (ret) | 1249 | if (ret) |
1249 | return ret; | 1250 | return ret; |
1250 | 1251 | ||
1252 | if (or->set_attr.total_bytes == 0) | ||
1253 | return 0; | ||
1254 | |||
1251 | /* set one value */ | 1255 | /* set one value */ |
1252 | cdbh->attrs_page.set_attr_offset = | 1256 | cdbh->attrs_page.set_attr_offset = |
1253 | osd_req_encode_offset(or, or->out.total_bytes, &out_padding); | 1257 | osd_req_encode_offset(or, or->out.total_bytes, &out_padding); |
1254 | 1258 | ||
1255 | ret = _req_append_segment(or, out_padding, &or->enc_get_attr, NULL, | 1259 | ret = _req_append_segment(or, out_padding, &or->set_attr, NULL, |
1256 | &or->out); | 1260 | &or->out); |
1257 | return ret; | 1261 | return ret; |
1258 | } | 1262 | } |