Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Dependencies: USBDevice USBMSD_SD mbed
Fork of USBMSD_SD_HelloWorld_Mbed by
Diff: USBMSD/USBMSD.cpp
- Revision:
- 10:cf8fd2b6ca23
- Parent:
- 9:9c343b9ee6d8
- Child:
- 11:a26e7b7a1221
--- a/USBMSD/USBMSD.cpp Tue Nov 15 09:16:25 2011 +0000
+++ b/USBMSD/USBMSD.cpp Wed Nov 16 11:06:27 2011 +0000
@@ -48,26 +48,74 @@
USBMSD::USBMSD(uint16_t vendor_id, uint16_t product_id, uint16_t product_release): USBDevice(vendor_id, product_id, product_release) {
}
-
-DigitalOut l2(LED2);
-// Called in ISR context to process a class specific request
-bool USBMSD::USBCallback_request(void) {
-
+bool USBMSD::USBCallback_request() {
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)) {
+ printf("report desc\r\n");
+ transfer->remaining = reportDescLength();
+ transfer->ptr = reportDesc();
+ transfer->direction = DEVICE_TO_HOST;
+ success = true;
+ }
+ break;
+ case HID_DESCRIPTOR:
+ printf("hid desc\r\n");
+ // 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 MSC_REQUEST_RESET:
- reset();
+ 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;
success = true;
- break;
case MSC_REQUEST_GET_MAX_LUN:
+ printf("get max lun\r\n");
transfer->remaining = 1;
- transfer->ptr = getMaxLUN();
+ transfer->ptr = dum;
transfer->direction = DEVICE_TO_HOST;
success = true;
break;
+ case SET_IDLE:
+ printf("set idle\r\n");
+ // First byte will be used for report ID
+ success = true;
default:
break;
}
@@ -76,6 +124,39 @@
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() {
@@ -91,13 +172,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);
@@ -121,7 +202,7 @@
bool USBMSD::EP2_OUT_callback() {
uint16_t size = 0;
uint8_t buf[MAX_PACKET_SIZE_EPBULK];
- read(EPBULK_OUT, buf, &size, MAX_PACKET_SIZE_EPBULK);
+ USBDevice::read(EPBULK_OUT, buf, &size, MAX_PACKET_SIZE_EPBULK);
switch (stage) {
// the device has to decode the CBW received
case READ_CBW:
@@ -544,11 +625,14 @@
}
// 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;
}
@@ -571,22 +655,45 @@
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
- // 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
-
- // Interface 0, Alternate Setting 0, MSC Class
+ // Interface 1, Alternate Setting 0, MSC Class
9, // bLength
4, // bDescriptorType
0x00, // bInterfaceNumber
@@ -595,7 +702,7 @@
0x08, // bInterfaceClass
0x06, // bInterfaceSubClass
0x50, // bInterfaceProtocol
- 0x04, // iInterface
+ 0x00, // iInterface
// endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
7, // bLength
@@ -613,7 +720,45 @@
0x02, // bmAttributes (0x02=bulk)
LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB)
MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB)
- 0 // bInterval
+ 0, // bInterval
+
+ // interface 1: HID
+ INTERFACE_DESCRIPTOR_LENGTH, // bLength
+ INTERFACE_DESCRIPTOR, // bDescriptorType
+ 0x01, // 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)
+
+ 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)
+
};
return configDescriptor;
}
