|  | @@ -104,6 +104,12 @@ int scsiNetworkCommand()
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |  	DBGMSG_F("------ in scsiNetworkCommand with command 0x%02x (size %d)", command, size);
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | +	// Rather than duplicating code, this just diverts a 'fake' read request to make the gvpscsi.device happy on the Amiga
 | 
	
		
			
				|  |  | +	if ((scsiDev.cdb[0] == SCSI_NETWORK_WIFI_CMD) && (scsiDev.cdb[1] == SCSI_NETWORK_WIFI_CMD_ALTREAD)) {
 | 
	
		
			
				|  |  | +		// Redirect the command as a READ.
 | 
	
		
			
				|  |  | +		command = 0x08;
 | 
	
		
			
				|  |  | +	}
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |  	switch (command) {
 | 
	
		
			
				|  |  |  	case 0x08:
 | 
	
		
			
				|  |  |  		// read(6)
 | 
	
	
		
			
				|  | @@ -156,26 +162,62 @@ int scsiNetworkCommand()
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |  			DBGMSG_BUF(scsiDev.data, scsiDev.dataLen);
 | 
	
		
			
				|  |  |  		}
 | 
	
		
			
				|  |  | +		// Patches around the weirdness on the Amiga SCSI devices
 | 
	
		
			
				|  |  | +		if ((scsiDev.cdb[0] == SCSI_NETWORK_WIFI_CMD) && (scsiDev.cdb[1] == SCSI_NETWORK_WIFI_CMD_ALTREAD)) {
 | 
	
		
			
				|  |  | +			scsiDev.data[2] = scsiDev.cdb[2];    // for me really
 | 
	
		
			
				|  |  | +			int extra = 0;
 | 
	
		
			
				|  |  | +			if (scsiDev.cdb[2] == AMIGASCSI_PATCH_24BYTE_BLOCKSIZE) {
 | 
	
		
			
				|  |  | +				if (scsiDev.dataLen<90) scsiDev.dataLen = 90;
 | 
	
		
			
				|  |  | +				int missing = (scsiDev.dataLen-90) % 24;
 | 
	
		
			
				|  |  | +				if (missing) {
 | 
	
		
			
				|  |  | +					scsiDev.dataLen += 24 - missing;
 | 
	
		
			
				|  |  | +					if (scsiDev.dataLen>NETWORK_PACKET_MAX_SIZE) {
 | 
	
		
			
				|  |  | +						extra = scsiDev.dataLen - NETWORK_PACKET_MAX_SIZE;
 | 
	
		
			
				|  |  | +						scsiDev.dataLen = NETWORK_PACKET_MAX_SIZE;
 | 
	
		
			
				|  |  | +					}
 | 
	
		
			
				|  |  | +				}
 | 
	
		
			
				|  |  | +				scsiEnterPhase(DATA_IN);
 | 
	
		
			
				|  |  | +				scsiWrite(scsiDev.data, scsiDev.dataLen);
 | 
	
		
			
				|  |  | +				while (!scsiIsWriteFinished(NULL))
 | 
	
		
			
				|  |  | +				{
 | 
	
		
			
				|  |  | +					platform_poll();
 | 
	
		
			
				|  |  | +				}
 | 
	
		
			
				|  |  | +				scsiFinishWrite();
 | 
	
		
			
				|  |  | +			} else {
 | 
	
		
			
				|  |  | +				extra = scsiDev.dataLen;     // F9 means send in ONE transaction
 | 
	
		
			
				|  |  | +				if (extra) scsiEnterPhase(DATA_IN);
 | 
	
		
			
				|  |  | +			}
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | -		// DaynaPort driver needs a delay between reading the initial packet size and the data so manually do two transfers
 | 
	
		
			
				|  |  | -		scsiEnterPhase(DATA_IN);
 | 
	
		
			
				|  |  | -		scsiWrite(scsiDev.data, 6);
 | 
	
		
			
				|  |  | -		while (!scsiIsWriteFinished(NULL))
 | 
	
		
			
				|  |  | -		{
 | 
	
		
			
				|  |  | -			platform_poll();
 | 
	
		
			
				|  |  | -		}
 | 
	
		
			
				|  |  | -		scsiFinishWrite();
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -		if (scsiDev.dataLen > 6)
 | 
	
		
			
				|  |  | -		{
 | 
	
		
			
				|  |  | -			s2s_delay_us(80);
 | 
	
		
			
				|  |  | -
 | 
	
		
			
				|  |  | -			scsiWrite(scsiDev.data + 6, scsiDev.dataLen - 6);
 | 
	
		
			
				|  |  | +			if (extra) {
 | 
	
		
			
				|  |  | +				// Just write the extra data to make the padding work for such a large packet
 | 
	
		
			
				|  |  | +				scsiWrite(scsiDev.data, extra);
 | 
	
		
			
				|  |  | +				while (!scsiIsWriteFinished(NULL))
 | 
	
		
			
				|  |  | +				{
 | 
	
		
			
				|  |  | +					platform_poll();
 | 
	
		
			
				|  |  | +				}
 | 
	
		
			
				|  |  | +				scsiFinishWrite();
 | 
	
		
			
				|  |  | +			}
 | 
	
		
			
				|  |  | +		} else {
 | 
	
		
			
				|  |  | +			// DaynaPort driver needs a delay between reading the initial packet size and the data so manually do two transfers
 | 
	
		
			
				|  |  | +			scsiEnterPhase(DATA_IN);
 | 
	
		
			
				|  |  | +			scsiWrite(scsiDev.data, 6);
 | 
	
		
			
				|  |  |  			while (!scsiIsWriteFinished(NULL))
 | 
	
		
			
				|  |  |  			{
 | 
	
		
			
				|  |  |  				platform_poll();
 | 
	
		
			
				|  |  |  			}
 | 
	
		
			
				|  |  |  			scsiFinishWrite();
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +			if (scsiDev.dataLen > 6)
 | 
	
		
			
				|  |  | +			{
 | 
	
		
			
				|  |  | +				s2s_delay_us(80);
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +				scsiWrite(scsiDev.data + 6, scsiDev.dataLen - 6);
 | 
	
		
			
				|  |  | +				while (!scsiIsWriteFinished(NULL))
 | 
	
		
			
				|  |  | +				{
 | 
	
		
			
				|  |  | +					platform_poll();
 | 
	
		
			
				|  |  | +				}
 | 
	
		
			
				|  |  | +				scsiFinishWrite();
 | 
	
		
			
				|  |  | +			}
 | 
	
		
			
				|  |  |  		}
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |  		scsiDev.status = GOOD;
 | 
	
	
		
			
				|  | @@ -311,6 +353,17 @@ int scsiNetworkCommand()
 | 
	
		
			
				|  |  |  			// return wi-fi scan results
 | 
	
		
			
				|  |  |  			if (!platform_network_wifi_scan_finished())
 | 
	
		
			
				|  |  |  			{
 | 
	
		
			
				|  |  | +				scsiDev.target->sense.code = ILLEGAL_REQUEST;
 | 
	
		
			
				|  |  | +				scsiDev.target->sense.asc = INVALID_FIELD_IN_CDB;
 | 
	
		
			
				|  |  | +				scsiDev.status = CHECK_CONDITION;
 | 
	
		
			
				|  |  | +				scsiDev.phase = STATUS;
 | 
	
		
			
				|  |  | +				break;
 | 
	
		
			
				|  |  | +			}
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +			if (unlikely(size < 2))
 | 
	
		
			
				|  |  | +			{
 | 
	
		
			
				|  |  | +				scsiDev.target->sense.code = ILLEGAL_REQUEST;
 | 
	
		
			
				|  |  | +				scsiDev.target->sense.asc = INVALID_FIELD_IN_CDB;
 | 
	
		
			
				|  |  |  				scsiDev.status = CHECK_CONDITION;
 | 
	
		
			
				|  |  |  				scsiDev.phase = STATUS;
 | 
	
		
			
				|  |  |  				break;
 | 
	
	
		
			
				|  | @@ -325,17 +378,23 @@ int scsiNetworkCommand()
 | 
	
		
			
				|  |  |  			}
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  |  			if (nets) {
 | 
	
		
			
				|  |  | -				int size = sizeof(struct wifi_network_entry) * nets;
 | 
	
		
			
				|  |  | -				if (size + 2 > sizeof(scsiDev.data))
 | 
	
		
			
				|  |  | +				unsigned int netsize = sizeof(struct wifi_network_entry) * nets;
 | 
	
		
			
				|  |  | +				if (netsize + 2 > sizeof(scsiDev.data))
 | 
	
		
			
				|  |  |  				{
 | 
	
		
			
				|  |  |  					log_f("WARNING: wifi_network_list is bigger than scsiDev.data, truncating");
 | 
	
		
			
				|  |  | -					size = sizeof(scsiDev.data) - 2;
 | 
	
		
			
				|  |  | -					size -= (size % (sizeof(struct wifi_network_entry)));
 | 
	
		
			
				|  |  | +					netsize = sizeof(scsiDev.data) - 2;
 | 
	
		
			
				|  |  | +					netsize -= (netsize % (sizeof(struct wifi_network_entry)));
 | 
	
		
			
				|  |  |  				}
 | 
	
		
			
				|  |  | -				scsiDev.data[0] = (size >> 8) & 0xff;
 | 
	
		
			
				|  |  | -				scsiDev.data[1] = size & 0xff;
 | 
	
		
			
				|  |  | -				memcpy(scsiDev.data + 2, wifi_network_list, size);
 | 
	
		
			
				|  |  | -				scsiDev.dataLen = size + 2;
 | 
	
		
			
				|  |  | +				if (netsize + 2 > size)
 | 
	
		
			
				|  |  | +				{
 | 
	
		
			
				|  |  | +					log_f("WARNING: wifi_network_list is bigger than requested dataLen, truncating");
 | 
	
		
			
				|  |  | +					netsize = size - 2;
 | 
	
		
			
				|  |  | +					netsize -= (netsize % (sizeof(struct wifi_network_entry)));
 | 
	
		
			
				|  |  | +				}
 | 
	
		
			
				|  |  | +				scsiDev.data[0] = (netsize >> 8) & 0xff;
 | 
	
		
			
				|  |  | +				scsiDev.data[1] = netsize & 0xff;
 | 
	
		
			
				|  |  | +				memcpy(scsiDev.data + 2, wifi_network_list, netsize);
 | 
	
		
			
				|  |  | +				scsiDev.dataLen = netsize + 2;
 | 
	
		
			
				|  |  |  			}
 | 
	
		
			
				|  |  |  			else
 | 
	
		
			
				|  |  |  			{
 | 
	
	
		
			
				|  | @@ -396,6 +455,14 @@ int scsiNetworkCommand()
 | 
	
		
			
				|  |  |  			scsiDev.phase = STATUS;
 | 
	
		
			
				|  |  |  			break;
 | 
	
		
			
				|  |  |  		}
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +		case SCSI_NETWORK_WIFI_CMD_GETMACADDRESS:
 | 
	
		
			
				|  |  | +			// Update for the gvpscsi.device on the Amiga as it doesn't like 0x09 command being called! - NOTE this only sends 6 bytes back
 | 
	
		
			
				|  |  | +			memcpy(scsiDev.data, scsiDev.boardCfg.wifiMACAddress, sizeof(scsiDev.boardCfg.wifiMACAddress));
 | 
	
		
			
				|  |  | +			memset(scsiDev.data + sizeof(scsiDev.boardCfg.wifiMACAddress), 0, sizeof(scsiDev.data) - sizeof(scsiDev.boardCfg.wifiMACAddress));
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  | +			scsiDev.dataLen = 6;
 | 
	
		
			
				|  |  | +			scsiDev.phase = DATA_IN;
 | 
	
		
			
				|  |  |  		}
 | 
	
		
			
				|  |  |  		break;
 | 
	
		
			
				|  |  |  
 | 
	
	
		
			
				|  | @@ -403,6 +470,7 @@ int scsiNetworkCommand()
 | 
	
		
			
				|  |  |  		handled = 0;
 | 
	
		
			
				|  |  |  	}
 | 
	
		
			
				|  |  |  
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |  	return handled;
 | 
	
		
			
				|  |  |  }
 | 
	
		
			
				|  |  |  
 | 
	
	
		
			
				|  | @@ -435,7 +503,7 @@ int scsiNetworkEnqueue(const uint8_t *buf, size_t len)
 | 
	
		
			
				|  |  |  	{
 | 
	
		
			
				|  |  |  		DBGMSG_F("%s: dropping packets in ring, write index caught up to read index", __func__);
 | 
	
		
			
				|  |  |  	}
 | 
	
		
			
				|  |  | -	
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |  	return 1;
 | 
	
		
			
				|  |  |  }
 | 
	
		
			
				|  |  |  
 | 
	
	
		
			
				|  | @@ -454,7 +522,7 @@ int scsiNetworkPurge(void)
 | 
	
		
			
				|  |  |  			scsiNetworkOutboundQueue.readIndex = 0;
 | 
	
		
			
				|  |  |  		else
 | 
	
		
			
				|  |  |  			scsiNetworkOutboundQueue.readIndex++;
 | 
	
		
			
				|  |  | -		
 | 
	
		
			
				|  |  | +
 | 
	
		
			
				|  |  |  		sent++;
 | 
	
		
			
				|  |  |  	}
 | 
	
		
			
				|  |  |  
 |