USBDevice stack

Dependents:   erg USBSerial_HelloWorld Slingshot SuperScanner ... more

Embed: (wiki syntax)

« Back to documentation index

Show/hide line numbers USBCDC.cpp Source File

USBCDC.cpp

00001 /* Copyright (c) 2010-2011 mbed.org, MIT License
00002 *
00003 * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
00004 * and associated documentation files (the "Software"), to deal in the Software without
00005 * restriction, including without limitation the rights to use, copy, modify, merge, publish,
00006 * distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the
00007 * Software is furnished to do so, subject to the following conditions:
00008 *
00009 * The above copyright notice and this permission notice shall be included in all copies or
00010 * substantial portions of the Software.
00011 *
00012 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
00013 * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
00014 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
00015 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
00016 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
00017 */
00018 
00019 #include "stdint.h"
00020 #include "USBCDC.h"
00021 
00022 static uint8_t cdc_line_coding[7]= {0x80, 0x25, 0x00, 0x00, 0x00, 0x00, 0x08};
00023 
00024 #define DEFAULT_CONFIGURATION (1)
00025 
00026 #define CDC_SET_LINE_CODING        0x20
00027 #define CDC_GET_LINE_CODING        0x21
00028 #define CDC_SET_CONTROL_LINE_STATE 0x22
00029 
00030 #define MAX_CDC_REPORT_SIZE MAX_PACKET_SIZE_EPBULK
00031 
00032 USBCDC::USBCDC(uint16_t vendor_id, uint16_t product_id, uint16_t product_release): USBDevice(vendor_id, product_id, product_release) {
00033     USBDevice::connect();
00034 }
00035 
00036 bool USBCDC::USBCallback_request(void) {
00037     /* Called in ISR context */
00038 
00039     bool success = false;
00040     CONTROL_TRANSFER * transfer = getTransferPtr();
00041 
00042     /* Process class-specific requests */
00043 
00044     if (transfer->setup.bmRequestType.Type == CLASS_TYPE) {
00045         switch (transfer->setup.bRequest) {
00046             case CDC_GET_LINE_CODING:
00047                 transfer->remaining = 7;
00048                 transfer->ptr = cdc_line_coding;
00049                 transfer->direction = DEVICE_TO_HOST;
00050                 success = true;
00051                 break;
00052             case CDC_SET_LINE_CODING:
00053                 transfer->remaining = 7;
00054                 success = true;
00055                 break;
00056             case CDC_SET_CONTROL_LINE_STATE:
00057                 success = true;
00058                 break;
00059             default:
00060                 break;
00061         }
00062     }
00063 
00064     return success;
00065 }
00066 
00067 
00068 // Called in ISR context
00069 // Set configuration. Return false if the
00070 // configuration is not supported.
00071 bool USBCDC::USBCallback_setConfiguration(uint8_t configuration) {
00072     if (configuration != DEFAULT_CONFIGURATION) {
00073         return false;
00074     }
00075 
00076     // Configure endpoints > 0
00077     addEndpoint(EPINT_IN, MAX_PACKET_SIZE_EPINT);
00078     addEndpoint(EPBULK_IN, MAX_PACKET_SIZE_EPBULK);
00079     addEndpoint(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);
00080 
00081     // We activate the endpoint to be able to recceive data
00082     readStart(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);
00083     return true;
00084 }
00085 
00086 bool USBCDC::send(uint8_t * buffer, uint32_t size) {
00087     return USBDevice::write(EPBULK_IN, buffer, size, MAX_CDC_REPORT_SIZE);
00088 }
00089 
00090 bool USBCDC::readEP(uint8_t * buffer, uint32_t * size) {
00091     if (!USBDevice::readEP(EPBULK_OUT, buffer, size, MAX_CDC_REPORT_SIZE))
00092         return false;
00093     if (!readStart(EPBULK_OUT, MAX_CDC_REPORT_SIZE))
00094         return false;
00095     return true;
00096 }
00097 
00098 bool USBCDC::readEP_NB(uint8_t * buffer, uint32_t * size) {
00099     if (!USBDevice::readEP_NB(EPBULK_OUT, buffer, size, MAX_CDC_REPORT_SIZE))
00100         return false;
00101     if (!readStart(EPBULK_OUT, MAX_CDC_REPORT_SIZE))
00102         return false;
00103     return true;
00104 }
00105 
00106 
00107 uint8_t * USBCDC::deviceDesc() {
00108     static uint8_t deviceDescriptor[] = {
00109         18,                   // bLength
00110         1,                    // bDescriptorType
00111         0x10, 0x01,           // bcdUSB
00112         2,                    // bDeviceClass
00113         0,                    // bDeviceSubClass
00114         0,                    // bDeviceProtocol
00115         MAX_PACKET_SIZE_EP0,  // bMaxPacketSize0
00116         LSB(VENDOR_ID), MSB(VENDOR_ID),  // idVendor
00117         LSB(PRODUCT_ID), MSB(PRODUCT_ID),// idProduct
00118         0x00, 0x01,           // bcdDevice
00119         1,                    // iManufacturer
00120         2,                    // iProduct
00121         3,                    // iSerialNumber
00122         1                     // bNumConfigurations
00123     };
00124     return deviceDescriptor;
00125 }
00126 
00127 uint8_t * USBCDC::stringIinterfaceDesc() {
00128     static uint8_t stringIinterfaceDescriptor[] = {
00129         0x08,
00130         STRING_DESCRIPTOR,
00131         'C',0,'D',0,'C',0,
00132     };
00133     return stringIinterfaceDescriptor;
00134 }
00135 
00136 uint8_t * USBCDC::stringIproductDesc() {
00137     static uint8_t stringIproductDescriptor[] = {
00138         0x16,
00139         STRING_DESCRIPTOR,
00140         'C',0,'D',0,'C',0,' ',0,'D',0,'E',0,'V',0,'I',0,'C',0,'E',0
00141     };
00142     return stringIproductDescriptor;
00143 }
00144 
00145 
00146 #define CONFIG1_DESC_SIZE (9+9+5+5+4+5+7+9+7+7)
00147 
00148 uint8_t * USBCDC::configurationDesc() {
00149     static uint8_t configDescriptor[] = {
00150         9,                      // bLength;
00151         2,                      // bDescriptorType;
00152         LSB(CONFIG1_DESC_SIZE), // wTotalLength
00153         MSB(CONFIG1_DESC_SIZE),
00154         2,                      // bNumInterfaces
00155         1,                      // bConfigurationValue
00156         0,                      // iConfiguration
00157         0x80,                   // bmAttributes
00158         50,                     // bMaxPower
00159 
00160         // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
00161         9,                      // bLength
00162         4,                      // bDescriptorType
00163         0,                      // bInterfaceNumber
00164         0,                      // bAlternateSetting
00165         1,                      // bNumEndpoints
00166         0x02,                   // bInterfaceClass
00167         0x02,                   // bInterfaceSubClass
00168         0x01,                   // bInterfaceProtocol
00169         0,                      // iInterface
00170 
00171         // CDC Header Functional Descriptor, CDC Spec 5.2.3.1, Table 26
00172         5,                      // bFunctionLength
00173         0x24,                   // bDescriptorType
00174         0x00,                   // bDescriptorSubtype
00175         0x10, 0x01,             // bcdCDC
00176 
00177         // Call Management Functional Descriptor, CDC Spec 5.2.3.2, Table 27
00178         5,                      // bFunctionLength
00179         0x24,                   // bDescriptorType
00180         0x01,                   // bDescriptorSubtype
00181         0x03,                   // bmCapabilities
00182         1,                      // bDataInterface
00183 
00184         // Abstract Control Management Functional Descriptor, CDC Spec 5.2.3.3, Table 28
00185         4,                      // bFunctionLength
00186         0x24,                   // bDescriptorType
00187         0x02,                   // bDescriptorSubtype
00188         0x06,                   // bmCapabilities
00189 
00190         // Union Functional Descriptor, CDC Spec 5.2.3.8, Table 33
00191         5,                      // bFunctionLength
00192         0x24,                   // bDescriptorType
00193         0x06,                   // bDescriptorSubtype
00194         0,                      // bMasterInterface
00195         1,                      // bSlaveInterface0
00196 
00197         // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
00198         ENDPOINT_DESCRIPTOR_LENGTH,     // bLength
00199         ENDPOINT_DESCRIPTOR,            // bDescriptorType
00200         PHY_TO_DESC(EPINT_IN),          // bEndpointAddress
00201         E_INTERRUPT,                    // bmAttributes (0x03=intr)
00202         LSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (LSB)
00203         MSB(MAX_PACKET_SIZE_EPINT),     // wMaxPacketSize (MSB)
00204         16,                             // bInterval
00205 
00206 
00207 
00208 
00209         // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
00210         9,          // bLength
00211         4,          // bDescriptorType
00212         1,          // bInterfaceNumber
00213         0,          // bAlternateSetting
00214         2,          // bNumEndpoints
00215         0x0A,       // bInterfaceClass
00216         0x00,       // bInterfaceSubClass
00217         0x00,       // bInterfaceProtocol
00218         0,          // iInterface
00219 
00220         // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
00221         7,                      // bLength
00222         5,                      // bDescriptorType
00223         PHY_TO_DESC(EPBULK_IN), // bEndpointAddress
00224         0x02,                   // bmAttributes (0x02=bulk)
00225         LSB(MAX_PACKET_SIZE_EPBULK),    // wMaxPacketSize (LSB)
00226         MSB(MAX_PACKET_SIZE_EPBULK),    // wMaxPacketSize (MSB)
00227         0,                      // bInterval
00228 
00229         // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
00230         7,                      // bLength
00231         5,                      // bDescriptorType
00232         PHY_TO_DESC(EPBULK_OUT),// bEndpointAddress
00233         0x02,                   // bmAttributes (0x02=bulk)
00234         LSB(MAX_PACKET_SIZE_EPBULK),    // wMaxPacketSize (LSB)
00235         MSB(MAX_PACKET_SIZE_EPBULK),     // wMaxPacketSize (MSB)
00236         0                       // bInterval
00237     };
00238     return configDescriptor;
00239 }