mirror of
https://git.FreeBSD.org/src.git
synced 2024-12-24 11:29:10 +00:00
Implement software (mode page) and hardware (config) write protection.
This commit is contained in:
parent
a62c8c6a99
commit
5396f4d279
Notes:
svn2git
2020-12-20 02:59:44 +00:00
svn path=/head/; revision=272748
@ -293,7 +293,7 @@ static struct scsi_control_page control_page_changeable = {
|
||||
/*page_length*/sizeof(struct scsi_control_page) - 2,
|
||||
/*rlec*/SCP_DSENSE,
|
||||
/*queue_flags*/SCP_QUEUE_ALG_MASK,
|
||||
/*eca_and_aen*/0,
|
||||
/*eca_and_aen*/SCP_SWP,
|
||||
/*flags4*/0,
|
||||
/*aen_holdoff_period*/{0, 0},
|
||||
/*busy_timeout_period*/{0, 0},
|
||||
@ -4447,7 +4447,7 @@ ctl_alloc_lun(struct ctl_softc *ctl_softc, struct ctl_lun *ctl_lun,
|
||||
struct ctl_port *port;
|
||||
struct scsi_vpd_id_descriptor *desc;
|
||||
struct scsi_vpd_id_t10 *t10id;
|
||||
const char *eui, *naa, *scsiname, *vendor;
|
||||
const char *eui, *naa, *scsiname, *vendor, *value;
|
||||
int lun_number, i, lun_malloced;
|
||||
int devidlen, idlen1, idlen2 = 0, len;
|
||||
|
||||
@ -4609,6 +4609,10 @@ ctl_alloc_lun(struct ctl_softc *ctl_softc, struct ctl_lun *ctl_lun,
|
||||
if (be_lun->flags & CTL_LUN_FLAG_PRIMARY)
|
||||
lun->flags |= CTL_LUN_PRIMARY_SC;
|
||||
|
||||
value = ctl_get_opt(&be_lun->options, "readonly");
|
||||
if (value != NULL && strcmp(value, "on") == 0)
|
||||
lun->flags |= CTL_LUN_READONLY;
|
||||
|
||||
lun->ctl_softc = ctl_softc;
|
||||
TAILQ_INIT(&lun->ooa_queue);
|
||||
TAILQ_INIT(&lun->blocked_queue);
|
||||
@ -6219,6 +6223,14 @@ ctl_control_page_handler(struct ctl_scsiio *ctsio,
|
||||
saved_cp->queue_flags |= user_cp->queue_flags & SCP_QUEUE_ALG_MASK;
|
||||
set_ua = 1;
|
||||
}
|
||||
if ((current_cp->eca_and_aen & SCP_SWP) !=
|
||||
(user_cp->eca_and_aen & SCP_SWP)) {
|
||||
current_cp->eca_and_aen &= ~SCP_SWP;
|
||||
current_cp->eca_and_aen |= user_cp->eca_and_aen & SCP_SWP;
|
||||
saved_cp->eca_and_aen &= ~SCP_SWP;
|
||||
saved_cp->eca_and_aen |= user_cp->eca_and_aen & SCP_SWP;
|
||||
set_ua = 1;
|
||||
}
|
||||
if (set_ua != 0) {
|
||||
int i;
|
||||
/*
|
||||
@ -7045,8 +7057,13 @@ ctl_mode_sense(struct ctl_scsiio *ctsio)
|
||||
header = (struct scsi_mode_hdr_6 *)ctsio->kern_data_ptr;
|
||||
|
||||
header->datalen = ctl_min(total_len - 1, 254);
|
||||
if (control_dev == 0)
|
||||
if (control_dev == 0) {
|
||||
header->dev_specific = 0x10; /* DPOFUA */
|
||||
if ((lun->flags & CTL_LUN_READONLY) ||
|
||||
(lun->mode_pages.control_page[CTL_PAGE_CURRENT]
|
||||
.eca_and_aen & SCP_SWP) != 0)
|
||||
header->dev_specific |= 0x80; /* WP */
|
||||
}
|
||||
if (dbd)
|
||||
header->block_descr_len = 0;
|
||||
else
|
||||
@ -7063,8 +7080,13 @@ ctl_mode_sense(struct ctl_scsiio *ctsio)
|
||||
|
||||
datalen = ctl_min(total_len - 2, 65533);
|
||||
scsi_ulto2b(datalen, header->datalen);
|
||||
if (control_dev == 0)
|
||||
if (control_dev == 0) {
|
||||
header->dev_specific = 0x10; /* DPOFUA */
|
||||
if ((lun->flags & CTL_LUN_READONLY) ||
|
||||
(lun->mode_pages.control_page[CTL_PAGE_CURRENT]
|
||||
.eca_and_aen & SCP_SWP) != 0)
|
||||
header->dev_specific |= 0x80; /* WP */
|
||||
}
|
||||
if (dbd)
|
||||
scsi_ulto2b(0, header->block_descr_len);
|
||||
else
|
||||
@ -11313,6 +11335,24 @@ ctl_scsiio_lun_check(struct ctl_softc *ctl_softc, struct ctl_lun *lun,
|
||||
}
|
||||
#endif
|
||||
|
||||
if (entry->pattern & CTL_LUN_PAT_WRITE) {
|
||||
if (lun->flags & CTL_LUN_READONLY) {
|
||||
ctl_set_sense(ctsio, /*current_error*/ 1,
|
||||
/*sense_key*/ SSD_KEY_DATA_PROTECT,
|
||||
/*asc*/ 0x27, /*ascq*/ 0x01, SSD_ELEM_NONE);
|
||||
retval = 1;
|
||||
goto bailout;
|
||||
}
|
||||
if ((lun->mode_pages.control_page[CTL_PAGE_CURRENT]
|
||||
.eca_and_aen & SCP_SWP) != 0) {
|
||||
ctl_set_sense(ctsio, /*current_error*/ 1,
|
||||
/*sense_key*/ SSD_KEY_DATA_PROTECT,
|
||||
/*asc*/ 0x27, /*ascq*/ 0x02, SSD_ELEM_NONE);
|
||||
retval = 1;
|
||||
goto bailout;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Check for a reservation conflict. If this command isn't allowed
|
||||
* even on reserved LUNs, and if this initiator isn't the one who
|
||||
|
@ -198,7 +198,8 @@ typedef enum {
|
||||
CTL_LUN_OFFLINE = 0x080,
|
||||
CTL_LUN_PR_RESERVED = 0x100,
|
||||
CTL_LUN_PRIMARY_SC = 0x200,
|
||||
CTL_LUN_SENSE_DESC = 0x400
|
||||
CTL_LUN_SENSE_DESC = 0x400,
|
||||
CTL_LUN_READONLY = 0x800
|
||||
} ctl_lun_flags;
|
||||
|
||||
typedef enum {
|
||||
|
@ -34,7 +34,7 @@
|
||||
.\" $Id: //depot/users/kenm/FreeBSD-test2/usr.sbin/ctladm/ctladm.8#3 $
|
||||
.\" $FreeBSD$
|
||||
.\"
|
||||
.Dd September 13, 2014
|
||||
.Dd October 8, 2014
|
||||
.Dt CTLADM 8
|
||||
.Os
|
||||
.Sh NAME
|
||||
@ -961,6 +961,9 @@ This allows to offload copying between different iSCSI targets residing
|
||||
on the same host in trusted environments.
|
||||
.It Va readcache
|
||||
Set to "off", disables read caching for the LUN, if supported by the backend.
|
||||
.It Va readonly
|
||||
Set to "on", blocks all media write operations to the LUN, reporting it
|
||||
as write protected.
|
||||
.It Va reordering
|
||||
Set to "unrestricted", allows target to process commands with SIMPLE task
|
||||
attribute in arbitrary order. Any data integrity exposures related to
|
||||
|
Loading…
Reference in New Issue
Block a user