\r
#include "MassStorageHost.h"\r
\r
-/* Project Tags, for reading out using the ButtLoad project */\r
-BUTTLOADTAG(ProjName, "LUFA MS Host App");\r
-BUTTLOADTAG(BuildTime, __TIME__);\r
-BUTTLOADTAG(BuildDate, __DATE__);\r
-BUTTLOADTAG(LUFAVersion, "LUFA V" LUFA_VERSION_STRING);\r
-\r
/* Scheduler Task List */\r
TASK_LIST\r
{\r
- { Task: USB_USBTask , TaskStatus: TASK_STOP },\r
- { Task: USB_MassStore_Host , TaskStatus: TASK_STOP },\r
+ { .Task = USB_USBTask , .TaskStatus = TASK_STOP },\r
+ { .Task = USB_MassStore_Host , .TaskStatus = TASK_STOP },\r
};\r
\r
/* Globals */\r
{\r
case HOST_STATE_Addressed:\r
/* Standard request to set the device configuration to configuration 1 */\r
- USB_HostRequest = (USB_Host_Request_Header_t)\r
+ USB_ControlRequest = (USB_Request_Header_t)\r
{\r
- bmRequestType: (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),\r
- bRequest: REQ_SetConfiguration,\r
- wValue: 1,\r
- wIndex: 0,\r
- wLength: 0,\r
+ .bmRequestType = (REQDIR_HOSTTODEVICE | REQTYPE_STANDARD | REQREC_DEVICE),\r
+ .bRequest = REQ_SetConfiguration,\r
+ .wValue = 1,\r
+ .wIndex = 0,\r
+ .wLength = 0,\r
};\r
\r
+ /* Select the control pipe for the request transfer */\r
+ Pipe_SelectPipe(PIPE_CONTROLPIPE);\r
+\r
/* Send the request, display error and wait for device detach if request fails */\r
if ((ErrorCode = USB_Host_SendControlRequest(NULL)) != HOST_SENDCONTROL_Successful)\r
{\r
/* Indicate device busy via the status LEDs */\r
UpdateStatus(Status_Busy);\r
\r
- /* Reset the Mass Storage device interface, ready for use */\r
- if ((ErrorCode = MassStore_MassStorageReset()) != HOST_SENDCONTROL_Successful)\r
- {\r
- ShowDiskReadError(PSTR("Mass Storage Reset"), ErrorCode);\r
- break;\r
- }\r
- \r
/* Send the request, display error and wait for device detach if request fails */\r
if ((ErrorCode = MassStore_GetMaxLUN(&MassStore_MaxLUNIndex)) != HOST_SENDCONTROL_Successful)\r
{ \r
- ShowDiskReadError(PSTR("Get Max LUN"), ErrorCode);\r
+ ShowDiskReadError(PSTR("Get Max LUN"), false, ErrorCode);\r
break;\r
}\r
\r
/* Print number of LUNs detected in the attached device */\r
printf_P(PSTR("Total LUNs: %d.\r\n"), (MassStore_MaxLUNIndex + 1));\r
-\r
- /* Set the prevent removal flag for the device, allowing it to be accessed */\r
- if ((ErrorCode = MassStore_PreventAllowMediumRemoval(0, true)) != 0)\r
+ \r
+ /* Reset the Mass Storage device interface, ready for use */\r
+ if ((ErrorCode = MassStore_MassStorageReset()) != HOST_SENDCONTROL_Successful)\r
{\r
- ShowDiskReadError(PSTR("Prevent/Allow Medium Removal"), ErrorCode);\r
+ ShowDiskReadError(PSTR("Mass Storage Reset"), false, ErrorCode);\r
break;\r
}\r
\r
/* Get sense data from the device - many devices will not accept any other commands until the sense data\r
* is read - both on start-up and after a failed command */\r
SCSI_Request_Sense_Response_t SenseData;\r
- if ((ErrorCode = MassStore_RequestSense(0, &SenseData)) != 0)\r
+ if (((ErrorCode = MassStore_RequestSense(0, &SenseData)) != 0) || (SCSICommandStatus.Status != Command_Pass))\r
+ {\r
+ ShowDiskReadError(PSTR("Request Sense"), (SCSICommandStatus.Status != Command_Pass), ErrorCode);\r
+ break;\r
+ }\r
+ \r
+ /* Set the prevent removal flag for the device, allowing it to be accessed */\r
+ if (((ErrorCode = MassStore_PreventAllowMediumRemoval(0, true)) != 0) || (SCSICommandStatus.Status != Command_Pass))\r
{\r
- ShowDiskReadError(PSTR("Request Sense"), ErrorCode);\r
+ ShowDiskReadError(PSTR("Prevent/Allow Medium Removal"), (SCSICommandStatus.Status != Command_Pass), ErrorCode);\r
break;\r
}\r
\r
- puts_P(PSTR("Waiting until ready"));\r
+ puts_P(PSTR("Waiting until ready.."));\r
\r
/* Wait until disk ready */\r
do\r
{\r
Serial_TxByte('.');\r
- MassStore_TestUnitReady(0);\r
+ \r
+ if ((ErrorCode = MassStore_TestUnitReady(0)) != 0)\r
+ {\r
+ ShowDiskReadError(PSTR("Test Unit Ready"), false, ErrorCode);\r
+ break; \r
+ }\r
}\r
while ((SCSICommandStatus.Status != Command_Pass) && USB_IsConnected);\r
\r
SCSI_Capacity_t DiskCapacity;\r
\r
/* Retrieve disk capacity */\r
- if ((ErrorCode = MassStore_ReadCapacity(0, &DiskCapacity)) != 0)\r
+ if (((ErrorCode = MassStore_ReadCapacity(0, &DiskCapacity)) != 0) || (SCSICommandStatus.Status != Command_Pass))\r
{\r
- ShowDiskReadError(PSTR("Read Capacity"), ErrorCode);\r
+ ShowDiskReadError(PSTR("Read Capacity"), (SCSICommandStatus.Status != Command_Pass), ErrorCode);\r
break;\r
}\r
\r
/* Display the disk capacity in blocks * block size bytes */\r
printf_P(PSTR("%lu blocks of %lu bytes.\r\n"), DiskCapacity.Blocks, DiskCapacity.BlockSize);\r
- \r
+\r
/* Create a new buffer capabable of holding a single block from the device */\r
uint8_t BlockBuffer[DiskCapacity.BlockSize];\r
\r
/* Read in the first 512 byte block from the device */\r
- if ((ErrorCode = MassStore_ReadDeviceBlock(0, 0x00000000, 1, DiskCapacity.BlockSize, BlockBuffer)) != 0)\r
+ if (((ErrorCode = MassStore_ReadDeviceBlock(0, 0x00000000, 1, DiskCapacity.BlockSize, BlockBuffer)) != 0) ||\r
+ (SCSICommandStatus.Status != Command_Pass))\r
{\r
- ShowDiskReadError(PSTR("Read Device Block"), ErrorCode);\r
+ ShowDiskReadError(PSTR("Read Device Block"), (SCSICommandStatus.Status != Command_Pass), ErrorCode);\r
break;\r
}\r
\r
- /* Show the number of bytes not transferred in the previous command */\r
- printf_P(PSTR("Transfer Residue: %lu\r\n"), SCSICommandStatus.DataTransferResidue);\r
- \r
puts_P(PSTR("\r\nContents of first block:\r\n"));\r
\r
/* Print out the first block in both HEX and ASCII, 16 bytes per line */\r
for (uint32_t CurrBlock = 0; CurrBlock < DiskCapacity.Blocks; CurrBlock++)\r
{\r
/* Read in the next block of data from the device */\r
- if ((ErrorCode = MassStore_ReadDeviceBlock(0, CurrBlock, 1, DiskCapacity.BlockSize, BlockBuffer)) != 0)\r
+ if (((ErrorCode = MassStore_ReadDeviceBlock(0, CurrBlock, 1, DiskCapacity.BlockSize, BlockBuffer)) != 0) ||\r
+ (SCSICommandStatus.Status != Command_Pass))\r
{\r
- ShowDiskReadError(PSTR("Read Device Block"), ErrorCode);\r
+ ShowDiskReadError(PSTR("Read Device Block"), (SCSICommandStatus.Status != Command_Pass), ErrorCode);\r
break;\r
}\r
\r
* continuing.\r
*\r
* \param CommandString ASCII string located in PROGMEM space indicating what operation failed\r
+ * \param FailedAtSCSILayer Indicates if the command failed at the (logical) SCSI layer or at the physical USB layer\r
* \param ErrorCode Error code of the function which failed to complete successfully\r
*/\r
-void ShowDiskReadError(char* CommandString, uint8_t ErrorCode)\r
+void ShowDiskReadError(char* CommandString, bool FailedAtSCSILayer, uint8_t ErrorCode)\r
{\r
- /* Display the error code */\r
- printf_P(PSTR(ESC_BG_RED "Command error (%S).\r\n"), CommandString);\r
- printf_P(PSTR(" -- Error Code: %d"), ErrorCode);\r
- \r
+ if (FailedAtSCSILayer)\r
+ {\r
+ /* Display the error code */\r
+ printf_P(PSTR(ESC_BG_RED "SCSI command error (%S).\r\n"), CommandString);\r
+ printf_P(PSTR(" -- Status Code: %d"), ErrorCode);\r
+ }\r
+ else\r
+ {\r
+ /* Display the error code */\r
+ printf_P(PSTR(ESC_BG_RED "Command error (%S).\r\n"), CommandString);\r
+ printf_P(PSTR(" -- Error Code: %d"), ErrorCode); \r
+ }\r
+\r
Pipe_Freeze();\r
\r
/* Indicate device error via the status LEDs */\r