Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 95e852e1 authored by Salyzyn, Mark's avatar Salyzyn, Mark Committed by James Bottomley
Browse files

[SCSI] aacraid: add parameter to control FUA and SYNCHRONIZE_CACHE policy



aacraid.cache parameter, Disable Queue Flush commands:
        bit 0 - Disable FUA in WRITE SCSI commands
        bit 1 - Disable SYNCHRONIZE_CACHE SCSI command
        bit 2 - Disable only if Battery not protecting adapter supplied Cache

e.g.: aacraid.cache=7 will disable the FUA and SYNCHRONIZE_CACHE
commands if the adapter has reported that it's cache is battery backed
up.

This parameter permits experimentation with tradeoffs between
performance and caching policy.

Signed-off-by: default avatarMark Salyzyn <aacraid@adaptec.com>
Signed-off-by: default avatarJames Bottomley <James.Bottomley@HansenPartnership.com>
parent 9b161a4d
Loading
Loading
Loading
Loading
+24 −12
Original line number Diff line number Diff line
@@ -144,6 +144,7 @@ static char *aac_get_status_string(u32 status);
 */	
 
static int nondasd = -1;
static int aac_cache = 0;
static int dacmode = -1;

int aac_commit = -1;
@@ -152,6 +153,8 @@ int aif_timeout = 120;

module_param(nondasd, int, S_IRUGO|S_IWUSR);
MODULE_PARM_DESC(nondasd, "Control scanning of hba for nondasd devices. 0=off, 1=on");
module_param_named(cache, aac_cache, int, S_IRUGO|S_IWUSR);
MODULE_PARM_DESC(cache, "Disable Queue Flush commands:\n\tbit 0 - Disable FUA in WRITE SCSI commands\n\tbit 1 - Disable SYNCHRONIZE_CACHE SCSI command\n\tbit 2 - Disable only if Battery not protecting Cache");
module_param(dacmode, int, S_IRUGO|S_IWUSR);
MODULE_PARM_DESC(dacmode, "Control whether dma addressing is using 64 bit DAC. 0=off, 1=on");
module_param_named(commit, aac_commit, int, S_IRUGO|S_IWUSR);
@@ -1013,7 +1016,8 @@ static int aac_write_raw_io(struct fib * fib, struct scsi_cmnd * cmd, u64 lba, u
	writecmd->block[1] = cpu_to_le32((u32)((lba&0xffffffff00000000LL)>>32));
	writecmd->count = cpu_to_le32(count<<9);
	writecmd->cid = cpu_to_le16(scmd_id(cmd));
	writecmd->flags = fua ?
	writecmd->flags = (fua && ((aac_cache & 5) != 1) &&
	  (((aac_cache & 5) != 5) || !fib->dev->cache_protected)) ?
		cpu_to_le16(IO_TYPE_WRITE|IO_SUREWRITE) :
		cpu_to_le16(IO_TYPE_WRITE);
	writecmd->bpTotal = 0;
@@ -1325,11 +1329,11 @@ int aac_get_adapter_info(struct aac_dev* dev)
		}
	}

	dev->cache_protected = 0;
	dev->nondasd_support = 0;
	dev->raid_scsi_mode = 0;
	if(dev->adapter_info.options & AAC_OPT_NONDASD){
	if(dev->adapter_info.options & AAC_OPT_NONDASD)
		dev->nondasd_support = 1;
	}

	/*
	 * If the firmware supports ROMB RAID/SCSI mode and we are currently
@@ -1351,9 +1355,8 @@ int aac_get_adapter_info(struct aac_dev* dev)
		printk(KERN_INFO "%s%d: ROMB RAID/SCSI mode enabled\n",
				dev->name, dev->id);
		
	if(nondasd != -1) {  
	if (nondasd != -1)
		dev->nondasd_support = (nondasd!=0);
	}
	if(dev->nondasd_support != 0) {
		printk(KERN_INFO "%s%d: Non-DASD support enabled.\n",dev->name, dev->id);
	}
@@ -2106,7 +2109,7 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
		mode_buf[2] = 0;	/* Device-specific param,
					   bit 8: 0/1 = write enabled/protected
					   bit 4: 0/1 = FUA enabled */
		if (dev->raw_io_interface)
		if (dev->raw_io_interface && ((aac_cache & 5) != 1))
			mode_buf[2] = 0x10;
		mode_buf[3] = 0;	/* Block descriptor length */
		if (((scsicmd->cmnd[2] & 0x3f) == 8) ||
@@ -2114,7 +2117,8 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
			mode_buf[0] = 6;
			mode_buf[4] = 8;
			mode_buf[5] = 1;
			mode_buf[6] = 0x04; /* WCE */
			mode_buf[6] = ((aac_cache & 6) == 2)
				? 0 : 0x04; /* WCE */
			mode_buf_length = 7;
			if (mode_buf_length > scsicmd->cmnd[4])
				mode_buf_length = scsicmd->cmnd[4];
@@ -2137,7 +2141,7 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
		mode_buf[3] = 0;	/* Device-specific param,
					   bit 8: 0/1 = write enabled/protected
					   bit 4: 0/1 = FUA enabled */
		if (dev->raw_io_interface)
		if (dev->raw_io_interface && ((aac_cache & 5) != 1))
			mode_buf[3] = 0x10;
		mode_buf[4] = 0;	/* reserved */
		mode_buf[5] = 0;	/* reserved */
@@ -2148,7 +2152,8 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
			mode_buf[1] = 9;
			mode_buf[8] = 8;
			mode_buf[9] = 1;
			mode_buf[10] = 0x04; /* WCE */
			mode_buf[10] = ((aac_cache & 6) == 2)
				? 0 : 0x04; /* WCE */
			mode_buf_length = 11;
			if (mode_buf_length > scsicmd->cmnd[8])
				mode_buf_length = scsicmd->cmnd[8];
@@ -2224,9 +2229,16 @@ int aac_scsi_cmd(struct scsi_cmnd * scsicmd)
			return aac_write(scsicmd);

		case SYNCHRONIZE_CACHE:
			if (((aac_cache & 6) == 6) && dev->cache_protected) {
				scsicmd->result = DID_OK << 16 |
					COMMAND_COMPLETE << 8 | SAM_STAT_GOOD;
				scsicmd->scsi_done(scsicmd);
				return 0;
			}
			/* Issue FIB to tell Firmware to flush it's cache */
			if ((aac_cache & 6) != 2)
				return aac_synchronize(scsicmd);
			
			/* FALLTHRU */
		default:
			/*
			 *	Unhandled commands
+2 −0
Original line number Diff line number Diff line
@@ -1016,6 +1016,7 @@ struct aac_dev
	 * lets break them out so we don't have to do an AND to check them
	 */
	u8			nondasd_support; 
	u8			cache_protected;
	u8			dac_support;
	u8			raid_scsi_mode;
	u8			comm_interface;
@@ -1770,6 +1771,7 @@ extern struct aac_common aac_config;
#define			AifEnConfigChange	3	/* Adapter configuration change */
#define			AifEnContainerChange	4	/* Container configuration change */
#define			AifEnDeviceFailure	5	/* SCSI device failed */
#define			AifEnBatteryEvent	14	/* Change in Battery State */
#define			AifEnAddContainer	15	/* A new array was created */
#define			AifEnDeleteContainer	16	/* A container was deleted */
#define			AifEnExpEvent		23	/* Firmware Event Log */
+4 −0
Original line number Diff line number Diff line
@@ -849,6 +849,10 @@ static void aac_handle_aif(struct aac_dev * dev, struct fib * fibptr)

	case AifCmdEventNotify:
		switch (le32_to_cpu(((__le32 *)aifcmd->data)[0])) {
		case AifEnBatteryEvent:
			dev->cache_protected =
				(((__le32 *)aifcmd->data)[1] == cpu_to_le32(3));
			break;
		/*
		 *	Add an Array.
		 */