nscsi: make sun4 probe-scsi happy (nw)

This commit is contained in:
Patrick Mackinlay 2018-09-16 14:30:22 +08:00
parent 59254bc5de
commit 2cca5549a8
3 changed files with 30 additions and 6 deletions

View File

@ -563,11 +563,13 @@ void nscsi_full_device::scsi_data_out(int buf, int size)
c->param2 = size; c->param2 = size;
} }
void nscsi_full_device::sense(bool deferred, uint8_t key) void nscsi_full_device::sense(bool deferred, uint8_t key, uint8_t asc, uint8_t ascq)
{ {
memset(scsi_sense_buffer, 0, sizeof(scsi_sense_buffer)); memset(scsi_sense_buffer, 0, sizeof(scsi_sense_buffer));
scsi_sense_buffer[0] = deferred ? 0x71 : 0x70; scsi_sense_buffer[0] = deferred ? 0x71 : 0x70;
scsi_sense_buffer[2] = key; scsi_sense_buffer[2] = key;
scsi_sense_buffer[12] = asc;
scsi_sense_buffer[13] = ascq;
} }
void nscsi_full_device::scsi_unknown_command() void nscsi_full_device::scsi_unknown_command()
@ -586,7 +588,11 @@ void nscsi_full_device::scsi_command()
switch(scsi_cmdbuf[0]) { switch(scsi_cmdbuf[0]) {
case SC_REQUEST_SENSE: case SC_REQUEST_SENSE:
LOG("command REQUEST SENSE\n"); LOG("command REQUEST SENSE\n");
scsi_data_in(SBUF_SENSE, 8); /*
* Targets shall be capable of returning eighteen bytes of data in
* response to a REQUEST SENSE command.
*/
scsi_data_in(SBUF_SENSE, 18);
scsi_status_complete(SS_GOOD); scsi_status_complete(SS_GOOD);
break; break;
default: default:
@ -619,7 +625,9 @@ int nscsi_full_device::get_lun(int def)
void nscsi_full_device::bad_lun() void nscsi_full_device::bad_lun()
{ {
scsi_status_complete(SS_CHECK_CONDITION); scsi_status_complete(SS_CHECK_CONDITION);
sense(false, 2);
// key:illegal request, asc:logical unit not supported
sense(false, 5, 0x25);
} }
// Arbitration delay (2.4us) // Arbitration delay (2.4us)

View File

@ -285,7 +285,7 @@ protected:
void scsi_data_in(int buf, int size); void scsi_data_in(int buf, int size);
void scsi_data_out(int buf, int size); void scsi_data_out(int buf, int size);
void sense(bool deferred, uint8_t key); void sense(bool deferred, uint8_t key, uint8_t asc = 0, uint8_t ascq = 0);
int get_lun(int def = 0); int get_lun(int def = 0);
void bad_lun(); void bad_lun();
@ -354,7 +354,7 @@ protected:
// Fast negation period (30ns) // Fast negation period (30ns)
virtual attotime scsi_fast_negation_period(); virtual attotime scsi_fast_negation_period();
uint8_t scsi_cmdbuf[4096], scsi_sense_buffer[8]; uint8_t scsi_cmdbuf[4096], scsi_sense_buffer[18];
int scsi_cmdsize; int scsi_cmdsize;
uint8_t scsi_identify; uint8_t scsi_identify;

View File

@ -113,6 +113,22 @@ void nscsi_cdrom_device::scsi_command()
int lun = get_lun(scsi_cmdbuf[1] >> 5); int lun = get_lun(scsi_cmdbuf[1] >> 5);
LOG("command INQUIRY lun=%d EVPD=%d page=%d alloc=%02x link=%02x\n", LOG("command INQUIRY lun=%d EVPD=%d page=%d alloc=%02x link=%02x\n",
lun, scsi_cmdbuf[1] & 1, scsi_cmdbuf[2], scsi_cmdbuf[4], scsi_cmdbuf[5]); lun, scsi_cmdbuf[1] & 1, scsi_cmdbuf[2], scsi_cmdbuf[4], scsi_cmdbuf[5]);
/*
* 7.5.3 Selection of an invalid logical unit
*
* The logical unit may not be valid because:
* a) the target does not support the logical unit (e.g. some targets
* support only one peripheral device). In response to an INQUIRY
* command, the target shall return the INQUIRY data with the
* peripheral qualifier set to the value required in 8.2.5.1.
*
* If the logic from the specification above is applied, Sun SCSI probe
* code gets confused and reports multiple valid logical units are
* attached; proper behaviour is produced when check condition status
* is returned with sense data ILLEGAL REQUEST and LOGICAL UNIT NOT
* SUPPORTED.
*/
if(lun) { if(lun) {
bad_lun(); bad_lun();
return; return;
@ -224,7 +240,7 @@ void nscsi_cdrom_device::scsi_command()
int pmin = page == 0x3f ? 0x00 : page; int pmin = page == 0x3f ? 0x00 : page;
for(int page=pmax; page >= pmin; page--) { for(int page=pmax; page >= pmin; page--) {
switch(page) { switch(page) {
case 0x00: // Unit attention parameters page (weird) case 0x00: // Vendor specific (does not require page format)
scsi_cmdbuf[pos++] = 0x80; // PS, page id scsi_cmdbuf[pos++] = 0x80; // PS, page id
scsi_cmdbuf[pos++] = 0x02; // Page length scsi_cmdbuf[pos++] = 0x02; // Page length
scsi_cmdbuf[pos++] = 0x00; // Meh scsi_cmdbuf[pos++] = 0x00; // Meh