USBMSD SD card Hello World for Mbed platforms
Dependencies: mbed USBMSD_SD USBDevice
Diff: USBMSD/USBMSD.cpp
- Revision:
- 12:a12eb1fc05f3
- Parent:
- 11:a26e7b7a1221
--- a/USBMSD/USBMSD.cpp Wed Nov 16 17:17:42 2011 +0000 +++ b/USBMSD/USBMSD.cpp Wed Nov 30 17:50:35 2011 +0000 @@ -48,69 +48,26 @@ USBMSD::USBMSD(uint16_t vendor_id, uint16_t product_id, uint16_t product_release): USBDevice(vendor_id, product_id, product_release) { } -bool USBMSD::USBCallback_request() { + +DigitalOut l2(LED2); +// Called in ISR context to process a class specific request +bool USBMSD::USBCallback_request(void) { + bool success = false; CONTROL_TRANSFER * transfer = getTransferPtr(); - uint8_t *hidDescriptor; - - // Process additional standard requests - - if ((transfer->setup.bmRequestType.Type == STANDARD_TYPE)) { - switch (transfer->setup.bRequest) { - case GET_DESCRIPTOR: - switch (DESCRIPTOR_TYPE(transfer->setup.wValue)) { - case REPORT_DESCRIPTOR: - if ((reportDesc() != NULL) \ - && (reportDescLength() != 0)) { - transfer->remaining = reportDescLength(); - transfer->ptr = reportDesc(); - transfer->direction = DEVICE_TO_HOST; - success = true; - } - break; - case HID_DESCRIPTOR: - // Find the HID descriptor, after the configuration descriptor - hidDescriptor = findDescriptor(HID_DESCRIPTOR); - if (hidDescriptor != NULL) { - transfer->remaining = HID_DESCRIPTOR_LENGTH; - transfer->ptr = hidDescriptor; - transfer->direction = DEVICE_TO_HOST; - success = true; - } - break; - - default: - break; - } - break; - default: - break; - } - } - - // Process class-specific requests if (transfer->setup.bmRequestType.Type == CLASS_TYPE) { - uint8_t * dum = {0}; switch (transfer->setup.bRequest) { - case SET_REPORT: - // First byte will be used for report ID - outputReport.data[0] = transfer->setup.wValue & 0xff; - outputReport.length = transfer->setup.wLength + 1; - - transfer->remaining = sizeof(outputReport.data) - 1; - transfer->ptr = &outputReport.data[1]; - transfer->direction = HOST_TO_DEVICE; - transfer->notify = true; + case MSC_REQUEST_RESET: + reset(); success = true; + break; case MSC_REQUEST_GET_MAX_LUN: transfer->remaining = 1; - transfer->ptr = dum; + transfer->ptr = getMaxLUN(); transfer->direction = DEVICE_TO_HOST; success = true; break; - case SET_IDLE: - success = true; default: break; } @@ -119,39 +76,6 @@ return success; } -bool USBMSD::send(HID_REPORT *report) { - return USBDevice::write(EPINT_IN, report->data, report->length, MAX_HID_REPORT_SIZE); -} - - -bool USBMSD::read(HID_REPORT *report) { - uint16_t bytesRead = 0; - bool result; - result = USBDevice::read(EPINT_OUT, report->data, &bytesRead, MAX_HID_REPORT_SIZE); - if (!readStart(EPINT_OUT, MAX_HID_REPORT_SIZE)) - return false; - report->length = bytesRead; - return result; -} - - -bool USBMSD::readNB(HID_REPORT *report) { - uint16_t bytesRead = 0; - bool result; - result = USBDevice::readNB(EPINT_OUT, report->data, &bytesRead, MAX_HID_REPORT_SIZE); - report->length = bytesRead; - if (!readStart(EPINT_OUT, MAX_HID_REPORT_SIZE)) - return false; - return result; -} - - -uint16_t USBMSD::reportDescLength() { - reportDesc(); - return reportLength; -} - - bool USBMSD::connect() { @@ -167,17 +91,13 @@ } BlockCount = disk_sectors(); - + //get memory size MemorySize = BlockCount * BlockSize; if (!MemorySize) { return false; } - /*printf("blockSize: %d\r\n", BlockSize); - printf("memSize: %d\r\n", MemorySize); - printf("number of blocks: %d\r\n", BlockCount);*/ - //connect the device USBDevice::connect(); return true; @@ -197,7 +117,7 @@ bool USBMSD::EP2_OUT_callback() { uint16_t size = 0; uint8_t buf[MAX_PACKET_SIZE_EPBULK]; - USBDevice::read(EPBULK_OUT, buf, &size, MAX_PACKET_SIZE_EPBULK); + readEP(EPBULK_OUT, buf, &size, MAX_PACKET_SIZE_EPBULK); switch (stage) { // the device has to decode the CBW received case READ_CBW: @@ -325,8 +245,8 @@ bool USBMSD::inquiryRequest (void) { uint8_t inquiry[] = { 0x00, 0x80, 0x00, 0x01, 36 - 4, 0x80, 0x00, 0x00, - 'M', 'b', 'e', 'd', '.', 'o', 'r', 'g', - 'M', 'b', 'e', 'd', ' ', 'U', 'S', 'B', ' ', 'D', 'i', 's', 'k', ' ', ' ', ' ', + 'M', 'B', 'E', 'D', '.', 'O', 'R', 'G', + 'M', 'B', 'E', 'D', ' ', 'U', 'S', 'B', ' ', 'D', 'I', 'S', 'K', ' ', ' ', ' ', '1', '.', '0', ' ', }; if (!write(inquiry, sizeof(inquiry))) { @@ -380,7 +300,9 @@ } stage = SEND_CSW; - writeNB(EPBULK_IN, buf, size, MAX_PACKET_SIZE_EPBULK); + if (!writeNB(EPBULK_IN, buf, size, MAX_PACKET_SIZE_EPBULK)) { + return false; + } csw.DataResidue -= size; csw.Status = CSW_PASSED; @@ -436,7 +358,7 @@ sendCSW(); } - +DigitalOut l1(LED1); void USBMSD::CBWDecode(uint8_t * buf, uint16_t size) { if (size == sizeof(cbw)) { memcpy((uint8_t *)&cbw, buf, size); @@ -618,14 +540,11 @@ } // Configure endpoints > 0 - addEndpoint(EPINT_IN, MAX_PACKET_SIZE_EPINT); - addEndpoint(EPINT_OUT, MAX_PACKET_SIZE_EPINT); - addEndpoint(EPBULK_IN, MAX_PACKET_SIZE_EPBULK); addEndpoint(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK); + //activate readings readStart(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK); - readStart(EPINT_OUT, MAX_PACKET_SIZE_EPINT); return true; } @@ -641,99 +560,38 @@ uint8_t * USBMSD::stringIproductDesc() { static uint8_t stringIproductDescriptor[] = { - 0x1e, //bLength + 0x12, //bLength STRING_DESCRIPTOR, //bDescriptorType 0x03 - 'M',0,'b',0,'e',0,'d',0,' ',0,'M',0,'S',0,'D', 0, ' ', 0, '&', 0, ' ', 0, 'H', 0, 'I', 0, 'D', 0 //bString iProduct - Mbed Audio + 'M',0,'b',0,'e',0,'d',0,' ',0,'M',0,'S',0,'D',0 //bString iProduct - Mbed Audio }; return stringIproductDescriptor; } -uint8_t * USBMSD::reportDesc() { - static uint8_t reportDescriptor[] = { - 0x06, LSB(0xFFAB), MSB(0xFFAB), - 0x0A, LSB(0x0200), MSB(0x0200), - 0xA1, 0x01, // Collection 0x01 - 0x75, 0x08, // report size = 8 bits - 0x15, 0x00, // logical minimum = 0 - 0x26, 0xFF, 0x00, // logical maximum = 255 - 0x95, 64, // report count - 0x09, 0x01, // usage - 0x81, 0x02, // Input (array) - 0x95, 64, // report count - 0x09, 0x02, // usage - 0x91, 0x02, // Output (array) - 0xC0 // end collection - - }; - reportLength = sizeof(reportDescriptor); - return reportDescriptor; -} - -#define TOTAL_DESCRIPTOR_LENGTH ((1 * CONFIGURATION_DESCRIPTOR_LENGTH) \ - + (2 * INTERFACE_DESCRIPTOR_LENGTH) \ - + (1 * HID_DESCRIPTOR_LENGTH) \ - + (4 * ENDPOINT_DESCRIPTOR_LENGTH)) uint8_t * USBMSD::configurationDesc() { static uint8_t configDescriptor[] = { - CONFIGURATION_DESCRIPTOR_LENGTH,// bLength - CONFIGURATION_DESCRIPTOR, // bDescriptorType - LSB(TOTAL_DESCRIPTOR_LENGTH), // wTotalLength (LSB) - MSB(TOTAL_DESCRIPTOR_LENGTH), // wTotalLength (MSB) - 0x02, // bNumInterfaces (2 interfaces) - DEFAULT_CONFIGURATION, // bConfigurationValue - 0x00, // iConfiguration - C_RESERVED | C_SELF_POWERED, // bmAttributes - C_POWER(0), // bMaxPower - - - // interface 1: HID - INTERFACE_DESCRIPTOR_LENGTH, // bLength - INTERFACE_DESCRIPTOR, // bDescriptorType - 0x00, // bInterfaceNumber - 0x00, // bAlternateSetting - 0x02, // bNumEndpoints - HID_CLASS, // bInterfaceClass - HID_SUBCLASS_NONE, // bInterfaceSubClass - HID_PROTOCOL_NONE, // bInterfaceProtocol - 0x00, // iInterface - HID_DESCRIPTOR_LENGTH, // bLength - HID_DESCRIPTOR, // bDescriptorType - LSB(HID_VERSION_1_11), // bcdHID (LSB) - MSB(HID_VERSION_1_11), // bcdHID (MSB) - 0x00, // bCountryCode - 0x01, // bNumDescriptors - REPORT_DESCRIPTOR, // bDescriptorType - LSB(this->reportDescLength()), // wDescriptorLength (LSB) - MSB(this->reportDescLength()), // wDescriptorLength (MSB) + // Configuration 1 + 9, // bLength + 2, // bDescriptorType + LSB(9 + 9 + 7 + 7), // wTotalLength + MSB(9 + 9 + 7 + 7), + 0x01, // bNumInterfaces + 0x01, // bConfigurationValue: 0x01 is used to select this configuration + 0x00, // iConfiguration: no string to describe this configuration + 0xC0, // bmAttributes + 100, // bMaxPower, device power consumption is 100 mA - ENDPOINT_DESCRIPTOR_LENGTH, // bLength - ENDPOINT_DESCRIPTOR, // bDescriptorType - PHY_TO_DESC(EPINT_IN), // bEndpointAddress - E_INTERRUPT, // bmAttributes - LSB(MAX_PACKET_SIZE_EPINT), // wMaxPacketSize (LSB) - MSB(MAX_PACKET_SIZE_EPINT), // wMaxPacketSize (MSB) - 10, // bInterval (milliseconds) - - ENDPOINT_DESCRIPTOR_LENGTH, // bLength - ENDPOINT_DESCRIPTOR, // bDescriptorType - PHY_TO_DESC(EPINT_OUT), // bEndpointAddress - E_INTERRUPT, // bmAttributes - LSB(MAX_PACKET_SIZE_EPINT), // wMaxPacketSize (LSB) - MSB(MAX_PACKET_SIZE_EPINT), // wMaxPacketSize (MSB) - 10, // bInterval (milliseconds) - - // Interface 1, Alternate Setting 0, MSC Class + // Interface 0, Alternate Setting 0, MSC Class 9, // bLength 4, // bDescriptorType - 0x01, // bInterfaceNumber + 0x00, // bInterfaceNumber 0x00, // bAlternateSetting 0x02, // bNumEndpoints 0x08, // bInterfaceClass 0x06, // bInterfaceSubClass 0x50, // bInterfaceProtocol - 0x00, // iInterface + 0x04, // iInterface // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13 7, // bLength @@ -751,9 +609,7 @@ 0x02, // bmAttributes (0x02=bulk) LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB) MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB) - 0, // bInterval - - + 0 // bInterval }; return configDescriptor; }