929
static int check_registration_key_exists(struct scsi_lu *lu, uint64_t key)
931
struct registration *reg;
933
list_for_each_entry(reg, &lu->registration_list,
934
registration_siblings) {
929
942
static void __unregister(struct scsi_lu *lu, struct registration *reg)
931
944
list_del(®->registration_siblings);
1192
1205
registration_siblings) {
1193
1206
/* we don't send myself */
1194
1207
if (sibling != reg)
1195
ua_sense_add_other_it_nexus(sibling->nexus_id,
1197
ASC_RESERVATIONS_PREEMPTED);
1208
ua_sense_add_it_nexus(sibling->nexus_id,
1209
cmd->dev, ASC_RESERVATIONS_PREEMPTED);
1198
1210
list_del(&sibling->registration_siblings);
1211
1223
uint16_t asc = ASC_INVALID_FIELD_IN_CDB;
1212
1224
uint8_t key = ILLEGAL_REQUEST;
1213
1225
int ret, abort;
1226
int res_released = 0, remove_all_reg = 0;
1214
1227
uint64_t res_key, sa_res_key;
1215
1228
uint8_t pr_scope, pr_type;
1217
struct registration *reg, *sibling, *n;
1230
struct registration *holder, *reg, *sibling, *n;
1219
1232
ret = check_pr_out_basic_parameter(cmd);
1237
1250
if (reg->key != res_key)
1238
1251
return SAM_STAT_RESERVATION_CONFLICT;
1240
remove_registration:
1241
if (!cmd->dev->pr_holder) {
1242
list_for_each_entry_safe(sibling, n, &cmd->dev->registration_list,
1243
registration_siblings) {
1245
if (sibling->key == sa_res_key) {
1246
__unregister(cmd->dev, sibling);
1254
ret = check_registration_key_exists(cmd->dev, sa_res_key);
1256
return SAM_STAT_RESERVATION_CONFLICT;
1259
holder = cmd->dev->pr_holder;
1262
if (holder->pr_type == PR_TYPE_WRITE_EXCLUSIVE_ALLREG ||
1263
holder->pr_type == PR_TYPE_EXCLUSIVE_ACCESS_ALLREG) {
1266
if (pr_type != holder->pr_type ||
1267
pr_scope != holder->pr_scope)
1269
reg->pr_type = pr_type;
1270
reg->pr_scope = pr_scope;
1271
cmd->dev->pr_holder = reg;
1275
if (holder->key == sa_res_key) {
1276
if ((pr_type != holder->pr_type) ||
1277
(pr_scope != holder->pr_scope))
1279
reg->pr_type = pr_type;
1280
reg->pr_scope = pr_scope;
1281
cmd->dev->pr_holder = reg;
1251
return SAM_STAT_GOOD;
1254
if (cmd->dev->pr_holder->pr_type == PR_TYPE_WRITE_EXCLUSIVE_ALLREG ||
1255
cmd->dev->pr_holder->pr_type == PR_TYPE_EXCLUSIVE_ACCESS_ALLREG) {
1258
goto remove_registration;
1260
list_for_each_entry_safe(sibling, n, &cmd->dev->registration_list,
1261
registration_siblings) {
1289
list_for_each_entry_safe(sibling, n, &cmd->dev->registration_list,
1290
registration_siblings) {
1294
if (sibling->key == sa_res_key || remove_all_reg) {
1295
ua_sense_add_it_nexus(sibling->nexus_id,
1296
cmd->dev, ASC_RESERVATIONS_PREEMPTED);
1266
1297
__unregister(cmd->dev, sibling);
1300
ua_sense_add_it_nexus(sibling->nexus_id,
1301
cmd->dev, ASC_RESERVATIONS_RELEASED);
1269
cmd->dev->pr_holder = reg;
1270
reg->pr_type = pr_type;
1271
reg->pr_scope = pr_scope;
1273
return SAM_STAT_GOOD;
1276
if (cmd->dev->pr_holder->key == sa_res_key) {
1277
cmd->dev->pr_holder = reg;
1278
reg->pr_type = pr_type;
1279
reg->pr_scope = pr_scope;
1281
goto remove_registration;
1285
goto remove_registration;
1305
cmd->dev->prgeneration++;
1290
1306
return SAM_STAT_GOOD;
1292
1308
scsi_set_in_resid_by_actual(cmd, 0);
1578
1594
Opt_scsi_id, Opt_scsi_sn,
1579
1595
Opt_vendor_id, Opt_product_id,
1580
1596
Opt_product_rev, Opt_sense_format,
1581
Opt_removable, Opt_online,
1597
Opt_removable, Opt_readonly, Opt_online,
1592
1609
{Opt_product_rev, "product_rev=%s"},
1593
1610
{Opt_sense_format, "sense_format=%s"},
1594
1611
{Opt_removable, "removable=%s"},
1612
{Opt_readonly, "readonly=%s"},
1595
1613
{Opt_online, "online=%s"},
1596
1614
{Opt_mode_page, "mode_page=%s"},
1597
1615
{Opt_path, "path=%s"},
1616
{Opt_bsoflags, "bsoflags=%s"},
1598
1617
{Opt_err, NULL},
1661
1681
match_strncpy(buf, &args[0], sizeof(buf));
1662
1682
attrs->removable = atoi(buf);
1685
match_strncpy(buf, &args[0], sizeof(buf));
1686
attrs->readonly = atoi(buf);
1664
1688
case Opt_online:
1665
1689
match_strncpy(buf, &args[0], sizeof(buf));