Version of http://mbed.org/cookbook/NetServicesTribute with setting set the same for LPC2368

Dependents:   UDPSocketExample 24LCxx_I2CApp WeatherPlatform_pachube HvZServerLib ... more

Committer:
simon
Date:
Tue Nov 23 14:15:36 2010 +0000
Revision:
0:350011bf8be7
Experimental version for testing UDP

Who changed what in which revision?

UserRevisionLine numberNew contents of line
simon 0:350011bf8be7 1
simon 0:350011bf8be7 2 /*
simon 0:350011bf8be7 3 Copyright (c) 2010 Donatien Garnier (donatiengar [at] gmail [dot] com)
simon 0:350011bf8be7 4
simon 0:350011bf8be7 5 Permission is hereby granted, free of charge, to any person obtaining a copy
simon 0:350011bf8be7 6 of this software and associated documentation files (the "Software"), to deal
simon 0:350011bf8be7 7 in the Software without restriction, including without limitation the rights
simon 0:350011bf8be7 8 to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
simon 0:350011bf8be7 9 copies of the Software, and to permit persons to whom the Software is
simon 0:350011bf8be7 10 furnished to do so, subject to the following conditions:
simon 0:350011bf8be7 11
simon 0:350011bf8be7 12 The above copyright notice and this permission notice shall be included in
simon 0:350011bf8be7 13 all copies or substantial portions of the Software.
simon 0:350011bf8be7 14
simon 0:350011bf8be7 15 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
simon 0:350011bf8be7 16 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
simon 0:350011bf8be7 17 FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
simon 0:350011bf8be7 18 AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
simon 0:350011bf8be7 19 LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
simon 0:350011bf8be7 20 OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
simon 0:350011bf8be7 21 THE SOFTWARE.
simon 0:350011bf8be7 22 */
simon 0:350011bf8be7 23
simon 0:350011bf8be7 24 #include "UsbDevice.h"
simon 0:350011bf8be7 25
simon 0:350011bf8be7 26 #include "netCfg.h"
simon 0:350011bf8be7 27 #if NET_USB
simon 0:350011bf8be7 28
simon 0:350011bf8be7 29 //#define __DEBUG
simon 0:350011bf8be7 30 #include "dbg/dbg.h"
simon 0:350011bf8be7 31
simon 0:350011bf8be7 32 UsbDevice::UsbDevice( UsbHostMgr* pMgr, int hub, int port, int addr ) : m_pControlEp(NULL), /*m_controlEp( this, 0x00, false, USB_CONTROL, 8 ),*/
simon 0:350011bf8be7 33 m_pMgr(pMgr), m_connected(false), m_enumerated(false), m_hub(hub), m_port(port), m_addr(addr), m_refs(0),
simon 0:350011bf8be7 34 m_vid(0), m_pid(0)
simon 0:350011bf8be7 35 {
simon 0:350011bf8be7 36
simon 0:350011bf8be7 37 }
simon 0:350011bf8be7 38
simon 0:350011bf8be7 39 UsbDevice::~UsbDevice()
simon 0:350011bf8be7 40 {
simon 0:350011bf8be7 41 if(m_pControlEp)
simon 0:350011bf8be7 42 delete m_pControlEp;
simon 0:350011bf8be7 43 }
simon 0:350011bf8be7 44
simon 0:350011bf8be7 45 UsbErr UsbDevice::enumerate()
simon 0:350011bf8be7 46 {
simon 0:350011bf8be7 47 // USB_INT32S rc;
simon 0:350011bf8be7 48
simon 0:350011bf8be7 49 UsbErr rc;
simon 0:350011bf8be7 50
simon 0:350011bf8be7 51 DBG("Starting enumeration (m_pMgr = %p)\n", m_pMgr);
simon 0:350011bf8be7 52
simon 0:350011bf8be7 53 #if 1
simon 0:350011bf8be7 54 m_pMgr->resetPort(m_hub, m_port);
simon 0:350011bf8be7 55 #else
simon 0:350011bf8be7 56 wait_ms(100); /* USB 2.0 spec says atleast 50ms delay beore port reset */
simon 0:350011bf8be7 57 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRS; // Initiate port reset
simon 0:350011bf8be7 58 while (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_PRS)
simon 0:350011bf8be7 59 __WFI(); // Wait for port reset to complete...
simon 0:350011bf8be7 60 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC; // ...and clear port reset signal
simon 0:350011bf8be7 61 wait_ms(200); /* Wait for 100 MS after port reset */
simon 0:350011bf8be7 62 #endif
simon 0:350011bf8be7 63
simon 0:350011bf8be7 64 DBG("Port reset\n");
simon 0:350011bf8be7 65
simon 0:350011bf8be7 66 wait_ms(200);
simon 0:350011bf8be7 67
simon 0:350011bf8be7 68 m_pControlEp = new UsbEndpoint( this, 0x00, false, USB_CONTROL, 8, 0 );
simon 0:350011bf8be7 69
simon 0:350011bf8be7 70 //EDCtrl->Control = 8 << 16;/* Put max pkt size = 8 */
simon 0:350011bf8be7 71 /* Read first 8 bytes of device desc */
simon 0:350011bf8be7 72 rc = controlReceive(USB_DEVICE_TO_HOST | USB_RECIPIENT_DEVICE, GET_DESCRIPTOR, (USB_DESCRIPTOR_TYPE_DEVICE << 8)|(0), 0, m_controlDataBuf, 8);
simon 0:350011bf8be7 73 if (rc)
simon 0:350011bf8be7 74 {
simon 0:350011bf8be7 75 DBG("RC=%d",rc);
simon 0:350011bf8be7 76 return (rc);
simon 0:350011bf8be7 77 }
simon 0:350011bf8be7 78
simon 0:350011bf8be7 79 DBG("Got descriptor, max ep size is %d\n", m_controlDataBuf[7]);
simon 0:350011bf8be7 80
simon 0:350011bf8be7 81 m_pControlEp->updateSize(m_controlDataBuf[7]); /* Get max pkt size of endpoint 0 */
simon 0:350011bf8be7 82 rc = controlSend(USB_HOST_TO_DEVICE | USB_RECIPIENT_DEVICE, SET_ADDRESS, m_addr, 0, NULL, 0); /* Set the device address to m_addr */
simon 0:350011bf8be7 83 if (rc)
simon 0:350011bf8be7 84 {
simon 0:350011bf8be7 85 // PRINT_Err(rc);
simon 0:350011bf8be7 86 return (rc);
simon 0:350011bf8be7 87 }
simon 0:350011bf8be7 88 wait_ms(2);
simon 0:350011bf8be7 89 //EDCtrl->Control = (EDCtrl->Control) | 1; /* Modify control pipe with address 1 */
simon 0:350011bf8be7 90
simon 0:350011bf8be7 91 //Update address
simon 0:350011bf8be7 92 m_pControlEp->updateAddr(m_addr);
simon 0:350011bf8be7 93 DBG("Ep addr is now %d", m_addr);
simon 0:350011bf8be7 94 /**/
simon 0:350011bf8be7 95
simon 0:350011bf8be7 96 //rc = HOST_GET_DESCRIPTOR(USB_DESCRIPTOR_TYPE_DEVICE, 0, TDBuffer, 17); //Read full device descriptor
simon 0:350011bf8be7 97 rc = controlReceive(USB_DEVICE_TO_HOST | USB_RECIPIENT_DEVICE, GET_DESCRIPTOR, (USB_DESCRIPTOR_TYPE_DEVICE << 8)|(0), 0, m_controlDataBuf, 17);
simon 0:350011bf8be7 98 if (rc)
simon 0:350011bf8be7 99 {
simon 0:350011bf8be7 100 //PRINT_Err(rc);
simon 0:350011bf8be7 101 return (rc);
simon 0:350011bf8be7 102 }
simon 0:350011bf8be7 103 /*
simon 0:350011bf8be7 104 rc = SerialCheckVidPid();
simon 0:350011bf8be7 105 if (rc != OK) {
simon 0:350011bf8be7 106 PRINT_Err(rc);
simon 0:350011bf8be7 107 return (rc);
simon 0:350011bf8be7 108 }
simon 0:350011bf8be7 109 */
simon 0:350011bf8be7 110 /**/
simon 0:350011bf8be7 111
simon 0:350011bf8be7 112 m_vid = *((uint16_t*)&m_controlDataBuf[8]);
simon 0:350011bf8be7 113 m_pid = *((uint16_t*)&m_controlDataBuf[10]);
simon 0:350011bf8be7 114
simon 0:350011bf8be7 115 DBG("VID: %02x, PID: %02x\n", m_vid, m_pid);
simon 0:350011bf8be7 116 /* Get the configuration descriptor */
simon 0:350011bf8be7 117 //rc = HOST_GET_DESCRIPTOR(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, TDBuffer, 9);
simon 0:350011bf8be7 118 rc = controlReceive(USB_DEVICE_TO_HOST | USB_RECIPIENT_DEVICE, GET_DESCRIPTOR, (USB_DESCRIPTOR_TYPE_CONFIGURATION << 8)|(0), 0, m_controlDataBuf, 9);
simon 0:350011bf8be7 119 if (rc)
simon 0:350011bf8be7 120 {
simon 0:350011bf8be7 121 //PRINT_Err(rc);
simon 0:350011bf8be7 122 return (rc);
simon 0:350011bf8be7 123 }
simon 0:350011bf8be7 124 /* Get the first configuration data */
simon 0:350011bf8be7 125 //rc = HOST_GET_DESCRIPTOR(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, TDBuffer, *((uint16_t*)&TDBuffer[2]));
simon 0:350011bf8be7 126 rc = controlReceive(USB_DEVICE_TO_HOST | USB_RECIPIENT_DEVICE, GET_DESCRIPTOR, (USB_DESCRIPTOR_TYPE_CONFIGURATION << 8)|(0), 0, m_controlDataBuf, *((uint16_t*)&m_controlDataBuf[2]));
simon 0:350011bf8be7 127 if (rc)
simon 0:350011bf8be7 128 {
simon 0:350011bf8be7 129 //PRINT_Err(rc);
simon 0:350011bf8be7 130 return (rc);
simon 0:350011bf8be7 131 }
simon 0:350011bf8be7 132
simon 0:350011bf8be7 133 DBG("Desc len is %d\n", *((uint16_t*)&m_controlDataBuf[2]));
simon 0:350011bf8be7 134
simon 0:350011bf8be7 135 DBG("Set configuration\n");
simon 0:350011bf8be7 136
simon 0:350011bf8be7 137 //rc = USBH_SET_CONFIGURATION(1);/* Select device configuration 1 */
simon 0:350011bf8be7 138 rc = controlSend(USB_HOST_TO_DEVICE | USB_RECIPIENT_DEVICE, SET_CONFIGURATION, 1, 0, NULL, 0);
simon 0:350011bf8be7 139 if (rc)
simon 0:350011bf8be7 140 {
simon 0:350011bf8be7 141 // PRINT_Err(rc);
simon 0:350011bf8be7 142 return rc;
simon 0:350011bf8be7 143 }
simon 0:350011bf8be7 144 wait_ms(100);/* Some devices may require this delay */
simon 0:350011bf8be7 145
simon 0:350011bf8be7 146 m_enumerated = true;
simon 0:350011bf8be7 147 return USBERR_OK;
simon 0:350011bf8be7 148 }
simon 0:350011bf8be7 149
simon 0:350011bf8be7 150 bool UsbDevice::connected()
simon 0:350011bf8be7 151 {
simon 0:350011bf8be7 152 return m_connected;
simon 0:350011bf8be7 153 }
simon 0:350011bf8be7 154
simon 0:350011bf8be7 155 bool UsbDevice::enumerated()
simon 0:350011bf8be7 156 {
simon 0:350011bf8be7 157 return m_enumerated;
simon 0:350011bf8be7 158 }
simon 0:350011bf8be7 159
simon 0:350011bf8be7 160 int UsbDevice::getPid()
simon 0:350011bf8be7 161 {
simon 0:350011bf8be7 162 return m_pid;
simon 0:350011bf8be7 163 }
simon 0:350011bf8be7 164
simon 0:350011bf8be7 165 int UsbDevice::getVid()
simon 0:350011bf8be7 166 {
simon 0:350011bf8be7 167 return m_vid;
simon 0:350011bf8be7 168 }
simon 0:350011bf8be7 169
simon 0:350011bf8be7 170 UsbErr UsbDevice::getConfigurationDescriptor(int config, uint8_t** pBuf)
simon 0:350011bf8be7 171 {
simon 0:350011bf8be7 172 //For now olny one config
simon 0:350011bf8be7 173 *pBuf = m_controlDataBuf;
simon 0:350011bf8be7 174 return USBERR_OK;
simon 0:350011bf8be7 175 }
simon 0:350011bf8be7 176
simon 0:350011bf8be7 177 UsbErr UsbDevice::getInterfaceDescriptor(int config, int item, uint8_t** pBuf)
simon 0:350011bf8be7 178 {
simon 0:350011bf8be7 179 byte* desc_ptr = m_controlDataBuf;
simon 0:350011bf8be7 180
simon 0:350011bf8be7 181 /* if (desc_ptr[1] != USB_DESCRIPTOR_TYPE_CONFIGURATION)
simon 0:350011bf8be7 182 {
simon 0:350011bf8be7 183 return USBERR_BADCONFIG;
simon 0:350011bf8be7 184 }*/
simon 0:350011bf8be7 185
simon 0:350011bf8be7 186 if(item>=m_controlDataBuf[4])//Interfaces count
simon 0:350011bf8be7 187 return USBERR_NOTFOUND;
simon 0:350011bf8be7 188
simon 0:350011bf8be7 189 desc_ptr += desc_ptr[0];
simon 0:350011bf8be7 190
simon 0:350011bf8be7 191 *pBuf = NULL;
simon 0:350011bf8be7 192
simon 0:350011bf8be7 193 while (desc_ptr < m_controlDataBuf + *((uint16_t*)&m_controlDataBuf[2]))
simon 0:350011bf8be7 194 {
simon 0:350011bf8be7 195
simon 0:350011bf8be7 196 switch (desc_ptr[1]) {
simon 0:350011bf8be7 197 case USB_DESCRIPTOR_TYPE_INTERFACE:
simon 0:350011bf8be7 198 if(desc_ptr[2] == item)
simon 0:350011bf8be7 199 {
simon 0:350011bf8be7 200 *pBuf = desc_ptr;
simon 0:350011bf8be7 201 return USBERR_OK;
simon 0:350011bf8be7 202 }
simon 0:350011bf8be7 203 desc_ptr += desc_ptr[0]; // Move to next descriptor start
simon 0:350011bf8be7 204 break;
simon 0:350011bf8be7 205 }
simon 0:350011bf8be7 206
simon 0:350011bf8be7 207 }
simon 0:350011bf8be7 208
simon 0:350011bf8be7 209 if(*pBuf == NULL)
simon 0:350011bf8be7 210 return USBERR_NOTFOUND;
simon 0:350011bf8be7 211
simon 0:350011bf8be7 212 return USBERR_OK;
simon 0:350011bf8be7 213 }
simon 0:350011bf8be7 214
simon 0:350011bf8be7 215
simon 0:350011bf8be7 216 UsbErr UsbDevice::setConfiguration(int config)
simon 0:350011bf8be7 217 {
simon 0:350011bf8be7 218 return USBERR_OK;
simon 0:350011bf8be7 219 }
simon 0:350011bf8be7 220
simon 0:350011bf8be7 221 UsbErr UsbDevice::controlSend(byte requestType, byte request, word value, word index, const byte* buf, int len)
simon 0:350011bf8be7 222 {
simon 0:350011bf8be7 223 UsbErr rc;
simon 0:350011bf8be7 224 fillControlBuf(requestType, request, value, index, len);
simon 0:350011bf8be7 225 m_pControlEp->setNextToken(TD_SETUP);
simon 0:350011bf8be7 226 rc = m_pControlEp->transfer(m_controlBuf, 8);
simon 0:350011bf8be7 227 while(m_pControlEp->status() == USBERR_PROCESSING);
simon 0:350011bf8be7 228 rc = (UsbErr) MIN(0, m_pControlEp->status());
simon 0:350011bf8be7 229 if(rc)
simon 0:350011bf8be7 230 return rc;
simon 0:350011bf8be7 231 if(len)
simon 0:350011bf8be7 232 {
simon 0:350011bf8be7 233 m_pControlEp->setNextToken(TD_OUT);
simon 0:350011bf8be7 234 rc = m_pControlEp->transfer((byte*)buf, len);
simon 0:350011bf8be7 235 while(m_pControlEp->status() == USBERR_PROCESSING);
simon 0:350011bf8be7 236 rc = (UsbErr) MIN(0, m_pControlEp->status());
simon 0:350011bf8be7 237 if(rc)
simon 0:350011bf8be7 238 return rc;
simon 0:350011bf8be7 239 }
simon 0:350011bf8be7 240 m_pControlEp->setNextToken(TD_IN);
simon 0:350011bf8be7 241 rc = m_pControlEp->transfer(NULL, 0);
simon 0:350011bf8be7 242 while(m_pControlEp->status() == USBERR_PROCESSING);
simon 0:350011bf8be7 243 rc = (UsbErr) MIN(0, m_pControlEp->status());
simon 0:350011bf8be7 244 if(rc)
simon 0:350011bf8be7 245 return rc;
simon 0:350011bf8be7 246 return USBERR_OK;
simon 0:350011bf8be7 247 }
simon 0:350011bf8be7 248
simon 0:350011bf8be7 249 UsbErr UsbDevice::controlReceive(byte requestType, byte request, word value, word index, const byte* buf, int len)
simon 0:350011bf8be7 250 {
simon 0:350011bf8be7 251 UsbErr rc;
simon 0:350011bf8be7 252 fillControlBuf(requestType, request, value, index, len);
simon 0:350011bf8be7 253 m_pControlEp->setNextToken(TD_SETUP);
simon 0:350011bf8be7 254 rc = m_pControlEp->transfer(m_controlBuf, 8);
simon 0:350011bf8be7 255 while(m_pControlEp->status() == USBERR_PROCESSING);
simon 0:350011bf8be7 256 rc = (UsbErr) MIN(0, m_pControlEp->status());
simon 0:350011bf8be7 257 if(rc)
simon 0:350011bf8be7 258 return rc;
simon 0:350011bf8be7 259 if(len)
simon 0:350011bf8be7 260 {
simon 0:350011bf8be7 261 m_pControlEp->setNextToken(TD_IN);
simon 0:350011bf8be7 262 rc = m_pControlEp->transfer( (byte*) buf, len);
simon 0:350011bf8be7 263 while(m_pControlEp->status() == USBERR_PROCESSING);
simon 0:350011bf8be7 264 rc = (UsbErr) MIN(0, m_pControlEp->status());
simon 0:350011bf8be7 265 if(rc)
simon 0:350011bf8be7 266 return rc;
simon 0:350011bf8be7 267 }
simon 0:350011bf8be7 268 m_pControlEp->setNextToken(TD_OUT);
simon 0:350011bf8be7 269 rc = m_pControlEp->transfer(NULL, 0);
simon 0:350011bf8be7 270 while(m_pControlEp->status() == USBERR_PROCESSING);
simon 0:350011bf8be7 271 rc = (UsbErr) MIN(0, m_pControlEp->status());
simon 0:350011bf8be7 272 if(rc)
simon 0:350011bf8be7 273 return rc;
simon 0:350011bf8be7 274 return USBERR_OK;
simon 0:350011bf8be7 275 }
simon 0:350011bf8be7 276
simon 0:350011bf8be7 277 void UsbDevice::fillControlBuf(byte requestType, byte request, word value, word index, int len)
simon 0:350011bf8be7 278 {
simon 0:350011bf8be7 279 #ifdef __BIG_ENDIAN
simon 0:350011bf8be7 280 #error "Must implement BE to LE conv here"
simon 0:350011bf8be7 281 #endif
simon 0:350011bf8be7 282 m_controlBuf[0] = requestType;
simon 0:350011bf8be7 283 m_controlBuf[1] = request;
simon 0:350011bf8be7 284 //We are in LE so it's fine
simon 0:350011bf8be7 285 *((word*)&m_controlBuf[2]) = value;
simon 0:350011bf8be7 286 *((word*)&m_controlBuf[4]) = index;
simon 0:350011bf8be7 287 *((word*)&m_controlBuf[6]) = (word) len;
simon 0:350011bf8be7 288 }
simon 0:350011bf8be7 289
simon 0:350011bf8be7 290
simon 0:350011bf8be7 291 #endif