inline int cbw_scsi_read_capacity(mass_dev* dev, void *buffer, int size)
{
    int ret;
    cbw_packet cbw;
    int retryCount;
    
    XPRINTF("USBHDFSD: cbw_scsi_read_capacity\n");

    cbw.signature = CBW_TAG;
    cbw.lun = 0;
	cbw.tag = -TAG_READ_CAPACITY;
	cbw.dataTransferLength = size;	//READ_CAPACITY_REPLY_LENGTH
	cbw.flags = 0x80;			//inquiry data will flow In
	cbw.comLength = 12;

	//scsi command packet
	cbw.comData[0] = 0x25;		//read capacity operation code
	cbw.comData[1] = 0;			//lun/reserved/RelAdr
	cbw.comData[2] = 0;			//LBA 1
	cbw.comData[3] = 0;			//LBA 2
	cbw.comData[4] = 0;			//LBA 3
	cbw.comData[5] = 0;			//LBA 4
	cbw.comData[6] = 0;			//Reserved
	cbw.comData[7] = 0;			//Reserved
	cbw.comData[8] = 0;			//Reserved/PMI
	cbw.comData[9] = 0;			//reserved
	cbw.comData[10] = 0;		//reserved
	cbw.comData[11] = 0;		//reserved

	ret = 1;
	retryCount = 6;
	while (ret != 0 && retryCount > 0) {
		usb_bulk_command(dev, &cbw);

		ret = usb_bulk_transfer(dev->bulkEpI, buffer, size);
        if (ret != 0)
            printf("USBHDFSD: cbw_scsi_read_capacity error from usb_bulk_transfer %d\n", ret);

		//HACK HACK HACK !!!
		//according to usb doc we should allways
		//attempt to read the CSW packet. But in some cases
		//reading of CSW packet just freeze ps2....:-(
        if (ret == USB_RC_STALL) {
            XPRINTF("USBHDFSD: call reset recovery ...\n");
			usb_bulk_reset(dev, 1);
		} else {
			ret = usb_bulk_manage_status(dev, -TAG_READ_CAPACITY);
		}
		retryCount--;
	}
    return ret;
}
Exemple #2
0
static inline int cbw_scsi_write_sector(mass_dev* dev, unsigned int lba, const void* buffer, unsigned short int sectorCount)
{
	int rcode, result;
	static cbw_packet cbw={
		CBW_TAG, 		// cbw.signature
		-TAG_WRITE,		// cbw.tag
		0,			// cbw.dataTransferLength
		0,			// cbw.flags
		0,			// cbw.lun
		12,			// cbw.comLength

		/* scsi command packet */
		{
			0x2A,		//write operation code
			0,		//LUN/DPO/FUA/Reserved/Reldr
			0,		//lba 1 (MSB)
			0,		//lba 2
			0,		//lba 3
			0,		//lba 4 (LSB)
			0,		//Reserved
			0,		//Transfer length MSB
			0,		//Transfer length LSB
			0,		//reserved
			0,		//reserved
			0,		//reserved
		}
	};
	XPRINTF("USBHDFSD: cbw_scsi_write_sector - 0x%08x %p 0x%04x\n", lba, buffer, sectorCount);

	cbw.dataTransferLength = dev->sectorSize * sectorCount;

	//scsi command packet
	cbw.comData[2] = (lba & 0xFF000000) >> 24;	//lba 1 (MSB)
	cbw.comData[3] = (lba & 0xFF0000) >> 16;	//lba 2
	cbw.comData[4] = (lba & 0xFF00) >> 8;		//lba 3
	cbw.comData[5] = (lba & 0xFF);			//lba 4 (LSB)
	cbw.comData[7] = (sectorCount & 0xFF00) >> 8;	//Transfer length MSB
	cbw.comData[8] = (sectorCount & 0xFF);		//Transfer length LSB

	result = -EIO;
	if(usb_bulk_command(dev, &cbw) == USB_RC_OK){
		rcode = usb_bulk_transfer(dev, USB_BLK_EP_OUT, (void*)buffer, dev->sectorSize * sectorCount);
		result = usb_bulk_manage_status(dev, -TAG_WRITE);

		if(rcode != USB_RC_OK) result = -EIO;
	}

	return result;
}
Exemple #3
0
static inline int cbw_scsi_inquiry(mass_dev* dev, void *buffer, int size)
{
	int rcode, result, retries;
	static cbw_packet cbw={
		CBW_TAG, 		// cbw.signature
		-TAG_INQUIRY,		// cbw.tag
		0,			// cbw.dataTransferLength
		0x80,			// cbw.flags
		0,			// cbw.lun
		12,			// cbw.comLength

		/* scsi command packet */
		{
			0x12,		// inquiry operation code
			0,		// lun/reserved
			0,		// reserved
			0,		// reserved
			0,		// inquiry reply length
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
		}
	};

	XPRINTF("USBHDFSD: cbw_scsi_inquiry\n");

	cbw.dataTransferLength = size;	//INQUIRY_REPLY_LENGTH
	cbw.comData[4] = size;		//inquiry reply length

	for(retries = USB_XFER_MAX_RETRIES; retries > 0; retries--){
		if(usb_bulk_command(dev, &cbw) == USB_RC_OK){
			rcode = usb_bulk_transfer(dev, USB_BLK_EP_IN, buffer, size);
			result = usb_bulk_manage_status(dev, -TAG_INQUIRY);

			if(rcode == USB_RC_OK && result == 0) return 0;
		}
	}

	return -EIO;
}
Exemple #4
0
static inline int cbw_scsi_request_sense(mass_dev* dev, void *buffer, int size)
{
	int rcode, result, retries;
	static cbw_packet cbw={
		CBW_TAG, 		// cbw.signature
		-TAG_REQUEST_SENSE,	// cbw.tag
		0,			// cbw.dataTransferLength
		0x80,			// cbw.flags
		0,			// cbw.lun
		12,			// cbw.comLength

		/* scsi command packet */
		{
			0x03,		// request sense operation code
			0,		// lun/reserved
			0,		// reserved
			0,		// reserved
			0,		// allocation length
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
			0,		// reserved
		}
	};

	cbw.dataTransferLength = size;
	cbw.comData[4] = size;

	XPRINTF("USBHDFSD: cbw_scsi_request_sense\n");

	for(retries = USB_XFER_MAX_RETRIES; retries > 0; retries--){
		if(usb_bulk_command(dev, &cbw) == USB_RC_OK){
			rcode = usb_bulk_transfer(dev, USB_BLK_EP_IN, buffer, size);
			result = usb_bulk_manage_status(dev, -TAG_REQUEST_SENSE);

			if(rcode == USB_RC_OK && result == 0) return 0;
		}
	}

	return -EIO;
}
Exemple #5
0
static inline int cbw_scsi_read_capacity(mass_dev* dev, void *buffer, int size)
{
	int rcode, result, retries;
	static cbw_packet cbw={
		CBW_TAG, 		// cbw.signature
		-TAG_READ_CAPACITY,	// cbw.tag
		0,			// cbw.dataTransferLength
		0x80,			// cbw.flags
		0,			// cbw.lun
		12,			// cbw.comLength

		/* scsi command packet */
		{
			0x25,		// read capacity operation code
			0,		// lun/reserved/RelAdr
			0,		// LBA 1
			0,		// LBA 2
			0,		// LBA 3
			0,		// LBA 4
			0,		// reserved
			0,		// reserved
			0,		// reserved/PMI
			0,		// reserved
			0,		// reserved
			0,		// reserved
		}
	};

	cbw.dataTransferLength = size;

	XPRINTF("USBHDFSD: cbw_scsi_read_capacity\n");

	for(retries = USB_XFER_MAX_RETRIES; retries > 0; retries--){
		if(usb_bulk_command(dev, &cbw) == USB_RC_OK){
			rcode = usb_bulk_transfer(dev, USB_BLK_EP_IN, buffer, size);
			result = usb_bulk_manage_status(dev, -TAG_READ_CAPACITY);

			if(rcode == USB_RC_OK && result == 0) return 0;
		}
	}

	return -EIO;
}
inline int cbw_scsi_inquiry(mass_dev* dev, void *buffer, int size)
{
    int ret;
    cbw_packet cbw;
    
    XPRINTF("USBHDFSD: cbw_scsi_inquiry\n");
    
    cbw.signature = CBW_TAG;
    cbw.lun = 0;
	cbw.tag = -TAG_INQUIRY;
	cbw.dataTransferLength = size;	//INQUIRY_REPLY_LENGTH
	cbw.flags = 0x80;			//inquiry data will flow In
	cbw.comLength = 12;

	//scsi command packet
	cbw.comData[0] = 0x12;		//inquiry operation code
	cbw.comData[1] = 0;			//lun/reserved
	cbw.comData[2] = 0;			//page code
	cbw.comData[3] = 0;			//reserved
	cbw.comData[4] = size;		//inquiry reply length
	cbw.comData[5] = 0;			//reserved
	cbw.comData[6] = 0;			//reserved
	cbw.comData[7] = 0;			//reserved
	cbw.comData[8] = 0;			//reserved
	cbw.comData[9] = 0;			//reserved
	cbw.comData[10] = 0;		//reserved
	cbw.comData[11] = 0;		//reserved
    
	usb_bulk_command(dev, &cbw);

	ret = usb_bulk_transfer(dev->bulkEpI, buffer, size);
    if (ret != 0)
        printf("USBHDFSD: cbw_scsi_inquiry error from usb_bulk_transfer %d\n", ret);
    
	usb_bulk_manage_status(dev, -TAG_INQUIRY);
    
    return ret; // TODO What to return???
}
inline int cbw_scsi_write_sector(mass_dev* dev, int lba, void* buffer, int sectorSize, int sectorCount)
{
    int ret;
    cbw_packet cbw;
    
    XPRINTF("USBHDFSD: cbw_scsi_write_sector\n");

    cbw.signature = CBW_TAG;
    cbw.lun = 0;
	cbw.tag = -TAG_WRITE;
	cbw.dataTransferLength = sectorSize	 * sectorCount;
	cbw.flags = 0x00;			//write data will flow Out
	cbw.comLength = 12;

	//scsi command packet
	cbw.comData[0] = 0x2A;		//write operation code
	cbw.comData[1] = 0;			//LUN/DPO/FUA/Reserved/Reldr
	cbw.comData[2] = (lba & 0xFF000000) >> 24;	//lba 1 (MSB)
	cbw.comData[3] = (lba & 0xFF0000) >> 16;	//lba 2
	cbw.comData[4] = (lba & 0xFF00) >> 8;	//lba 3
	cbw.comData[5] = (lba & 0xFF);		//lba 4 (LSB)
	cbw.comData[6] = 0;			//Reserved
	cbw.comData[7] = (sectorCount & 0xFF00) >> 8;	//Transfer length MSB
	cbw.comData[8] = (sectorCount & 0xFF);			//Transfer length LSB
	cbw.comData[9] = 0;			//reserved
	cbw.comData[10] = 0;		//reserved
	cbw.comData[11] = 0;		//reserved
    
    usb_bulk_command(dev, &cbw);

    ret = usb_bulk_transfer(dev->bulkEpO, buffer, sectorSize * sectorCount);
    if (ret != 0)
        printf("USBHDFSD: cbw_scsi_write_sector error from usb_bulk_transfer %d\n", ret);

    ret = usb_bulk_manage_status(dev, -TAG_WRITE);
    return ret;
}
inline int cbw_scsi_request_sense(mass_dev* dev, void *buffer, int size)
{
    int ret;
    cbw_packet cbw;
    
    XPRINTF("USBHDFSD: cbw_scsi_request_sense\n");

    cbw.signature = CBW_TAG;
    cbw.lun = 0;
	cbw.tag = -TAG_REQUEST_SENSE;
	cbw.dataTransferLength = size;	//REQUEST_SENSE_REPLY_LENGTH
	cbw.flags = 0x80;			//sense data will flow In
	cbw.comLength = 12;

	//scsi command packet
	cbw.comData[0] = 0x03;		//request sense operation code
	cbw.comData[1] = 0;			//lun/reserved
	cbw.comData[2] = 0;			//reserved
	cbw.comData[3] = 0;			//reserved
	cbw.comData[4] = size;		//allocation length
	cbw.comData[5] = 0;			//reserved
	cbw.comData[6] = 0;			//reserved
	cbw.comData[7] = 0;			//reserved
	cbw.comData[8] = 0;			//reserved
	cbw.comData[9] = 0;			//reserved
	cbw.comData[10] = 0;		//reserved
	cbw.comData[11] = 0;		//reserved
    
    usb_bulk_command(dev, &cbw);

    ret = usb_bulk_transfer(dev->bulkEpI, buffer, size);
    if (ret != 0)
        printf("USBHDFSD: cbw_scsi_request_sense error from usb_bulk_transfer %d\n", ret);

    ret = usb_bulk_manage_status(dev, -TAG_REQUEST_SENSE);
    return ret;
}