Dependencies:   FATFileSystem

Committer:
nhiro3303
Date:
Tue Aug 22 06:18:15 2017 +0000
Revision:
0:42b8e1bc6235
ps3 test library

Who changed what in which revision?

UserRevisionLine numberNew contents of line
nhiro3303 0:42b8e1bc6235 1 /* mbed USBHost Library
nhiro3303 0:42b8e1bc6235 2 * Copyright (c) 2006-2013 ARM Limited
nhiro3303 0:42b8e1bc6235 3 *
nhiro3303 0:42b8e1bc6235 4 * Licensed under the Apache License, Version 2.0 (the "License");
nhiro3303 0:42b8e1bc6235 5 * you may not use this file except in compliance with the License.
nhiro3303 0:42b8e1bc6235 6 * You may obtain a copy of the License at
nhiro3303 0:42b8e1bc6235 7 *
nhiro3303 0:42b8e1bc6235 8 * http://www.apache.org/licenses/LICENSE-2.0
nhiro3303 0:42b8e1bc6235 9 *
nhiro3303 0:42b8e1bc6235 10 * Unless required by applicable law or agreed to in writing, software
nhiro3303 0:42b8e1bc6235 11 * distributed under the License is distributed on an "AS IS" BASIS,
nhiro3303 0:42b8e1bc6235 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
nhiro3303 0:42b8e1bc6235 13 * See the License for the specific language governing permissions and
nhiro3303 0:42b8e1bc6235 14 * limitations under the License.
nhiro3303 0:42b8e1bc6235 15 */
nhiro3303 0:42b8e1bc6235 16
nhiro3303 0:42b8e1bc6235 17 #if defined(TARGET_LPC4088)||defined(TARGET_LPC1768)
nhiro3303 0:42b8e1bc6235 18 #include "USBHALHost.h"
nhiro3303 0:42b8e1bc6235 19
nhiro3303 0:42b8e1bc6235 20 #ifndef CTASSERT
nhiro3303 0:42b8e1bc6235 21 template <bool>struct CtAssert;
nhiro3303 0:42b8e1bc6235 22 template <>struct CtAssert<true> {};
nhiro3303 0:42b8e1bc6235 23 #define CTASSERT(A) CtAssert<A>();
nhiro3303 0:42b8e1bc6235 24 #endif
nhiro3303 0:42b8e1bc6235 25
nhiro3303 0:42b8e1bc6235 26 #ifdef _USB_DBG
nhiro3303 0:42b8e1bc6235 27 #define USB_DBG(...) do{fprintf(stderr,"[%s@%d] ",__PRETTY_FUNCTION__,__LINE__);fprintf(stderr,__VA_ARGS__);fprintf(stderr,"\n");} while(0);
nhiro3303 0:42b8e1bc6235 28 #define USB_DBG_HEX(A,B) debug_hex(A,B)
nhiro3303 0:42b8e1bc6235 29 #define USB_DBG_ED(A) while(0)
nhiro3303 0:42b8e1bc6235 30 #define USB_DBG_TD(A) while(0)
nhiro3303 0:42b8e1bc6235 31 #define USB_DBG_ED_IF(A,B) while(0)
nhiro3303 0:42b8e1bc6235 32 void debug_hex(uint8_t* buf, int size);
nhiro3303 0:42b8e1bc6235 33 #else
nhiro3303 0:42b8e1bc6235 34 #define USB_DBG(...) while(0)
nhiro3303 0:42b8e1bc6235 35 #define USB_DBG_ED(A) while(0)
nhiro3303 0:42b8e1bc6235 36 #define USB_DBG_TD(A) while(0)
nhiro3303 0:42b8e1bc6235 37 #define USB_DBG_ED_IF(A,B) while(0)
nhiro3303 0:42b8e1bc6235 38 #define USB_DBG_HEX(A,B) while(0)
nhiro3303 0:42b8e1bc6235 39 #endif
nhiro3303 0:42b8e1bc6235 40
nhiro3303 0:42b8e1bc6235 41 #define USB_TRACE1(A) while(0)
nhiro3303 0:42b8e1bc6235 42
nhiro3303 0:42b8e1bc6235 43 #ifdef _USB_TEST
nhiro3303 0:42b8e1bc6235 44 #undef USB_TEST_ASSERT
nhiro3303 0:42b8e1bc6235 45 void usb_test_assert_internal(const char *expr, const char *file, int line);
nhiro3303 0:42b8e1bc6235 46 #define USB_TEST_ASSERT(EXPR) while(!(EXPR)){usb_test_assert_internal(#EXPR,__FILE__,__LINE__);}
nhiro3303 0:42b8e1bc6235 47 #else
nhiro3303 0:42b8e1bc6235 48 #define USB_TEST_ASSERT(EXPR) while(0)
nhiro3303 0:42b8e1bc6235 49 #endif
nhiro3303 0:42b8e1bc6235 50
nhiro3303 0:42b8e1bc6235 51 #define USB_INFO(...) do{fprintf(stderr,__VA_ARGS__);fprintf(stderr,"\n");}while(0);
nhiro3303 0:42b8e1bc6235 52
nhiro3303 0:42b8e1bc6235 53 // bits of the USB/OTG clock control register
nhiro3303 0:42b8e1bc6235 54 #define HOST_CLK_EN (1<<0)
nhiro3303 0:42b8e1bc6235 55 #define DEV_CLK_EN (1<<1)
nhiro3303 0:42b8e1bc6235 56 #define PORTSEL_CLK_EN (1<<3)
nhiro3303 0:42b8e1bc6235 57 #define AHB_CLK_EN (1<<4)
nhiro3303 0:42b8e1bc6235 58
nhiro3303 0:42b8e1bc6235 59 // bits of the USB/OTG clock status register
nhiro3303 0:42b8e1bc6235 60 #define HOST_CLK_ON (1<<0)
nhiro3303 0:42b8e1bc6235 61 #define DEV_CLK_ON (1<<1)
nhiro3303 0:42b8e1bc6235 62 #define PORTSEL_CLK_ON (1<<3)
nhiro3303 0:42b8e1bc6235 63 #define AHB_CLK_ON (1<<4)
nhiro3303 0:42b8e1bc6235 64
nhiro3303 0:42b8e1bc6235 65 // we need host clock, OTG/portsel clock and AHB clock
nhiro3303 0:42b8e1bc6235 66 #define CLOCK_MASK (HOST_CLK_EN | PORTSEL_CLK_EN | AHB_CLK_EN)
nhiro3303 0:42b8e1bc6235 67 #define FI 0x2EDF /* 12000 bits per frame (-1) */
nhiro3303 0:42b8e1bc6235 68 #define DEFAULT_FMINTERVAL ((((6 * (FI - 210)) / 7) << 16) | FI)
nhiro3303 0:42b8e1bc6235 69
nhiro3303 0:42b8e1bc6235 70 USBHALHost* USBHALHost::instHost;
nhiro3303 0:42b8e1bc6235 71
nhiro3303 0:42b8e1bc6235 72 USBHALHost::USBHALHost() {
nhiro3303 0:42b8e1bc6235 73 instHost = this;
nhiro3303 0:42b8e1bc6235 74 }
nhiro3303 0:42b8e1bc6235 75
nhiro3303 0:42b8e1bc6235 76 void USBHALHost::init() {
nhiro3303 0:42b8e1bc6235 77 NVIC_DisableIRQ(USB_IRQn);
nhiro3303 0:42b8e1bc6235 78 m_pHcca = new HCCA();
nhiro3303 0:42b8e1bc6235 79 init_hw_ohci(m_pHcca);
nhiro3303 0:42b8e1bc6235 80 ResetRootHub();
nhiro3303 0:42b8e1bc6235 81 NVIC_SetVector(USB_IRQn, (uint32_t)_usbisr);
nhiro3303 0:42b8e1bc6235 82 NVIC_SetPriority(USB_IRQn, 0);
nhiro3303 0:42b8e1bc6235 83 NVIC_EnableIRQ(USB_IRQn);
nhiro3303 0:42b8e1bc6235 84
nhiro3303 0:42b8e1bc6235 85 USB_INFO("Simple USBHost Library for LPC4088/LPC1768");
nhiro3303 0:42b8e1bc6235 86 bool lowSpeed = wait_attach();
nhiro3303 0:42b8e1bc6235 87 addDevice(NULL, 0, lowSpeed);
nhiro3303 0:42b8e1bc6235 88 }
nhiro3303 0:42b8e1bc6235 89
nhiro3303 0:42b8e1bc6235 90 void USBHALHost::init_hw_ohci(HCCA* pHcca) {
nhiro3303 0:42b8e1bc6235 91 LPC_SC->PCONP &= ~(1UL<<31); //Cut power
nhiro3303 0:42b8e1bc6235 92 wait_ms(1000);
nhiro3303 0:42b8e1bc6235 93 LPC_SC->PCONP |= (1UL<<31); // turn on power for USB
nhiro3303 0:42b8e1bc6235 94 LPC_USB->USBClkCtrl |= CLOCK_MASK; // Enable USB host clock, port selection and AHB clock
nhiro3303 0:42b8e1bc6235 95 // Wait for clocks to become available
nhiro3303 0:42b8e1bc6235 96 while ((LPC_USB->USBClkSt & CLOCK_MASK) != CLOCK_MASK)
nhiro3303 0:42b8e1bc6235 97 ;
nhiro3303 0:42b8e1bc6235 98 LPC_USB->OTGStCtrl |= 1;
nhiro3303 0:42b8e1bc6235 99 LPC_USB->USBClkCtrl &= ~PORTSEL_CLK_EN;
nhiro3303 0:42b8e1bc6235 100
nhiro3303 0:42b8e1bc6235 101 #if defined(TARGET_LPC1768)
nhiro3303 0:42b8e1bc6235 102 LPC_PINCON->PINSEL1 &= ~((3<<26) | (3<<28));
nhiro3303 0:42b8e1bc6235 103 LPC_PINCON->PINSEL1 |= ((1<<26)|(1<<28)); // 0x14000000
nhiro3303 0:42b8e1bc6235 104 #elif defined(TARGET_LPC4088)
nhiro3303 0:42b8e1bc6235 105 LPC_IOCON->P0_29 = 0x01; // USB_D+1
nhiro3303 0:42b8e1bc6235 106 LPC_IOCON->P0_30 = 0x01; // USB_D-1
nhiro3303 0:42b8e1bc6235 107 // DO NOT CHANGE P1_19.
nhiro3303 0:42b8e1bc6235 108 #else
nhiro3303 0:42b8e1bc6235 109 #error "target error"
nhiro3303 0:42b8e1bc6235 110 #endif
nhiro3303 0:42b8e1bc6235 111 USB_DBG("initialize OHCI\n");
nhiro3303 0:42b8e1bc6235 112 wait_ms(100); /* Wait 50 ms before apply reset */
nhiro3303 0:42b8e1bc6235 113 USB_TEST_ASSERT((LPC_USB->HcRevision&0xff) == 0x10); // check revision
nhiro3303 0:42b8e1bc6235 114 LPC_USB->HcControl = 0; /* HARDWARE RESET */
nhiro3303 0:42b8e1bc6235 115 LPC_USB->HcControlHeadED = 0; /* Initialize Control list head to Zero */
nhiro3303 0:42b8e1bc6235 116 LPC_USB->HcBulkHeadED = 0; /* Initialize Bulk list head to Zero */
nhiro3303 0:42b8e1bc6235 117 /* SOFTWARE RESET */
nhiro3303 0:42b8e1bc6235 118 LPC_USB->HcCommandStatus = OR_CMD_STATUS_HCR;
nhiro3303 0:42b8e1bc6235 119 LPC_USB->HcFmInterval = DEFAULT_FMINTERVAL; /* Write Fm Interval and Largest Data Packet Counter */
nhiro3303 0:42b8e1bc6235 120 LPC_USB->HcPeriodicStart = FI*90/100;
nhiro3303 0:42b8e1bc6235 121 /* Put HC in operational state */
nhiro3303 0:42b8e1bc6235 122 LPC_USB->HcControl = (LPC_USB->HcControl & (~OR_CONTROL_HCFS)) | OR_CONTROL_HC_OPER;
nhiro3303 0:42b8e1bc6235 123 LPC_USB->HcRhStatus = OR_RH_STATUS_LPSC; /* Set Global Power */
nhiro3303 0:42b8e1bc6235 124 USB_TEST_ASSERT(pHcca);
nhiro3303 0:42b8e1bc6235 125 for (int i = 0; i < 32; i++) {
nhiro3303 0:42b8e1bc6235 126 pHcca->InterruptTable[i] = NULL;
nhiro3303 0:42b8e1bc6235 127 }
nhiro3303 0:42b8e1bc6235 128 LPC_USB->HcHCCA = reinterpret_cast<uint32_t>(pHcca);
nhiro3303 0:42b8e1bc6235 129 LPC_USB->HcInterruptStatus |= LPC_USB->HcInterruptStatus; /* Clear Interrrupt Status */
nhiro3303 0:42b8e1bc6235 130 LPC_USB->HcInterruptEnable = OR_INTR_ENABLE_MIE|OR_INTR_ENABLE_WDH|OR_INTR_ENABLE_FNO;
nhiro3303 0:42b8e1bc6235 131
nhiro3303 0:42b8e1bc6235 132 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_CSC;
nhiro3303 0:42b8e1bc6235 133 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC;
nhiro3303 0:42b8e1bc6235 134 }
nhiro3303 0:42b8e1bc6235 135
nhiro3303 0:42b8e1bc6235 136 void USBHALHost::ResetRootHub() {
nhiro3303 0:42b8e1bc6235 137 wait_ms(100); /* USB 2.0 spec says at least 50ms delay before port reset */
nhiro3303 0:42b8e1bc6235 138 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRS; // Initiate port reset
nhiro3303 0:42b8e1bc6235 139 USB_DBG("Before loop\n");
nhiro3303 0:42b8e1bc6235 140 while (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_PRS)
nhiro3303 0:42b8e1bc6235 141 ;
nhiro3303 0:42b8e1bc6235 142 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC; // ...and clear port reset signal
nhiro3303 0:42b8e1bc6235 143 USB_DBG("After loop\n");
nhiro3303 0:42b8e1bc6235 144 wait_ms(200); /* Wait for 100 MS after port reset */
nhiro3303 0:42b8e1bc6235 145 }
nhiro3303 0:42b8e1bc6235 146
nhiro3303 0:42b8e1bc6235 147 bool USBHALHost::wait_attach() {
nhiro3303 0:42b8e1bc6235 148 bool lowSpeed = false;
nhiro3303 0:42b8e1bc6235 149 uint32_t status = LPC_USB->HcRhPortStatus1;
nhiro3303 0:42b8e1bc6235 150 if (status & OR_RH_PORT_LSDA) { // lowSpeedDeviceAttached
nhiro3303 0:42b8e1bc6235 151 lowSpeed = true;
nhiro3303 0:42b8e1bc6235 152 }
nhiro3303 0:42b8e1bc6235 153 return lowSpeed;
nhiro3303 0:42b8e1bc6235 154 }
nhiro3303 0:42b8e1bc6235 155
nhiro3303 0:42b8e1bc6235 156 void enable(ENDPOINT_TYPE type) {
nhiro3303 0:42b8e1bc6235 157 switch(type) {
nhiro3303 0:42b8e1bc6235 158 case CONTROL_ENDPOINT:
nhiro3303 0:42b8e1bc6235 159 LPC_USB->HcCommandStatus |= OR_CMD_STATUS_CLF;
nhiro3303 0:42b8e1bc6235 160 LPC_USB->HcControl |= OR_CONTROL_CLE;
nhiro3303 0:42b8e1bc6235 161 break;
nhiro3303 0:42b8e1bc6235 162 case ISOCHRONOUS_ENDPOINT:
nhiro3303 0:42b8e1bc6235 163 LPC_USB->HcControl |= OR_CONTROL_PLE;
nhiro3303 0:42b8e1bc6235 164 break;
nhiro3303 0:42b8e1bc6235 165 case BULK_ENDPOINT:
nhiro3303 0:42b8e1bc6235 166 LPC_USB->HcCommandStatus |= OR_CMD_STATUS_BLF;
nhiro3303 0:42b8e1bc6235 167 LPC_USB->HcControl |= OR_CONTROL_BLE;
nhiro3303 0:42b8e1bc6235 168 break;
nhiro3303 0:42b8e1bc6235 169 case INTERRUPT_ENDPOINT:
nhiro3303 0:42b8e1bc6235 170 LPC_USB->HcControl |= OR_CONTROL_PLE;
nhiro3303 0:42b8e1bc6235 171 break;
nhiro3303 0:42b8e1bc6235 172 }
nhiro3303 0:42b8e1bc6235 173 }
nhiro3303 0:42b8e1bc6235 174
nhiro3303 0:42b8e1bc6235 175 void USBHALHost::token_init(USBEndpoint* ep) {
nhiro3303 0:42b8e1bc6235 176 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 177 if (ed == NULL) {
nhiro3303 0:42b8e1bc6235 178 ed = new HCED(ep);
nhiro3303 0:42b8e1bc6235 179 ep->setHALData<HCED*>(ed);
nhiro3303 0:42b8e1bc6235 180 }
nhiro3303 0:42b8e1bc6235 181 USBDeviceConnected* dev = ep->getDevice();
nhiro3303 0:42b8e1bc6235 182 USB_TEST_ASSERT(dev);
nhiro3303 0:42b8e1bc6235 183 if (dev) {
nhiro3303 0:42b8e1bc6235 184 uint8_t devAddr = dev->getAddress();
nhiro3303 0:42b8e1bc6235 185 USB_DBG("devAddr=%02x", devAddr);
nhiro3303 0:42b8e1bc6235 186 ed->setFunctionAddress(devAddr);
nhiro3303 0:42b8e1bc6235 187 }
nhiro3303 0:42b8e1bc6235 188 uint16_t size = ep->getSize();
nhiro3303 0:42b8e1bc6235 189 USB_DBG("MaxPacketSize=%d", size);
nhiro3303 0:42b8e1bc6235 190 ed->setMaxPacketSize(size);
nhiro3303 0:42b8e1bc6235 191 if (ed->HeadTd == NULL) {
nhiro3303 0:42b8e1bc6235 192 HCTD* td = new HCTD(ed);
nhiro3303 0:42b8e1bc6235 193 ed->TailTd = td;
nhiro3303 0:42b8e1bc6235 194 ed->HeadTd = td;
nhiro3303 0:42b8e1bc6235 195 switch(ep->getType()) {
nhiro3303 0:42b8e1bc6235 196 case CONTROL_ENDPOINT:
nhiro3303 0:42b8e1bc6235 197 ed->Next = reinterpret_cast<HCED*>(LPC_USB->HcControlHeadED);
nhiro3303 0:42b8e1bc6235 198 LPC_USB->HcControlHeadED = reinterpret_cast<uint32_t>(ed);
nhiro3303 0:42b8e1bc6235 199 break;
nhiro3303 0:42b8e1bc6235 200 case BULK_ENDPOINT:
nhiro3303 0:42b8e1bc6235 201 ed->Next = reinterpret_cast<HCED*>(LPC_USB->HcBulkHeadED);
nhiro3303 0:42b8e1bc6235 202 LPC_USB->HcBulkHeadED = reinterpret_cast<uint32_t>(ed);
nhiro3303 0:42b8e1bc6235 203 break;
nhiro3303 0:42b8e1bc6235 204 case INTERRUPT_ENDPOINT:
nhiro3303 0:42b8e1bc6235 205 HCCA* pHcca = reinterpret_cast<HCCA*>(LPC_USB->HcHCCA);
nhiro3303 0:42b8e1bc6235 206 ed->Next = pHcca->InterruptTable[0];
nhiro3303 0:42b8e1bc6235 207 pHcca->InterruptTable[0] = ed;
nhiro3303 0:42b8e1bc6235 208 break;
nhiro3303 0:42b8e1bc6235 209 }
nhiro3303 0:42b8e1bc6235 210 }
nhiro3303 0:42b8e1bc6235 211 }
nhiro3303 0:42b8e1bc6235 212
nhiro3303 0:42b8e1bc6235 213 int USBHALHost::token_setup(USBEndpoint* ep, SETUP_PACKET* setup, uint16_t wLength) {
nhiro3303 0:42b8e1bc6235 214 token_init(ep);
nhiro3303 0:42b8e1bc6235 215 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 216 HCTD* td = ed->TailTd;
nhiro3303 0:42b8e1bc6235 217 setup->wLength = wLength;
nhiro3303 0:42b8e1bc6235 218 TBUF* tbuf = new(sizeof(SETUP_PACKET))TBUF(setup, sizeof(SETUP_PACKET));
nhiro3303 0:42b8e1bc6235 219 td->transfer(tbuf, sizeof(SETUP_PACKET));
nhiro3303 0:42b8e1bc6235 220 td->Control |= TD_TOGGLE_0|TD_SETUP; // DATA0
nhiro3303 0:42b8e1bc6235 221 HCTD* blank = new HCTD(ed);
nhiro3303 0:42b8e1bc6235 222 ed->enqueue(blank);
nhiro3303 0:42b8e1bc6235 223 //DBG_ED(ed);
nhiro3303 0:42b8e1bc6235 224 enable(ep->getType());
nhiro3303 0:42b8e1bc6235 225
nhiro3303 0:42b8e1bc6235 226 td = ed->get_queue_HCTD();
nhiro3303 0:42b8e1bc6235 227 USB_TEST_ASSERT(td);
nhiro3303 0:42b8e1bc6235 228 int result = td->getLengthTransferred();
nhiro3303 0:42b8e1bc6235 229 USB_DBG_TD(td);
nhiro3303 0:42b8e1bc6235 230 delete tbuf;
nhiro3303 0:42b8e1bc6235 231 delete td;
nhiro3303 0:42b8e1bc6235 232 return result;
nhiro3303 0:42b8e1bc6235 233 }
nhiro3303 0:42b8e1bc6235 234
nhiro3303 0:42b8e1bc6235 235 static HCED* getHCED_iso(USBEndpoint* ep) {
nhiro3303 0:42b8e1bc6235 236 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 237 if (ed != NULL) {
nhiro3303 0:42b8e1bc6235 238 return ed;
nhiro3303 0:42b8e1bc6235 239 }
nhiro3303 0:42b8e1bc6235 240 ed = new HCED(ep);
nhiro3303 0:42b8e1bc6235 241 ep->setHALData<HCED*>(ed);
nhiro3303 0:42b8e1bc6235 242 ed->setFormat(); // F Format ITD
nhiro3303 0:42b8e1bc6235 243 ed->iso.FrameCount = ep->ohci.frameCount;
nhiro3303 0:42b8e1bc6235 244 ed->iso.queue_limit = ep->ohci.queueLimit;
nhiro3303 0:42b8e1bc6235 245 ed->iso.queue_count = 0;
nhiro3303 0:42b8e1bc6235 246 ed->iso.Current_FrameCount = 0;
nhiro3303 0:42b8e1bc6235 247 ed->iso.Current_itd = NULL;
nhiro3303 0:42b8e1bc6235 248 ed->iso.FrameNumber = LPC_USB->HcFmNumber + 10; // after 10msec
nhiro3303 0:42b8e1bc6235 249 HCITD* itd = ed->new_HCITD();
nhiro3303 0:42b8e1bc6235 250 ed->init_queue(reinterpret_cast<HCTD*>(itd));
nhiro3303 0:42b8e1bc6235 251 HCCA* hcca = reinterpret_cast<HCCA*>(LPC_USB->HcHCCA);
nhiro3303 0:42b8e1bc6235 252 hcca->enqueue(ed);
nhiro3303 0:42b8e1bc6235 253 LPC_USB->HcControl |= OR_CONTROL_PLE; // PeriodicListEnable
nhiro3303 0:42b8e1bc6235 254 LPC_USB->HcControl |= OR_CONTROL_IE; // IsochronousEnable
nhiro3303 0:42b8e1bc6235 255 return ed;
nhiro3303 0:42b8e1bc6235 256 }
nhiro3303 0:42b8e1bc6235 257
nhiro3303 0:42b8e1bc6235 258 static void enablePeriodic() {
nhiro3303 0:42b8e1bc6235 259 LPC_USB->HcControl |= OR_CONTROL_PLE;
nhiro3303 0:42b8e1bc6235 260 }
nhiro3303 0:42b8e1bc6235 261
nhiro3303 0:42b8e1bc6235 262 HCITD* isochronousReceive(USBEndpoint* ep) {
nhiro3303 0:42b8e1bc6235 263 HCED* ed = getHCED_iso(ep);
nhiro3303 0:42b8e1bc6235 264 USB_TEST_ASSERT(ed);
nhiro3303 0:42b8e1bc6235 265 while(ed->iso.queue_count < ed->iso.queue_limit) {
nhiro3303 0:42b8e1bc6235 266 HCITD* blank_itd = ed->new_HCITD();
nhiro3303 0:42b8e1bc6235 267 if (ed->enqueue(reinterpret_cast<HCTD*>(blank_itd))) {
nhiro3303 0:42b8e1bc6235 268 ed->iso.queue_count++;
nhiro3303 0:42b8e1bc6235 269 }
nhiro3303 0:42b8e1bc6235 270 enablePeriodic();
nhiro3303 0:42b8e1bc6235 271 }
nhiro3303 0:42b8e1bc6235 272
nhiro3303 0:42b8e1bc6235 273 HCITD* itd = ed->get_queue_HCITD();
nhiro3303 0:42b8e1bc6235 274 if (itd) {
nhiro3303 0:42b8e1bc6235 275 ed->iso.queue_count--;
nhiro3303 0:42b8e1bc6235 276 }
nhiro3303 0:42b8e1bc6235 277 return itd;
nhiro3303 0:42b8e1bc6235 278 }
nhiro3303 0:42b8e1bc6235 279
nhiro3303 0:42b8e1bc6235 280 int USBHALHost::token_iso_in(USBEndpoint* ep, uint8_t* data, int size) {
nhiro3303 0:42b8e1bc6235 281 HCED* ed = getHCED_iso(ep);
nhiro3303 0:42b8e1bc6235 282 if (ed->iso.Current_FrameCount == 0) {
nhiro3303 0:42b8e1bc6235 283 HCITD* itd = isochronousReceive(ep);
nhiro3303 0:42b8e1bc6235 284 if (itd == NULL) {
nhiro3303 0:42b8e1bc6235 285 return -1;
nhiro3303 0:42b8e1bc6235 286 }
nhiro3303 0:42b8e1bc6235 287 if (itd->ConditionCode() != 0) {
nhiro3303 0:42b8e1bc6235 288 delete itd;
nhiro3303 0:42b8e1bc6235 289 return -1;
nhiro3303 0:42b8e1bc6235 290 }
nhiro3303 0:42b8e1bc6235 291 ed->iso.Current_itd = itd;
nhiro3303 0:42b8e1bc6235 292 }
nhiro3303 0:42b8e1bc6235 293
nhiro3303 0:42b8e1bc6235 294 HCITD* itd = ed->iso.Current_itd;
nhiro3303 0:42b8e1bc6235 295 int fc = ed->iso.Current_FrameCount;
nhiro3303 0:42b8e1bc6235 296 int result = -1;
nhiro3303 0:42b8e1bc6235 297 uint8_t cc = itd->ConditionCode(fc);
nhiro3303 0:42b8e1bc6235 298 if (cc == 0 || cc == 9) {
nhiro3303 0:42b8e1bc6235 299 result = itd->Length(fc);
nhiro3303 0:42b8e1bc6235 300 memcpy(data, itd->Buffer(fc), result);
nhiro3303 0:42b8e1bc6235 301 }
nhiro3303 0:42b8e1bc6235 302
nhiro3303 0:42b8e1bc6235 303 if (++ed->iso.Current_FrameCount >= itd->FrameCount()) {
nhiro3303 0:42b8e1bc6235 304 ed->iso.Current_FrameCount = 0;
nhiro3303 0:42b8e1bc6235 305 delete ed->iso.Current_itd;
nhiro3303 0:42b8e1bc6235 306 }
nhiro3303 0:42b8e1bc6235 307 return result;
nhiro3303 0:42b8e1bc6235 308 }
nhiro3303 0:42b8e1bc6235 309
nhiro3303 0:42b8e1bc6235 310 int USBHALHost::multi_token_in(USBEndpoint* ep, uint8_t* data, int size) {
nhiro3303 0:42b8e1bc6235 311 token_init(ep);
nhiro3303 0:42b8e1bc6235 312 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 313 HCTD* td = ed->TailTd;
nhiro3303 0:42b8e1bc6235 314 TBUF* tbuf = NULL;
nhiro3303 0:42b8e1bc6235 315 if (data != NULL) {
nhiro3303 0:42b8e1bc6235 316 tbuf = new(size)TBUF();
nhiro3303 0:42b8e1bc6235 317 td->transfer(tbuf, size);
nhiro3303 0:42b8e1bc6235 318 }
nhiro3303 0:42b8e1bc6235 319 td->Control |= TD_IN;
nhiro3303 0:42b8e1bc6235 320 HCTD* blank = new HCTD(ed);
nhiro3303 0:42b8e1bc6235 321 ed->enqueue(blank);
nhiro3303 0:42b8e1bc6235 322 USB_DBG_ED_IF(ed->EndpointNumber()==0, ed); // control transfer
nhiro3303 0:42b8e1bc6235 323 enable(ep->getType());
nhiro3303 0:42b8e1bc6235 324
nhiro3303 0:42b8e1bc6235 325 td = ed->get_queue_HCTD();
nhiro3303 0:42b8e1bc6235 326 USB_TEST_ASSERT(td);
nhiro3303 0:42b8e1bc6235 327 if (data != NULL) {
nhiro3303 0:42b8e1bc6235 328 memcpy(data, tbuf->buf, size);
nhiro3303 0:42b8e1bc6235 329 delete tbuf;
nhiro3303 0:42b8e1bc6235 330 }
nhiro3303 0:42b8e1bc6235 331 int result = td->getLengthTransferred();
nhiro3303 0:42b8e1bc6235 332 delete td;
nhiro3303 0:42b8e1bc6235 333 return result;
nhiro3303 0:42b8e1bc6235 334 }
nhiro3303 0:42b8e1bc6235 335
nhiro3303 0:42b8e1bc6235 336 int USBHALHost::multi_token_out(USBEndpoint* ep, const uint8_t* data, int size) {
nhiro3303 0:42b8e1bc6235 337 token_init(ep);
nhiro3303 0:42b8e1bc6235 338 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 339 HCTD* td = ed->TailTd;
nhiro3303 0:42b8e1bc6235 340 TBUF* tbuf = NULL;
nhiro3303 0:42b8e1bc6235 341 if (data != NULL) {
nhiro3303 0:42b8e1bc6235 342 tbuf = new(size)TBUF(data, size);
nhiro3303 0:42b8e1bc6235 343 td->transfer(tbuf, size);
nhiro3303 0:42b8e1bc6235 344 }
nhiro3303 0:42b8e1bc6235 345 td->Control |= TD_OUT;
nhiro3303 0:42b8e1bc6235 346 HCTD* blank = new HCTD(ed);
nhiro3303 0:42b8e1bc6235 347 ed->enqueue(blank);
nhiro3303 0:42b8e1bc6235 348 USB_DBG_ED(ed);
nhiro3303 0:42b8e1bc6235 349 enable(ep->getType());
nhiro3303 0:42b8e1bc6235 350
nhiro3303 0:42b8e1bc6235 351 td = ed->get_queue_HCTD();
nhiro3303 0:42b8e1bc6235 352 USB_TEST_ASSERT(td);
nhiro3303 0:42b8e1bc6235 353 if (data != NULL) {
nhiro3303 0:42b8e1bc6235 354 delete tbuf;
nhiro3303 0:42b8e1bc6235 355 }
nhiro3303 0:42b8e1bc6235 356 int result = td->getLengthTransferred();
nhiro3303 0:42b8e1bc6235 357 delete td;
nhiro3303 0:42b8e1bc6235 358 return result;
nhiro3303 0:42b8e1bc6235 359 }
nhiro3303 0:42b8e1bc6235 360
nhiro3303 0:42b8e1bc6235 361 void USBHALHost::multi_token_inNB(USBEndpoint* ep, uint8_t* data, int size) {
nhiro3303 0:42b8e1bc6235 362 token_init(ep);
nhiro3303 0:42b8e1bc6235 363 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 364 HCTD* td = ed->TailTd;
nhiro3303 0:42b8e1bc6235 365 TBUF* tbuf = new(size)TBUF();
nhiro3303 0:42b8e1bc6235 366 td->transfer(tbuf, size);
nhiro3303 0:42b8e1bc6235 367 td->Control |= TD_IN;
nhiro3303 0:42b8e1bc6235 368 HCTD* blank = new HCTD(ed);
nhiro3303 0:42b8e1bc6235 369 ed->enqueue(blank);
nhiro3303 0:42b8e1bc6235 370 enable(ep->getType());
nhiro3303 0:42b8e1bc6235 371 }
nhiro3303 0:42b8e1bc6235 372
nhiro3303 0:42b8e1bc6235 373 USB_TYPE USBHALHost::multi_token_inNB_result(USBEndpoint* ep) {
nhiro3303 0:42b8e1bc6235 374 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 375 if (ed == NULL) {
nhiro3303 0:42b8e1bc6235 376 return USB_TYPE_ERROR;
nhiro3303 0:42b8e1bc6235 377 }
nhiro3303 0:42b8e1bc6235 378 HCTD* td = ed->get_queue_HCTD(0);
nhiro3303 0:42b8e1bc6235 379 if (td) {
nhiro3303 0:42b8e1bc6235 380 int len = td->getLengthTransferred();
nhiro3303 0:42b8e1bc6235 381 TBUF* tbuf = (TBUF*)td->buf_top;
nhiro3303 0:42b8e1bc6235 382 memcpy(ep->getBufStart(), tbuf->buf, len);
nhiro3303 0:42b8e1bc6235 383 ep->setLengthTransferred(len);
nhiro3303 0:42b8e1bc6235 384 ep->setState((USB_TYPE)td->ConditionCode());
nhiro3303 0:42b8e1bc6235 385 delete td;
nhiro3303 0:42b8e1bc6235 386 delete tbuf;
nhiro3303 0:42b8e1bc6235 387 return USB_TYPE_OK;
nhiro3303 0:42b8e1bc6235 388 }
nhiro3303 0:42b8e1bc6235 389 return USB_TYPE_PROCESSING;
nhiro3303 0:42b8e1bc6235 390 }
nhiro3303 0:42b8e1bc6235 391
nhiro3303 0:42b8e1bc6235 392 void USBHALHost::setToggle(USBEndpoint* ep, uint8_t toggle) {
nhiro3303 0:42b8e1bc6235 393 USB_TEST_ASSERT(toggle == 1);
nhiro3303 0:42b8e1bc6235 394 HCED* ed = ep->getHALData<HCED*>();
nhiro3303 0:42b8e1bc6235 395 ed->setToggle(toggle);
nhiro3303 0:42b8e1bc6235 396 }
nhiro3303 0:42b8e1bc6235 397
nhiro3303 0:42b8e1bc6235 398 void USBHALHost::_usbisr(void) {
nhiro3303 0:42b8e1bc6235 399 if (instHost) {
nhiro3303 0:42b8e1bc6235 400 instHost->UsbIrqhandler();
nhiro3303 0:42b8e1bc6235 401 }
nhiro3303 0:42b8e1bc6235 402 }
nhiro3303 0:42b8e1bc6235 403
nhiro3303 0:42b8e1bc6235 404 HCTD* td_reverse(HCTD* td)
nhiro3303 0:42b8e1bc6235 405 {
nhiro3303 0:42b8e1bc6235 406 HCTD* result = NULL;
nhiro3303 0:42b8e1bc6235 407 HCTD* next;
nhiro3303 0:42b8e1bc6235 408 while(td) {
nhiro3303 0:42b8e1bc6235 409 next = const_cast<HCTD*>(td->Next);
nhiro3303 0:42b8e1bc6235 410 td->Next = result;
nhiro3303 0:42b8e1bc6235 411 result = td;
nhiro3303 0:42b8e1bc6235 412 td = next;
nhiro3303 0:42b8e1bc6235 413 }
nhiro3303 0:42b8e1bc6235 414 return result;
nhiro3303 0:42b8e1bc6235 415 }
nhiro3303 0:42b8e1bc6235 416
nhiro3303 0:42b8e1bc6235 417 void USBHALHost::UsbIrqhandler() {
nhiro3303 0:42b8e1bc6235 418 if (!(LPC_USB->HcInterruptStatus & LPC_USB->HcInterruptEnable)) {
nhiro3303 0:42b8e1bc6235 419 return;
nhiro3303 0:42b8e1bc6235 420 }
nhiro3303 0:42b8e1bc6235 421 m_report_irq++;
nhiro3303 0:42b8e1bc6235 422 uint32_t status = LPC_USB->HcInterruptStatus;
nhiro3303 0:42b8e1bc6235 423 if (status & OR_INTR_STATUS_FNO) {
nhiro3303 0:42b8e1bc6235 424 m_report_FNO++;
nhiro3303 0:42b8e1bc6235 425 }
nhiro3303 0:42b8e1bc6235 426 if (status & OR_INTR_STATUS_WDH) {
nhiro3303 0:42b8e1bc6235 427 union {
nhiro3303 0:42b8e1bc6235 428 HCTD* done_td;
nhiro3303 0:42b8e1bc6235 429 uint32_t lsb;
nhiro3303 0:42b8e1bc6235 430 };
nhiro3303 0:42b8e1bc6235 431 done_td = const_cast<HCTD*>(m_pHcca->DoneHead);
nhiro3303 0:42b8e1bc6235 432 USB_TEST_ASSERT(done_td);
nhiro3303 0:42b8e1bc6235 433 m_pHcca->DoneHead = NULL; // reset
nhiro3303 0:42b8e1bc6235 434 if (lsb & 1) { // error ?
nhiro3303 0:42b8e1bc6235 435 lsb &= ~1;
nhiro3303 0:42b8e1bc6235 436 }
nhiro3303 0:42b8e1bc6235 437 HCTD* td = td_reverse(done_td);
nhiro3303 0:42b8e1bc6235 438 while(td) {
nhiro3303 0:42b8e1bc6235 439 HCED* ed = td->parent;
nhiro3303 0:42b8e1bc6235 440 USB_TEST_ASSERT(ed);
nhiro3303 0:42b8e1bc6235 441 if (ed) {
nhiro3303 0:42b8e1bc6235 442 ed->irqWdhHandler(td);
nhiro3303 0:42b8e1bc6235 443 }
nhiro3303 0:42b8e1bc6235 444 td = td->Next;
nhiro3303 0:42b8e1bc6235 445 }
nhiro3303 0:42b8e1bc6235 446 m_report_WDH++;
nhiro3303 0:42b8e1bc6235 447 }
nhiro3303 0:42b8e1bc6235 448 LPC_USB->HcInterruptStatus = status; // Clear Interrrupt Status
nhiro3303 0:42b8e1bc6235 449 }
nhiro3303 0:42b8e1bc6235 450
nhiro3303 0:42b8e1bc6235 451 TBUF::TBUF(const void* data, int size) {
nhiro3303 0:42b8e1bc6235 452 if (size > 0) {
nhiro3303 0:42b8e1bc6235 453 memcpy(buf, data, size);
nhiro3303 0:42b8e1bc6235 454 }
nhiro3303 0:42b8e1bc6235 455 }
nhiro3303 0:42b8e1bc6235 456
nhiro3303 0:42b8e1bc6235 457 HCTD::HCTD(HCED* obj) {
nhiro3303 0:42b8e1bc6235 458 CTASSERT(sizeof(HCTD) == 36);
nhiro3303 0:42b8e1bc6235 459 USB_TEST_ASSERT(obj);
nhiro3303 0:42b8e1bc6235 460 Control = TD_CC|TD_ROUNDING;
nhiro3303 0:42b8e1bc6235 461 CurrBufPtr = NULL;
nhiro3303 0:42b8e1bc6235 462 Next = NULL;
nhiro3303 0:42b8e1bc6235 463 BufEnd = NULL;
nhiro3303 0:42b8e1bc6235 464 buf_top = NULL;
nhiro3303 0:42b8e1bc6235 465 buf_size = 0;
nhiro3303 0:42b8e1bc6235 466 parent = obj;
nhiro3303 0:42b8e1bc6235 467 }
nhiro3303 0:42b8e1bc6235 468
nhiro3303 0:42b8e1bc6235 469 HCITD::HCITD(HCED* obj, uint16_t FrameNumber, int FrameCount, uint16_t PacketSize) {
nhiro3303 0:42b8e1bc6235 470 Control = 0xe0000000 | // CC ConditionCode NOT ACCESSED
nhiro3303 0:42b8e1bc6235 471 ((FrameCount-1) << 24)| // FC FrameCount
nhiro3303 0:42b8e1bc6235 472 TD_DELAY_INT(0) | // DI DelayInterrupt
nhiro3303 0:42b8e1bc6235 473 FrameNumber; // SF StartingFrame
nhiro3303 0:42b8e1bc6235 474 BufferPage0 = const_cast<uint8_t*>(buf);
nhiro3303 0:42b8e1bc6235 475 BufferEnd = const_cast<uint8_t*>(buf) + PacketSize * FrameCount - 1;
nhiro3303 0:42b8e1bc6235 476 Next = NULL;
nhiro3303 0:42b8e1bc6235 477 parent = obj;
nhiro3303 0:42b8e1bc6235 478 uint32_t addr = reinterpret_cast<uint32_t>(buf);
nhiro3303 0:42b8e1bc6235 479 for(int i = 0; i < FrameCount; i++) {
nhiro3303 0:42b8e1bc6235 480 uint16_t offset = addr & 0x0fff;
nhiro3303 0:42b8e1bc6235 481 if ((addr&0xfffff000) == (reinterpret_cast<uint32_t>(BufferEnd)&0xfffff000)) {
nhiro3303 0:42b8e1bc6235 482 offset |= 0x1000;
nhiro3303 0:42b8e1bc6235 483 }
nhiro3303 0:42b8e1bc6235 484 OffsetPSW[i] = 0xe000|offset;
nhiro3303 0:42b8e1bc6235 485 addr += PacketSize;
nhiro3303 0:42b8e1bc6235 486 }
nhiro3303 0:42b8e1bc6235 487 }
nhiro3303 0:42b8e1bc6235 488
nhiro3303 0:42b8e1bc6235 489 uint8_t* HCITD::Buffer(int fc) {
nhiro3303 0:42b8e1bc6235 490 int offset = fc * parent->getMaxPacketSize();
nhiro3303 0:42b8e1bc6235 491 return const_cast<uint8_t*>(buf) + offset;
nhiro3303 0:42b8e1bc6235 492 }
nhiro3303 0:42b8e1bc6235 493
nhiro3303 0:42b8e1bc6235 494 HCED::HCED(USBEndpoint* ep) {
nhiro3303 0:42b8e1bc6235 495 CTASSERT(sizeof(HCED) <= (64*2));
nhiro3303 0:42b8e1bc6235 496 USBDeviceConnected* dev = ep->getDevice();
nhiro3303 0:42b8e1bc6235 497 int devAddr = 0;
nhiro3303 0:42b8e1bc6235 498 bool lowSpeed = false;
nhiro3303 0:42b8e1bc6235 499 if (dev) {
nhiro3303 0:42b8e1bc6235 500 devAddr = dev->getAddress();
nhiro3303 0:42b8e1bc6235 501 lowSpeed = dev->getSpeed();
nhiro3303 0:42b8e1bc6235 502 }
nhiro3303 0:42b8e1bc6235 503 int ep_number = ep->getAddress();
nhiro3303 0:42b8e1bc6235 504 int MaxPacketSize = ep->getSize();
nhiro3303 0:42b8e1bc6235 505 Control = devAddr | /* USB address */
nhiro3303 0:42b8e1bc6235 506 ((ep_number & 0x7F) << 7) | /* Endpoint address */
nhiro3303 0:42b8e1bc6235 507 (ep_number!=0?(((ep_number&0x80)?2:1) << 11):0)| /* direction : Out = 1, 2 = In */
nhiro3303 0:42b8e1bc6235 508 ((lowSpeed?1:0) << 13) | /* speed full=0 low=1 */
nhiro3303 0:42b8e1bc6235 509 (MaxPacketSize << 16); /* MaxPkt Size */
nhiro3303 0:42b8e1bc6235 510 TailTd = NULL;
nhiro3303 0:42b8e1bc6235 511 HeadTd = NULL;
nhiro3303 0:42b8e1bc6235 512 Next = NULL;
nhiro3303 0:42b8e1bc6235 513 }
nhiro3303 0:42b8e1bc6235 514
nhiro3303 0:42b8e1bc6235 515 bool HCED::enqueue(HCTD* td) {
nhiro3303 0:42b8e1bc6235 516 if (td) {
nhiro3303 0:42b8e1bc6235 517 HCTD* tail = reinterpret_cast<HCTD*>(TailTd);
nhiro3303 0:42b8e1bc6235 518 if (tail) {
nhiro3303 0:42b8e1bc6235 519 tail->Next = td;
nhiro3303 0:42b8e1bc6235 520 TailTd = reinterpret_cast<HCTD*>(td);
nhiro3303 0:42b8e1bc6235 521 return true;
nhiro3303 0:42b8e1bc6235 522 }
nhiro3303 0:42b8e1bc6235 523 }
nhiro3303 0:42b8e1bc6235 524 return false;
nhiro3303 0:42b8e1bc6235 525 }
nhiro3303 0:42b8e1bc6235 526
nhiro3303 0:42b8e1bc6235 527 void HCED::init_queue(HCTD* td) {
nhiro3303 0:42b8e1bc6235 528 TailTd = reinterpret_cast<HCTD*>(td);
nhiro3303 0:42b8e1bc6235 529 HeadTd = reinterpret_cast<HCTD*>(td);
nhiro3303 0:42b8e1bc6235 530 }
nhiro3303 0:42b8e1bc6235 531
nhiro3303 0:42b8e1bc6235 532 void HCED::setToggle(uint8_t toggle) {
nhiro3303 0:42b8e1bc6235 533 uint32_t c = reinterpret_cast<uint32_t>(HeadTd);
nhiro3303 0:42b8e1bc6235 534 if (toggle == 0) { // DATA0
nhiro3303 0:42b8e1bc6235 535 c &= ~0x02;
nhiro3303 0:42b8e1bc6235 536 } else { // DATA1
nhiro3303 0:42b8e1bc6235 537 c |= 0x02;
nhiro3303 0:42b8e1bc6235 538 }
nhiro3303 0:42b8e1bc6235 539 HeadTd = reinterpret_cast<HCTD*>(c);
nhiro3303 0:42b8e1bc6235 540 }
nhiro3303 0:42b8e1bc6235 541
nhiro3303 0:42b8e1bc6235 542 uint8_t HCED::getToggle() {
nhiro3303 0:42b8e1bc6235 543 uint32_t c = reinterpret_cast<uint32_t>(HeadTd);
nhiro3303 0:42b8e1bc6235 544 return (c&0x02) ? 1 : 0;
nhiro3303 0:42b8e1bc6235 545 }
nhiro3303 0:42b8e1bc6235 546
nhiro3303 0:42b8e1bc6235 547 HCTD* HCED::get_queue_HCTD(uint32_t millisec)
nhiro3303 0:42b8e1bc6235 548 {
nhiro3303 0:42b8e1bc6235 549 for(int i = 0; i < 16; i++) {
nhiro3303 0:42b8e1bc6235 550 osEvent evt = done_queue_get(millisec);
nhiro3303 0:42b8e1bc6235 551 if (evt.status == osEventMessage) {
nhiro3303 0:42b8e1bc6235 552 HCTD* td = reinterpret_cast<HCTD*>(evt.value.p);
nhiro3303 0:42b8e1bc6235 553 USB_TEST_ASSERT(td);
nhiro3303 0:42b8e1bc6235 554 uint8_t cc = td->ConditionCode();
nhiro3303 0:42b8e1bc6235 555 if (cc != 0) {
nhiro3303 0:42b8e1bc6235 556 m_ConditionCode = cc;
nhiro3303 0:42b8e1bc6235 557 USB_DBG_TD(td);
nhiro3303 0:42b8e1bc6235 558 }
nhiro3303 0:42b8e1bc6235 559 return td;
nhiro3303 0:42b8e1bc6235 560 } else if (evt.status == osOK) {
nhiro3303 0:42b8e1bc6235 561 continue;
nhiro3303 0:42b8e1bc6235 562 } else if (evt.status == osEventTimeout) {
nhiro3303 0:42b8e1bc6235 563 return NULL;
nhiro3303 0:42b8e1bc6235 564 } else {
nhiro3303 0:42b8e1bc6235 565 USB_DBG("evt.status: %02x\n", evt.status);
nhiro3303 0:42b8e1bc6235 566 USB_TEST_ASSERT(evt.status == osEventMessage);
nhiro3303 0:42b8e1bc6235 567 }
nhiro3303 0:42b8e1bc6235 568 }
nhiro3303 0:42b8e1bc6235 569 return NULL;
nhiro3303 0:42b8e1bc6235 570 }
nhiro3303 0:42b8e1bc6235 571
nhiro3303 0:42b8e1bc6235 572 HCITD* HCED::get_queue_HCITD() {
nhiro3303 0:42b8e1bc6235 573 osEvent evt = done_queue_get(0);
nhiro3303 0:42b8e1bc6235 574 if (evt.status == osEventMessage) {
nhiro3303 0:42b8e1bc6235 575 HCITD* itd = reinterpret_cast<HCITD*>(evt.value.p);
nhiro3303 0:42b8e1bc6235 576 USB_TEST_ASSERT(itd);
nhiro3303 0:42b8e1bc6235 577 return itd;
nhiro3303 0:42b8e1bc6235 578 }
nhiro3303 0:42b8e1bc6235 579 return NULL;
nhiro3303 0:42b8e1bc6235 580 }
nhiro3303 0:42b8e1bc6235 581 HCITD* HCED::new_HCITD() {
nhiro3303 0:42b8e1bc6235 582 uint16_t mps = getMaxPacketSize();
nhiro3303 0:42b8e1bc6235 583 int total_size = mps * iso.FrameCount;
nhiro3303 0:42b8e1bc6235 584 HCITD* itd = new(total_size)HCITD(this, iso.FrameNumber, iso.FrameCount, mps);
nhiro3303 0:42b8e1bc6235 585 iso.FrameNumber += iso.FrameCount;
nhiro3303 0:42b8e1bc6235 586 return itd;
nhiro3303 0:42b8e1bc6235 587 }
nhiro3303 0:42b8e1bc6235 588
nhiro3303 0:42b8e1bc6235 589 void HCCA::enqueue(HCED* ed) {
nhiro3303 0:42b8e1bc6235 590 for(int i = 0; i < 32; i++) {
nhiro3303 0:42b8e1bc6235 591 if (InterruptTable[i] == NULL) {
nhiro3303 0:42b8e1bc6235 592 InterruptTable[i] = ed;
nhiro3303 0:42b8e1bc6235 593 } else {
nhiro3303 0:42b8e1bc6235 594 HCED* nextEd = InterruptTable[i];
nhiro3303 0:42b8e1bc6235 595 while(nextEd->Next && nextEd->Next != ed) {
nhiro3303 0:42b8e1bc6235 596 nextEd = nextEd->Next;
nhiro3303 0:42b8e1bc6235 597 }
nhiro3303 0:42b8e1bc6235 598 nextEd->Next = ed;
nhiro3303 0:42b8e1bc6235 599 }
nhiro3303 0:42b8e1bc6235 600 }
nhiro3303 0:42b8e1bc6235 601 }
nhiro3303 0:42b8e1bc6235 602
nhiro3303 0:42b8e1bc6235 603 #endif // defined(TARGET_LPC4088)||defined(TARGET_LPC1768)
nhiro3303 0:42b8e1bc6235 604