The preloaded firmware shipped on the mBot.

Dependencies:   mbed

Please use the version of this project/repo found at: http://developer.mbed.org/teams/Outrageous-Circuits/code/Official_mBot/

Committer:
jeffknaggs
Date:
Tue Nov 25 14:49:40 2014 +0000
Revision:
1:ffd9a51e7d35
Parent:
0:865d42c46692
Initial commit.

Who changed what in which revision?

UserRevisionLine numberNew contents of line
jeffknaggs 0:865d42c46692 1 /* Copyright (c) 2010-2011 mbed.org, MIT License
jeffknaggs 0:865d42c46692 2 *
jeffknaggs 0:865d42c46692 3 * Permission is hereby granted, free of charge, to any person obtaining a copy of this software
jeffknaggs 0:865d42c46692 4 * and associated documentation files (the "Software"), to deal in the Software without
jeffknaggs 0:865d42c46692 5 * restriction, including without limitation the rights to use, copy, modify, merge, publish,
jeffknaggs 0:865d42c46692 6 * distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the
jeffknaggs 0:865d42c46692 7 * Software is furnished to do so, subject to the following conditions:
jeffknaggs 0:865d42c46692 8 *
jeffknaggs 0:865d42c46692 9 * The above copyright notice and this permission notice shall be included in all copies or
jeffknaggs 0:865d42c46692 10 * substantial portions of the Software.
jeffknaggs 0:865d42c46692 11 *
jeffknaggs 0:865d42c46692 12 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING
jeffknaggs 0:865d42c46692 13 * BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
jeffknaggs 0:865d42c46692 14 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
jeffknaggs 0:865d42c46692 15 * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
jeffknaggs 0:865d42c46692 16 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
jeffknaggs 0:865d42c46692 17 */
jeffknaggs 0:865d42c46692 18
jeffknaggs 0:865d42c46692 19 #include "stdint.h"
jeffknaggs 0:865d42c46692 20 #include "USBCDC.h"
jeffknaggs 0:865d42c46692 21
jeffknaggs 0:865d42c46692 22 static uint8_t cdc_line_coding[7]= {0x80, 0x25, 0x00, 0x00, 0x00, 0x00, 0x08};
jeffknaggs 0:865d42c46692 23
jeffknaggs 0:865d42c46692 24 #define DEFAULT_CONFIGURATION (1)
jeffknaggs 0:865d42c46692 25
jeffknaggs 0:865d42c46692 26 #define CDC_SET_LINE_CODING 0x20
jeffknaggs 0:865d42c46692 27 #define CDC_GET_LINE_CODING 0x21
jeffknaggs 0:865d42c46692 28 #define CDC_SET_CONTROL_LINE_STATE 0x22
jeffknaggs 0:865d42c46692 29
jeffknaggs 0:865d42c46692 30 #define MAX_CDC_REPORT_SIZE MAX_PACKET_SIZE_EPBULK
jeffknaggs 0:865d42c46692 31
jeffknaggs 0:865d42c46692 32 USBCDC::USBCDC(uint16_t vendor_id, uint16_t product_id, uint16_t product_release, bool connect_blocking): USBDevice(vendor_id, product_id, product_release) {
jeffknaggs 0:865d42c46692 33 terminal_connected = false;
jeffknaggs 0:865d42c46692 34 USBDevice::connect(connect_blocking);
jeffknaggs 0:865d42c46692 35 }
jeffknaggs 0:865d42c46692 36
jeffknaggs 0:865d42c46692 37 bool USBCDC::USBCallback_request(void) {
jeffknaggs 0:865d42c46692 38 /* Called in ISR context */
jeffknaggs 0:865d42c46692 39
jeffknaggs 0:865d42c46692 40 bool success = false;
jeffknaggs 0:865d42c46692 41 CONTROL_TRANSFER * transfer = getTransferPtr();
jeffknaggs 0:865d42c46692 42
jeffknaggs 0:865d42c46692 43 /* Process class-specific requests */
jeffknaggs 0:865d42c46692 44
jeffknaggs 0:865d42c46692 45 if (transfer->setup.bmRequestType.Type == CLASS_TYPE) {
jeffknaggs 0:865d42c46692 46 switch (transfer->setup.bRequest) {
jeffknaggs 0:865d42c46692 47 case CDC_GET_LINE_CODING:
jeffknaggs 0:865d42c46692 48 transfer->remaining = 7;
jeffknaggs 0:865d42c46692 49 transfer->ptr = cdc_line_coding;
jeffknaggs 0:865d42c46692 50 transfer->direction = DEVICE_TO_HOST;
jeffknaggs 0:865d42c46692 51 success = true;
jeffknaggs 0:865d42c46692 52 break;
jeffknaggs 0:865d42c46692 53 case CDC_SET_LINE_CODING:
jeffknaggs 0:865d42c46692 54 transfer->remaining = 7;
jeffknaggs 0:865d42c46692 55 transfer->notify = true;
jeffknaggs 0:865d42c46692 56 success = true;
jeffknaggs 0:865d42c46692 57 terminal_connected = true;
jeffknaggs 0:865d42c46692 58 break;
jeffknaggs 0:865d42c46692 59 case CDC_SET_CONTROL_LINE_STATE:
jeffknaggs 0:865d42c46692 60 terminal_connected = false;
jeffknaggs 0:865d42c46692 61 success = true;
jeffknaggs 0:865d42c46692 62 break;
jeffknaggs 0:865d42c46692 63 default:
jeffknaggs 0:865d42c46692 64 break;
jeffknaggs 0:865d42c46692 65 }
jeffknaggs 0:865d42c46692 66 }
jeffknaggs 0:865d42c46692 67
jeffknaggs 0:865d42c46692 68 return success;
jeffknaggs 0:865d42c46692 69 }
jeffknaggs 0:865d42c46692 70
jeffknaggs 0:865d42c46692 71 void USBCDC::USBCallback_requestCompleted(uint8_t *buf, uint32_t length) {
jeffknaggs 0:865d42c46692 72 // Request of setting line coding has 7 bytes
jeffknaggs 0:865d42c46692 73 if (length != 7) {
jeffknaggs 0:865d42c46692 74 return;
jeffknaggs 0:865d42c46692 75 }
jeffknaggs 0:865d42c46692 76
jeffknaggs 0:865d42c46692 77 CONTROL_TRANSFER * transfer = getTransferPtr();
jeffknaggs 0:865d42c46692 78
jeffknaggs 0:865d42c46692 79 /* Process class-specific requests */
jeffknaggs 0:865d42c46692 80 if (transfer->setup.bmRequestType.Type == CLASS_TYPE) {
jeffknaggs 0:865d42c46692 81 if (transfer->setup.bRequest == CDC_SET_LINE_CODING) {
jeffknaggs 0:865d42c46692 82 if (memcmp(cdc_line_coding, buf, 7)) {
jeffknaggs 0:865d42c46692 83 memcpy(cdc_line_coding, buf, 7);
jeffknaggs 0:865d42c46692 84
jeffknaggs 0:865d42c46692 85 int baud = buf[0] + (buf[1] << 8)
jeffknaggs 0:865d42c46692 86 + (buf[2] << 16) + (buf[3] << 24);
jeffknaggs 0:865d42c46692 87 int stop = buf[4];
jeffknaggs 0:865d42c46692 88 int bits = buf[6];
jeffknaggs 0:865d42c46692 89 int parity = buf[5];
jeffknaggs 0:865d42c46692 90
jeffknaggs 0:865d42c46692 91 lineCodingChanged(baud, bits, parity, stop);
jeffknaggs 0:865d42c46692 92 }
jeffknaggs 0:865d42c46692 93 }
jeffknaggs 0:865d42c46692 94 }
jeffknaggs 0:865d42c46692 95 }
jeffknaggs 0:865d42c46692 96
jeffknaggs 0:865d42c46692 97 // Called in ISR context
jeffknaggs 0:865d42c46692 98 // Set configuration. Return false if the
jeffknaggs 0:865d42c46692 99 // configuration is not supported.
jeffknaggs 0:865d42c46692 100 bool USBCDC::USBCallback_setConfiguration(uint8_t configuration) {
jeffknaggs 0:865d42c46692 101 if (configuration != DEFAULT_CONFIGURATION) {
jeffknaggs 0:865d42c46692 102 return false;
jeffknaggs 0:865d42c46692 103 }
jeffknaggs 0:865d42c46692 104
jeffknaggs 0:865d42c46692 105 // Configure endpoints > 0
jeffknaggs 0:865d42c46692 106 addEndpoint(EPINT_IN, MAX_PACKET_SIZE_EPINT);
jeffknaggs 0:865d42c46692 107 addEndpoint(EPBULK_IN, MAX_PACKET_SIZE_EPBULK);
jeffknaggs 0:865d42c46692 108 addEndpoint(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);
jeffknaggs 0:865d42c46692 109
jeffknaggs 0:865d42c46692 110 // We activate the endpoint to be able to recceive data
jeffknaggs 0:865d42c46692 111 readStart(EPBULK_OUT, MAX_PACKET_SIZE_EPBULK);
jeffknaggs 0:865d42c46692 112 return true;
jeffknaggs 0:865d42c46692 113 }
jeffknaggs 0:865d42c46692 114
jeffknaggs 0:865d42c46692 115 bool USBCDC::send(uint8_t * buffer, uint32_t size) {
jeffknaggs 0:865d42c46692 116 return USBDevice::write(EPBULK_IN, buffer, size, MAX_CDC_REPORT_SIZE);
jeffknaggs 0:865d42c46692 117 }
jeffknaggs 0:865d42c46692 118
jeffknaggs 0:865d42c46692 119 bool USBCDC::readEP(uint8_t * buffer, uint32_t * size) {
jeffknaggs 0:865d42c46692 120 if (!USBDevice::readEP(EPBULK_OUT, buffer, size, MAX_CDC_REPORT_SIZE))
jeffknaggs 0:865d42c46692 121 return false;
jeffknaggs 0:865d42c46692 122 if (!readStart(EPBULK_OUT, MAX_CDC_REPORT_SIZE))
jeffknaggs 0:865d42c46692 123 return false;
jeffknaggs 0:865d42c46692 124 return true;
jeffknaggs 0:865d42c46692 125 }
jeffknaggs 0:865d42c46692 126
jeffknaggs 0:865d42c46692 127 bool USBCDC::readEP_NB(uint8_t * buffer, uint32_t * size) {
jeffknaggs 0:865d42c46692 128 if (!USBDevice::readEP_NB(EPBULK_OUT, buffer, size, MAX_CDC_REPORT_SIZE))
jeffknaggs 0:865d42c46692 129 return false;
jeffknaggs 0:865d42c46692 130 if (!readStart(EPBULK_OUT, MAX_CDC_REPORT_SIZE))
jeffknaggs 0:865d42c46692 131 return false;
jeffknaggs 0:865d42c46692 132 return true;
jeffknaggs 0:865d42c46692 133 }
jeffknaggs 0:865d42c46692 134
jeffknaggs 0:865d42c46692 135
jeffknaggs 0:865d42c46692 136 uint8_t * USBCDC::deviceDesc() {
jeffknaggs 0:865d42c46692 137 static uint8_t deviceDescriptor[] = {
jeffknaggs 0:865d42c46692 138 18, // bLength
jeffknaggs 0:865d42c46692 139 1, // bDescriptorType
jeffknaggs 0:865d42c46692 140 0x10, 0x01, // bcdUSB
jeffknaggs 0:865d42c46692 141 2, // bDeviceClass
jeffknaggs 0:865d42c46692 142 0, // bDeviceSubClass
jeffknaggs 0:865d42c46692 143 0, // bDeviceProtocol
jeffknaggs 0:865d42c46692 144 MAX_PACKET_SIZE_EP0, // bMaxPacketSize0
jeffknaggs 0:865d42c46692 145 (uint8_t)(LSB(VENDOR_ID)), (uint8_t)(MSB(VENDOR_ID)), // idVendor
jeffknaggs 0:865d42c46692 146 (uint8_t)(LSB(PRODUCT_ID)), (uint8_t)(MSB(PRODUCT_ID)),// idProduct
jeffknaggs 0:865d42c46692 147 0x00, 0x01, // bcdDevice
jeffknaggs 0:865d42c46692 148 1, // iManufacturer
jeffknaggs 0:865d42c46692 149 2, // iProduct
jeffknaggs 0:865d42c46692 150 3, // iSerialNumber
jeffknaggs 0:865d42c46692 151 1 // bNumConfigurations
jeffknaggs 0:865d42c46692 152 };
jeffknaggs 0:865d42c46692 153 return deviceDescriptor;
jeffknaggs 0:865d42c46692 154 }
jeffknaggs 0:865d42c46692 155
jeffknaggs 0:865d42c46692 156 uint8_t * USBCDC::stringIinterfaceDesc() {
jeffknaggs 0:865d42c46692 157 static uint8_t stringIinterfaceDescriptor[] = {
jeffknaggs 0:865d42c46692 158 0x08,
jeffknaggs 0:865d42c46692 159 STRING_DESCRIPTOR,
jeffknaggs 0:865d42c46692 160 'C',0,'D',0,'C',0,
jeffknaggs 0:865d42c46692 161 };
jeffknaggs 0:865d42c46692 162 return stringIinterfaceDescriptor;
jeffknaggs 0:865d42c46692 163 }
jeffknaggs 0:865d42c46692 164
jeffknaggs 0:865d42c46692 165 uint8_t * USBCDC::stringIproductDesc() {
jeffknaggs 0:865d42c46692 166 static uint8_t stringIproductDescriptor[] = {
jeffknaggs 0:865d42c46692 167 0x16,
jeffknaggs 0:865d42c46692 168 STRING_DESCRIPTOR,
jeffknaggs 0:865d42c46692 169 'C',0,'D',0,'C',0,' ',0,'D',0,'E',0,'V',0,'I',0,'C',0,'E',0
jeffknaggs 0:865d42c46692 170 };
jeffknaggs 0:865d42c46692 171 return stringIproductDescriptor;
jeffknaggs 0:865d42c46692 172 }
jeffknaggs 0:865d42c46692 173
jeffknaggs 0:865d42c46692 174
jeffknaggs 0:865d42c46692 175 #define CONFIG1_DESC_SIZE (9+8+9+5+5+4+5+7+9+7+7)
jeffknaggs 0:865d42c46692 176
jeffknaggs 0:865d42c46692 177 uint8_t * USBCDC::configurationDesc() {
jeffknaggs 0:865d42c46692 178 static uint8_t configDescriptor[] = {
jeffknaggs 0:865d42c46692 179 // configuration descriptor
jeffknaggs 0:865d42c46692 180 9, // bLength
jeffknaggs 0:865d42c46692 181 2, // bDescriptorType
jeffknaggs 0:865d42c46692 182 LSB(CONFIG1_DESC_SIZE), // wTotalLength
jeffknaggs 0:865d42c46692 183 MSB(CONFIG1_DESC_SIZE),
jeffknaggs 0:865d42c46692 184 2, // bNumInterfaces
jeffknaggs 0:865d42c46692 185 1, // bConfigurationValue
jeffknaggs 0:865d42c46692 186 0, // iConfiguration
jeffknaggs 0:865d42c46692 187 0x80, // bmAttributes
jeffknaggs 0:865d42c46692 188 50, // bMaxPower
jeffknaggs 0:865d42c46692 189
jeffknaggs 0:865d42c46692 190 // IAD to associate the two CDC interfaces
jeffknaggs 0:865d42c46692 191 0x08, // bLength
jeffknaggs 0:865d42c46692 192 0x0b, // bDescriptorType
jeffknaggs 0:865d42c46692 193 0x00, // bFirstInterface
jeffknaggs 0:865d42c46692 194 0x02, // bInterfaceCount
jeffknaggs 0:865d42c46692 195 0x02, // bFunctionClass
jeffknaggs 0:865d42c46692 196 0x02, // bFunctionSubClass
jeffknaggs 0:865d42c46692 197 0, // bFunctionProtocol
jeffknaggs 0:865d42c46692 198 0, // iFunction
jeffknaggs 0:865d42c46692 199
jeffknaggs 0:865d42c46692 200 // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
jeffknaggs 0:865d42c46692 201 9, // bLength
jeffknaggs 0:865d42c46692 202 4, // bDescriptorType
jeffknaggs 0:865d42c46692 203 0, // bInterfaceNumber
jeffknaggs 0:865d42c46692 204 0, // bAlternateSetting
jeffknaggs 0:865d42c46692 205 1, // bNumEndpoints
jeffknaggs 0:865d42c46692 206 0x02, // bInterfaceClass
jeffknaggs 0:865d42c46692 207 0x02, // bInterfaceSubClass
jeffknaggs 0:865d42c46692 208 0x01, // bInterfaceProtocol
jeffknaggs 0:865d42c46692 209 0, // iInterface
jeffknaggs 0:865d42c46692 210
jeffknaggs 0:865d42c46692 211 // CDC Header Functional Descriptor, CDC Spec 5.2.3.1, Table 26
jeffknaggs 0:865d42c46692 212 5, // bFunctionLength
jeffknaggs 0:865d42c46692 213 0x24, // bDescriptorType
jeffknaggs 0:865d42c46692 214 0x00, // bDescriptorSubtype
jeffknaggs 0:865d42c46692 215 0x10, 0x01, // bcdCDC
jeffknaggs 0:865d42c46692 216
jeffknaggs 0:865d42c46692 217 // Call Management Functional Descriptor, CDC Spec 5.2.3.2, Table 27
jeffknaggs 0:865d42c46692 218 5, // bFunctionLength
jeffknaggs 0:865d42c46692 219 0x24, // bDescriptorType
jeffknaggs 0:865d42c46692 220 0x01, // bDescriptorSubtype
jeffknaggs 0:865d42c46692 221 0x03, // bmCapabilities
jeffknaggs 0:865d42c46692 222 1, // bDataInterface
jeffknaggs 0:865d42c46692 223
jeffknaggs 0:865d42c46692 224 // Abstract Control Management Functional Descriptor, CDC Spec 5.2.3.3, Table 28
jeffknaggs 0:865d42c46692 225 4, // bFunctionLength
jeffknaggs 0:865d42c46692 226 0x24, // bDescriptorType
jeffknaggs 0:865d42c46692 227 0x02, // bDescriptorSubtype
jeffknaggs 0:865d42c46692 228 0x06, // bmCapabilities
jeffknaggs 0:865d42c46692 229
jeffknaggs 0:865d42c46692 230 // Union Functional Descriptor, CDC Spec 5.2.3.8, Table 33
jeffknaggs 0:865d42c46692 231 5, // bFunctionLength
jeffknaggs 0:865d42c46692 232 0x24, // bDescriptorType
jeffknaggs 0:865d42c46692 233 0x06, // bDescriptorSubtype
jeffknaggs 0:865d42c46692 234 0, // bMasterInterface
jeffknaggs 0:865d42c46692 235 1, // bSlaveInterface0
jeffknaggs 0:865d42c46692 236
jeffknaggs 0:865d42c46692 237 // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
jeffknaggs 0:865d42c46692 238 ENDPOINT_DESCRIPTOR_LENGTH, // bLength
jeffknaggs 0:865d42c46692 239 ENDPOINT_DESCRIPTOR, // bDescriptorType
jeffknaggs 0:865d42c46692 240 PHY_TO_DESC(EPINT_IN), // bEndpointAddress
jeffknaggs 0:865d42c46692 241 E_INTERRUPT, // bmAttributes (0x03=intr)
jeffknaggs 0:865d42c46692 242 LSB(MAX_PACKET_SIZE_EPINT), // wMaxPacketSize (LSB)
jeffknaggs 0:865d42c46692 243 MSB(MAX_PACKET_SIZE_EPINT), // wMaxPacketSize (MSB)
jeffknaggs 0:865d42c46692 244 16, // bInterval
jeffknaggs 0:865d42c46692 245
jeffknaggs 0:865d42c46692 246
jeffknaggs 0:865d42c46692 247
jeffknaggs 0:865d42c46692 248
jeffknaggs 0:865d42c46692 249 // interface descriptor, USB spec 9.6.5, page 267-269, Table 9-12
jeffknaggs 0:865d42c46692 250 9, // bLength
jeffknaggs 0:865d42c46692 251 4, // bDescriptorType
jeffknaggs 0:865d42c46692 252 1, // bInterfaceNumber
jeffknaggs 0:865d42c46692 253 0, // bAlternateSetting
jeffknaggs 0:865d42c46692 254 2, // bNumEndpoints
jeffknaggs 0:865d42c46692 255 0x0A, // bInterfaceClass
jeffknaggs 0:865d42c46692 256 0x00, // bInterfaceSubClass
jeffknaggs 0:865d42c46692 257 0x00, // bInterfaceProtocol
jeffknaggs 0:865d42c46692 258 0, // iInterface
jeffknaggs 0:865d42c46692 259
jeffknaggs 0:865d42c46692 260 // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
jeffknaggs 0:865d42c46692 261 ENDPOINT_DESCRIPTOR_LENGTH, // bLength
jeffknaggs 0:865d42c46692 262 ENDPOINT_DESCRIPTOR, // bDescriptorType
jeffknaggs 0:865d42c46692 263 PHY_TO_DESC(EPBULK_IN), // bEndpointAddress
jeffknaggs 0:865d42c46692 264 E_BULK, // bmAttributes (0x02=bulk)
jeffknaggs 0:865d42c46692 265 LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB)
jeffknaggs 0:865d42c46692 266 MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB)
jeffknaggs 0:865d42c46692 267 0, // bInterval
jeffknaggs 0:865d42c46692 268
jeffknaggs 0:865d42c46692 269 // endpoint descriptor, USB spec 9.6.6, page 269-271, Table 9-13
jeffknaggs 0:865d42c46692 270 ENDPOINT_DESCRIPTOR_LENGTH, // bLength
jeffknaggs 0:865d42c46692 271 ENDPOINT_DESCRIPTOR, // bDescriptorType
jeffknaggs 0:865d42c46692 272 PHY_TO_DESC(EPBULK_OUT), // bEndpointAddress
jeffknaggs 0:865d42c46692 273 E_BULK, // bmAttributes (0x02=bulk)
jeffknaggs 0:865d42c46692 274 LSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (LSB)
jeffknaggs 0:865d42c46692 275 MSB(MAX_PACKET_SIZE_EPBULK),// wMaxPacketSize (MSB)
jeffknaggs 0:865d42c46692 276 0 // bInterval
jeffknaggs 0:865d42c46692 277 };
jeffknaggs 0:865d42c46692 278 return configDescriptor;
jeffknaggs 0:865d42c46692 279 }