Writing data to and from a USB stick

Dependencies:   mbed

Committer:
ms523
Date:
Sun Nov 06 15:45:12 2011 +0000
Revision:
0:5934350323b2
Working with a USB stick

Who changed what in which revision?

UserRevisionLine numberNew contents of line
ms523 0:5934350323b2 1 /*
ms523 0:5934350323b2 2 **************************************************************************************************************
ms523 0:5934350323b2 3 * NXP USB Host Stack
ms523 0:5934350323b2 4 *
ms523 0:5934350323b2 5 * (c) Copyright 2008, NXP SemiConductors
ms523 0:5934350323b2 6 * (c) Copyright 2008, OnChip Technologies LLC
ms523 0:5934350323b2 7 * All Rights Reserved
ms523 0:5934350323b2 8 *
ms523 0:5934350323b2 9 * www.nxp.com
ms523 0:5934350323b2 10 * www.onchiptech.com
ms523 0:5934350323b2 11 *
ms523 0:5934350323b2 12 * File : usbhost_lpc17xx.c
ms523 0:5934350323b2 13 * Programmer(s) : Ravikanth.P
ms523 0:5934350323b2 14 * Version :
ms523 0:5934350323b2 15 *
ms523 0:5934350323b2 16 **************************************************************************************************************
ms523 0:5934350323b2 17 */
ms523 0:5934350323b2 18
ms523 0:5934350323b2 19 /*
ms523 0:5934350323b2 20 **************************************************************************************************************
ms523 0:5934350323b2 21 * INCLUDE HEADER FILES
ms523 0:5934350323b2 22 **************************************************************************************************************
ms523 0:5934350323b2 23 */
ms523 0:5934350323b2 24
ms523 0:5934350323b2 25 #include "usbhost_lpc17xx.h"
ms523 0:5934350323b2 26
ms523 0:5934350323b2 27 /*
ms523 0:5934350323b2 28 **************************************************************************************************************
ms523 0:5934350323b2 29 * GLOBAL VARIABLES
ms523 0:5934350323b2 30 **************************************************************************************************************
ms523 0:5934350323b2 31 */
ms523 0:5934350323b2 32 int gUSBConnected;
ms523 0:5934350323b2 33
ms523 0:5934350323b2 34 volatile USB_INT32U HOST_RhscIntr = 0; /* Root Hub Status Change interrupt */
ms523 0:5934350323b2 35 volatile USB_INT32U HOST_WdhIntr = 0; /* Semaphore to wait until the TD is submitted */
ms523 0:5934350323b2 36 volatile USB_INT08U HOST_TDControlStatus = 0;
ms523 0:5934350323b2 37 volatile HCED *EDCtrl; /* Control endpoint descriptor structure */
ms523 0:5934350323b2 38 volatile HCED *EDBulkIn; /* BulkIn endpoint descriptor structure */
ms523 0:5934350323b2 39 volatile HCED *EDBulkOut; /* BulkOut endpoint descriptor structure */
ms523 0:5934350323b2 40 volatile HCTD *TDHead; /* Head transfer descriptor structure */
ms523 0:5934350323b2 41 volatile HCTD *TDTail; /* Tail transfer descriptor structure */
ms523 0:5934350323b2 42 volatile HCCA *Hcca; /* Host Controller Communications Area structure */
ms523 0:5934350323b2 43 USB_INT16U *TDBufNonVol; /* Identical to TDBuffer just to reduce compiler warnings */
ms523 0:5934350323b2 44 volatile USB_INT08U *TDBuffer; /* Current Buffer Pointer of transfer descriptor */
ms523 0:5934350323b2 45
ms523 0:5934350323b2 46 // USB host structures
ms523 0:5934350323b2 47 // AHB SRAM block 1
ms523 0:5934350323b2 48 #define HOSTBASEADDR 0x2007C000
ms523 0:5934350323b2 49 // reserve memory for the linker
ms523 0:5934350323b2 50 static USB_INT08U HostBuf[0x200] __attribute__((at(HOSTBASEADDR)));
ms523 0:5934350323b2 51 /*
ms523 0:5934350323b2 52 **************************************************************************************************************
ms523 0:5934350323b2 53 * DELAY IN MILLI SECONDS
ms523 0:5934350323b2 54 *
ms523 0:5934350323b2 55 * Description: This function provides a delay in milli seconds
ms523 0:5934350323b2 56 *
ms523 0:5934350323b2 57 * Arguments : delay The delay required
ms523 0:5934350323b2 58 *
ms523 0:5934350323b2 59 * Returns : None
ms523 0:5934350323b2 60 *
ms523 0:5934350323b2 61 **************************************************************************************************************
ms523 0:5934350323b2 62 */
ms523 0:5934350323b2 63
ms523 0:5934350323b2 64 void Host_DelayMS (USB_INT32U delay)
ms523 0:5934350323b2 65 {
ms523 0:5934350323b2 66 volatile USB_INT32U i;
ms523 0:5934350323b2 67
ms523 0:5934350323b2 68
ms523 0:5934350323b2 69 for (i = 0; i < delay; i++) {
ms523 0:5934350323b2 70 Host_DelayUS(1000);
ms523 0:5934350323b2 71 }
ms523 0:5934350323b2 72 }
ms523 0:5934350323b2 73
ms523 0:5934350323b2 74 /*
ms523 0:5934350323b2 75 **************************************************************************************************************
ms523 0:5934350323b2 76 * DELAY IN MICRO SECONDS
ms523 0:5934350323b2 77 *
ms523 0:5934350323b2 78 * Description: This function provides a delay in micro seconds
ms523 0:5934350323b2 79 *
ms523 0:5934350323b2 80 * Arguments : delay The delay required
ms523 0:5934350323b2 81 *
ms523 0:5934350323b2 82 * Returns : None
ms523 0:5934350323b2 83 *
ms523 0:5934350323b2 84 **************************************************************************************************************
ms523 0:5934350323b2 85 */
ms523 0:5934350323b2 86
ms523 0:5934350323b2 87 void Host_DelayUS (USB_INT32U delay)
ms523 0:5934350323b2 88 {
ms523 0:5934350323b2 89 volatile USB_INT32U i;
ms523 0:5934350323b2 90
ms523 0:5934350323b2 91
ms523 0:5934350323b2 92 for (i = 0; i < (4 * delay); i++) { /* This logic was tested. It gives app. 1 micro sec delay */
ms523 0:5934350323b2 93 ;
ms523 0:5934350323b2 94 }
ms523 0:5934350323b2 95 }
ms523 0:5934350323b2 96
ms523 0:5934350323b2 97 // bits of the USB/OTG clock control register
ms523 0:5934350323b2 98 #define HOST_CLK_EN (1<<0)
ms523 0:5934350323b2 99 #define DEV_CLK_EN (1<<1)
ms523 0:5934350323b2 100 #define PORTSEL_CLK_EN (1<<3)
ms523 0:5934350323b2 101 #define AHB_CLK_EN (1<<4)
ms523 0:5934350323b2 102
ms523 0:5934350323b2 103 // bits of the USB/OTG clock status register
ms523 0:5934350323b2 104 #define HOST_CLK_ON (1<<0)
ms523 0:5934350323b2 105 #define DEV_CLK_ON (1<<1)
ms523 0:5934350323b2 106 #define PORTSEL_CLK_ON (1<<3)
ms523 0:5934350323b2 107 #define AHB_CLK_ON (1<<4)
ms523 0:5934350323b2 108
ms523 0:5934350323b2 109 // we need host clock, OTG/portsel clock and AHB clock
ms523 0:5934350323b2 110 #define CLOCK_MASK (HOST_CLK_EN | PORTSEL_CLK_EN | AHB_CLK_EN)
ms523 0:5934350323b2 111
ms523 0:5934350323b2 112 /*
ms523 0:5934350323b2 113 **************************************************************************************************************
ms523 0:5934350323b2 114 * INITIALIZE THE HOST CONTROLLER
ms523 0:5934350323b2 115 *
ms523 0:5934350323b2 116 * Description: This function initializes lpc17xx host controller
ms523 0:5934350323b2 117 *
ms523 0:5934350323b2 118 * Arguments : None
ms523 0:5934350323b2 119 *
ms523 0:5934350323b2 120 * Returns :
ms523 0:5934350323b2 121 *
ms523 0:5934350323b2 122 **************************************************************************************************************
ms523 0:5934350323b2 123 */
ms523 0:5934350323b2 124 void Host_Init (void)
ms523 0:5934350323b2 125 {
ms523 0:5934350323b2 126 PRINT_Log("In Host_Init\n");
ms523 0:5934350323b2 127 NVIC_DisableIRQ(USB_IRQn); /* Disable the USB interrupt source */
ms523 0:5934350323b2 128
ms523 0:5934350323b2 129 // turn on power for USB
ms523 0:5934350323b2 130 LPC_SC->PCONP |= (1UL<<31);
ms523 0:5934350323b2 131 // Enable USB host clock, port selection and AHB clock
ms523 0:5934350323b2 132 LPC_USB->USBClkCtrl |= CLOCK_MASK;
ms523 0:5934350323b2 133 // Wait for clocks to become available
ms523 0:5934350323b2 134 while ((LPC_USB->USBClkSt & CLOCK_MASK) != CLOCK_MASK)
ms523 0:5934350323b2 135 ;
ms523 0:5934350323b2 136
ms523 0:5934350323b2 137 // it seems the bits[0:1] mean the following
ms523 0:5934350323b2 138 // 0: U1=device, U2=host
ms523 0:5934350323b2 139 // 1: U1=host, U2=host
ms523 0:5934350323b2 140 // 2: reserved
ms523 0:5934350323b2 141 // 3: U1=host, U2=device
ms523 0:5934350323b2 142 // NB: this register is only available if OTG clock (aka "port select") is enabled!!
ms523 0:5934350323b2 143 // since we don't care about port 2, set just bit 0 to 1 (U1=host)
ms523 0:5934350323b2 144 LPC_USB->OTGStCtrl |= 1;
ms523 0:5934350323b2 145
ms523 0:5934350323b2 146 // now that we've configured the ports, we can turn off the portsel clock
ms523 0:5934350323b2 147 LPC_USB->USBClkCtrl &= ~PORTSEL_CLK_EN;
ms523 0:5934350323b2 148
ms523 0:5934350323b2 149 // power pins are not connected on mbed, so we can skip them
ms523 0:5934350323b2 150 /* P1[18] = USB_UP_LED, 01 */
ms523 0:5934350323b2 151 /* P1[19] = /USB_PPWR, 10 */
ms523 0:5934350323b2 152 /* P1[22] = USB_PWRD, 10 */
ms523 0:5934350323b2 153 /* P1[27] = /USB_OVRCR, 10 */
ms523 0:5934350323b2 154 /*LPC_PINCON->PINSEL3 &= ~((3<<4) | (3<<6) | (3<<12) | (3<<22));
ms523 0:5934350323b2 155 LPC_PINCON->PINSEL3 |= ((1<<4)|(2<<6) | (2<<12) | (2<<22)); // 0x00802080
ms523 0:5934350323b2 156 */
ms523 0:5934350323b2 157
ms523 0:5934350323b2 158 // configure USB D+/D- pins
ms523 0:5934350323b2 159 /* P0[29] = USB_D+, 01 */
ms523 0:5934350323b2 160 /* P0[30] = USB_D-, 01 */
ms523 0:5934350323b2 161 LPC_PINCON->PINSEL1 &= ~((3<<26) | (3<<28));
ms523 0:5934350323b2 162 LPC_PINCON->PINSEL1 |= ((1<<26)|(1<<28)); // 0x14000000
ms523 0:5934350323b2 163
ms523 0:5934350323b2 164 PRINT_Log("Initializing Host Stack\n");
ms523 0:5934350323b2 165
ms523 0:5934350323b2 166 Hcca = (volatile HCCA *)(HostBuf+0x000);
ms523 0:5934350323b2 167 TDHead = (volatile HCTD *)(HostBuf+0x100);
ms523 0:5934350323b2 168 TDTail = (volatile HCTD *)(HostBuf+0x110);
ms523 0:5934350323b2 169 EDCtrl = (volatile HCED *)(HostBuf+0x120);
ms523 0:5934350323b2 170 EDBulkIn = (volatile HCED *)(HostBuf+0x130);
ms523 0:5934350323b2 171 EDBulkOut = (volatile HCED *)(HostBuf+0x140);
ms523 0:5934350323b2 172 TDBuffer = (volatile USB_INT08U *)(HostBuf+0x150);
ms523 0:5934350323b2 173
ms523 0:5934350323b2 174 /* Initialize all the TDs, EDs and HCCA to 0 */
ms523 0:5934350323b2 175 Host_EDInit(EDCtrl);
ms523 0:5934350323b2 176 Host_EDInit(EDBulkIn);
ms523 0:5934350323b2 177 Host_EDInit(EDBulkOut);
ms523 0:5934350323b2 178 Host_TDInit(TDHead);
ms523 0:5934350323b2 179 Host_TDInit(TDTail);
ms523 0:5934350323b2 180 Host_HCCAInit(Hcca);
ms523 0:5934350323b2 181
ms523 0:5934350323b2 182 Host_DelayMS(50); /* Wait 50 ms before apply reset */
ms523 0:5934350323b2 183 LPC_USB->HcControl = 0; /* HARDWARE RESET */
ms523 0:5934350323b2 184 LPC_USB->HcControlHeadED = 0; /* Initialize Control list head to Zero */
ms523 0:5934350323b2 185 LPC_USB->HcBulkHeadED = 0; /* Initialize Bulk list head to Zero */
ms523 0:5934350323b2 186
ms523 0:5934350323b2 187 /* SOFTWARE RESET */
ms523 0:5934350323b2 188 LPC_USB->HcCommandStatus = OR_CMD_STATUS_HCR;
ms523 0:5934350323b2 189 LPC_USB->HcFmInterval = DEFAULT_FMINTERVAL; /* Write Fm Interval and Largest Data Packet Counter */
ms523 0:5934350323b2 190
ms523 0:5934350323b2 191 /* Put HC in operational state */
ms523 0:5934350323b2 192 LPC_USB->HcControl = (LPC_USB->HcControl & (~OR_CONTROL_HCFS)) | OR_CONTROL_HC_OPER;
ms523 0:5934350323b2 193 LPC_USB->HcRhStatus = OR_RH_STATUS_LPSC; /* Set Global Power */
ms523 0:5934350323b2 194
ms523 0:5934350323b2 195 LPC_USB->HcHCCA = (USB_INT32U)Hcca;
ms523 0:5934350323b2 196 LPC_USB->HcInterruptStatus |= LPC_USB->HcInterruptStatus; /* Clear Interrrupt Status */
ms523 0:5934350323b2 197
ms523 0:5934350323b2 198
ms523 0:5934350323b2 199 LPC_USB->HcInterruptEnable = OR_INTR_ENABLE_MIE |
ms523 0:5934350323b2 200 OR_INTR_ENABLE_WDH |
ms523 0:5934350323b2 201 OR_INTR_ENABLE_RHSC;
ms523 0:5934350323b2 202
ms523 0:5934350323b2 203 NVIC_SetPriority(USB_IRQn, 0); /* highest priority */
ms523 0:5934350323b2 204 /* Enable the USB Interrupt */
ms523 0:5934350323b2 205 NVIC_EnableIRQ(USB_IRQn);
ms523 0:5934350323b2 206 PRINT_Log("Host Initialized\n");
ms523 0:5934350323b2 207 }
ms523 0:5934350323b2 208
ms523 0:5934350323b2 209 /*
ms523 0:5934350323b2 210 **************************************************************************************************************
ms523 0:5934350323b2 211 * INTERRUPT SERVICE ROUTINE
ms523 0:5934350323b2 212 *
ms523 0:5934350323b2 213 * Description: This function services the interrupt caused by host controller
ms523 0:5934350323b2 214 *
ms523 0:5934350323b2 215 * Arguments : None
ms523 0:5934350323b2 216 *
ms523 0:5934350323b2 217 * Returns : None
ms523 0:5934350323b2 218 *
ms523 0:5934350323b2 219 **************************************************************************************************************
ms523 0:5934350323b2 220 */
ms523 0:5934350323b2 221
ms523 0:5934350323b2 222 void USB_IRQHandler (void) __irq
ms523 0:5934350323b2 223 {
ms523 0:5934350323b2 224 USB_INT32U int_status;
ms523 0:5934350323b2 225 USB_INT32U ie_status;
ms523 0:5934350323b2 226
ms523 0:5934350323b2 227 int_status = LPC_USB->HcInterruptStatus; /* Read Interrupt Status */
ms523 0:5934350323b2 228 ie_status = LPC_USB->HcInterruptEnable; /* Read Interrupt enable status */
ms523 0:5934350323b2 229
ms523 0:5934350323b2 230 if (!(int_status & ie_status)) {
ms523 0:5934350323b2 231 return;
ms523 0:5934350323b2 232 } else {
ms523 0:5934350323b2 233
ms523 0:5934350323b2 234 int_status = int_status & ie_status;
ms523 0:5934350323b2 235 if (int_status & OR_INTR_STATUS_RHSC) { /* Root hub status change interrupt */
ms523 0:5934350323b2 236 if (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_CSC) {
ms523 0:5934350323b2 237 if (LPC_USB->HcRhStatus & OR_RH_STATUS_DRWE) {
ms523 0:5934350323b2 238 /*
ms523 0:5934350323b2 239 * When DRWE is on, Connect Status Change
ms523 0:5934350323b2 240 * means a remote wakeup event.
ms523 0:5934350323b2 241 */
ms523 0:5934350323b2 242 HOST_RhscIntr = 1;// JUST SOMETHING FOR A BREAKPOINT
ms523 0:5934350323b2 243 }
ms523 0:5934350323b2 244 else {
ms523 0:5934350323b2 245 /*
ms523 0:5934350323b2 246 * When DRWE is off, Connect Status Change
ms523 0:5934350323b2 247 * is NOT a remote wakeup event
ms523 0:5934350323b2 248 */
ms523 0:5934350323b2 249 if (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_CCS) {
ms523 0:5934350323b2 250 if (!gUSBConnected) {
ms523 0:5934350323b2 251 HOST_TDControlStatus = 0;
ms523 0:5934350323b2 252 HOST_WdhIntr = 0;
ms523 0:5934350323b2 253 HOST_RhscIntr = 1;
ms523 0:5934350323b2 254 gUSBConnected = 1;
ms523 0:5934350323b2 255 }
ms523 0:5934350323b2 256 else
ms523 0:5934350323b2 257 PRINT_Log("Spurious status change (connected)?\n");
ms523 0:5934350323b2 258 } else {
ms523 0:5934350323b2 259 if (gUSBConnected) {
ms523 0:5934350323b2 260 LPC_USB->HcInterruptEnable = 0; // why do we get multiple disc. rupts???
ms523 0:5934350323b2 261 HOST_RhscIntr = 0;
ms523 0:5934350323b2 262 gUSBConnected = 0;
ms523 0:5934350323b2 263 }
ms523 0:5934350323b2 264 else
ms523 0:5934350323b2 265 PRINT_Log("Spurious status change (disconnected)?\n");
ms523 0:5934350323b2 266 }
ms523 0:5934350323b2 267 }
ms523 0:5934350323b2 268 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_CSC;
ms523 0:5934350323b2 269 }
ms523 0:5934350323b2 270 if (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_PRSC) {
ms523 0:5934350323b2 271 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC;
ms523 0:5934350323b2 272 }
ms523 0:5934350323b2 273 }
ms523 0:5934350323b2 274 if (int_status & OR_INTR_STATUS_WDH) { /* Writeback Done Head interrupt */
ms523 0:5934350323b2 275 HOST_WdhIntr = 1;
ms523 0:5934350323b2 276 HOST_TDControlStatus = (TDHead->Control >> 28) & 0xf;
ms523 0:5934350323b2 277 }
ms523 0:5934350323b2 278 LPC_USB->HcInterruptStatus = int_status; /* Clear interrupt status register */
ms523 0:5934350323b2 279 }
ms523 0:5934350323b2 280 return;
ms523 0:5934350323b2 281 }
ms523 0:5934350323b2 282
ms523 0:5934350323b2 283 /*
ms523 0:5934350323b2 284 **************************************************************************************************************
ms523 0:5934350323b2 285 * PROCESS TRANSFER DESCRIPTOR
ms523 0:5934350323b2 286 *
ms523 0:5934350323b2 287 * Description: This function processes the transfer descriptor
ms523 0:5934350323b2 288 *
ms523 0:5934350323b2 289 * Arguments : ed Endpoint descriptor that contains this transfer descriptor
ms523 0:5934350323b2 290 * token SETUP, IN, OUT
ms523 0:5934350323b2 291 * buffer Current Buffer Pointer of the transfer descriptor
ms523 0:5934350323b2 292 * buffer_len Length of the buffer
ms523 0:5934350323b2 293 *
ms523 0:5934350323b2 294 * Returns : OK if TD submission is successful
ms523 0:5934350323b2 295 * ERROR if TD submission fails
ms523 0:5934350323b2 296 *
ms523 0:5934350323b2 297 **************************************************************************************************************
ms523 0:5934350323b2 298 */
ms523 0:5934350323b2 299
ms523 0:5934350323b2 300 USB_INT32S Host_ProcessTD (volatile HCED *ed,
ms523 0:5934350323b2 301 volatile USB_INT32U token,
ms523 0:5934350323b2 302 volatile USB_INT08U *buffer,
ms523 0:5934350323b2 303 USB_INT32U buffer_len)
ms523 0:5934350323b2 304 {
ms523 0:5934350323b2 305 volatile USB_INT32U td_toggle;
ms523 0:5934350323b2 306
ms523 0:5934350323b2 307
ms523 0:5934350323b2 308 if (ed == EDCtrl) {
ms523 0:5934350323b2 309 if (token == TD_SETUP) {
ms523 0:5934350323b2 310 td_toggle = TD_TOGGLE_0;
ms523 0:5934350323b2 311 } else {
ms523 0:5934350323b2 312 td_toggle = TD_TOGGLE_1;
ms523 0:5934350323b2 313 }
ms523 0:5934350323b2 314 } else {
ms523 0:5934350323b2 315 td_toggle = 0;
ms523 0:5934350323b2 316 }
ms523 0:5934350323b2 317 TDHead->Control = (TD_ROUNDING |
ms523 0:5934350323b2 318 token |
ms523 0:5934350323b2 319 TD_DELAY_INT(0) |
ms523 0:5934350323b2 320 td_toggle |
ms523 0:5934350323b2 321 TD_CC);
ms523 0:5934350323b2 322 TDTail->Control = 0;
ms523 0:5934350323b2 323 TDHead->CurrBufPtr = (USB_INT32U) buffer;
ms523 0:5934350323b2 324 TDTail->CurrBufPtr = 0;
ms523 0:5934350323b2 325 TDHead->Next = (USB_INT32U) TDTail;
ms523 0:5934350323b2 326 TDTail->Next = 0;
ms523 0:5934350323b2 327 TDHead->BufEnd = (USB_INT32U)(buffer + (buffer_len - 1));
ms523 0:5934350323b2 328 TDTail->BufEnd = 0;
ms523 0:5934350323b2 329
ms523 0:5934350323b2 330 ed->HeadTd = (USB_INT32U)TDHead | ((ed->HeadTd) & 0x00000002);
ms523 0:5934350323b2 331 ed->TailTd = (USB_INT32U)TDTail;
ms523 0:5934350323b2 332 ed->Next = 0;
ms523 0:5934350323b2 333
ms523 0:5934350323b2 334 if (ed == EDCtrl) {
ms523 0:5934350323b2 335 LPC_USB->HcControlHeadED = (USB_INT32U)ed;
ms523 0:5934350323b2 336 LPC_USB->HcCommandStatus = LPC_USB->HcCommandStatus | OR_CMD_STATUS_CLF;
ms523 0:5934350323b2 337 LPC_USB->HcControl = LPC_USB->HcControl | OR_CONTROL_CLE;
ms523 0:5934350323b2 338 } else {
ms523 0:5934350323b2 339 LPC_USB->HcBulkHeadED = (USB_INT32U)ed;
ms523 0:5934350323b2 340 LPC_USB->HcCommandStatus = LPC_USB->HcCommandStatus | OR_CMD_STATUS_BLF;
ms523 0:5934350323b2 341 LPC_USB->HcControl = LPC_USB->HcControl | OR_CONTROL_BLE;
ms523 0:5934350323b2 342 }
ms523 0:5934350323b2 343
ms523 0:5934350323b2 344 Host_WDHWait();
ms523 0:5934350323b2 345
ms523 0:5934350323b2 346 // if (!(TDHead->Control & 0xF0000000)) {
ms523 0:5934350323b2 347 if (!HOST_TDControlStatus) {
ms523 0:5934350323b2 348 return (OK);
ms523 0:5934350323b2 349 } else {
ms523 0:5934350323b2 350 return (ERR_TD_FAIL);
ms523 0:5934350323b2 351 }
ms523 0:5934350323b2 352 }
ms523 0:5934350323b2 353
ms523 0:5934350323b2 354 /*
ms523 0:5934350323b2 355 **************************************************************************************************************
ms523 0:5934350323b2 356 * ENUMERATE THE DEVICE
ms523 0:5934350323b2 357 *
ms523 0:5934350323b2 358 * Description: This function is used to enumerate the device connected
ms523 0:5934350323b2 359 *
ms523 0:5934350323b2 360 * Arguments : None
ms523 0:5934350323b2 361 *
ms523 0:5934350323b2 362 * Returns : None
ms523 0:5934350323b2 363 *
ms523 0:5934350323b2 364 **************************************************************************************************************
ms523 0:5934350323b2 365 */
ms523 0:5934350323b2 366
ms523 0:5934350323b2 367 USB_INT32S Host_EnumDev (void)
ms523 0:5934350323b2 368 {
ms523 0:5934350323b2 369 USB_INT32S rc;
ms523 0:5934350323b2 370
ms523 0:5934350323b2 371 PRINT_Log("Connect a Mass Storage device\n");
ms523 0:5934350323b2 372 while (!HOST_RhscIntr)
ms523 0:5934350323b2 373 __WFI();
ms523 0:5934350323b2 374 Host_DelayMS(100); /* USB 2.0 spec says atleast 50ms delay beore port reset */
ms523 0:5934350323b2 375 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRS; // Initiate port reset
ms523 0:5934350323b2 376 while (LPC_USB->HcRhPortStatus1 & OR_RH_PORT_PRS)
ms523 0:5934350323b2 377 __WFI(); // Wait for port reset to complete...
ms523 0:5934350323b2 378 LPC_USB->HcRhPortStatus1 = OR_RH_PORT_PRSC; // ...and clear port reset signal
ms523 0:5934350323b2 379 Host_DelayMS(200); /* Wait for 100 MS after port reset */
ms523 0:5934350323b2 380
ms523 0:5934350323b2 381 EDCtrl->Control = 8 << 16; /* Put max pkt size = 8 */
ms523 0:5934350323b2 382 /* Read first 8 bytes of device desc */
ms523 0:5934350323b2 383 rc = HOST_GET_DESCRIPTOR(USB_DESCRIPTOR_TYPE_DEVICE, 0, TDBuffer, 8);
ms523 0:5934350323b2 384 if (rc != OK) {
ms523 0:5934350323b2 385 PRINT_Err(rc);
ms523 0:5934350323b2 386 return (rc);
ms523 0:5934350323b2 387 }
ms523 0:5934350323b2 388 EDCtrl->Control = TDBuffer[7] << 16; /* Get max pkt size of endpoint 0 */
ms523 0:5934350323b2 389 rc = HOST_SET_ADDRESS(1); /* Set the device address to 1 */
ms523 0:5934350323b2 390 if (rc != OK) {
ms523 0:5934350323b2 391 PRINT_Err(rc);
ms523 0:5934350323b2 392 return (rc);
ms523 0:5934350323b2 393 }
ms523 0:5934350323b2 394 Host_DelayMS(2);
ms523 0:5934350323b2 395 EDCtrl->Control = (EDCtrl->Control) | 1; /* Modify control pipe with address 1 */
ms523 0:5934350323b2 396 /* Get the configuration descriptor */
ms523 0:5934350323b2 397 rc = HOST_GET_DESCRIPTOR(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, TDBuffer, 9);
ms523 0:5934350323b2 398 if (rc != OK) {
ms523 0:5934350323b2 399 PRINT_Err(rc);
ms523 0:5934350323b2 400 return (rc);
ms523 0:5934350323b2 401 }
ms523 0:5934350323b2 402 /* Get the first configuration data */
ms523 0:5934350323b2 403 rc = HOST_GET_DESCRIPTOR(USB_DESCRIPTOR_TYPE_CONFIGURATION, 0, TDBuffer, ReadLE16U(&TDBuffer[2]));
ms523 0:5934350323b2 404 if (rc != OK) {
ms523 0:5934350323b2 405 PRINT_Err(rc);
ms523 0:5934350323b2 406 return (rc);
ms523 0:5934350323b2 407 }
ms523 0:5934350323b2 408 rc = MS_ParseConfiguration(); /* Parse the configuration */
ms523 0:5934350323b2 409 if (rc != OK) {
ms523 0:5934350323b2 410 PRINT_Err(rc);
ms523 0:5934350323b2 411 return (rc);
ms523 0:5934350323b2 412 }
ms523 0:5934350323b2 413 rc = USBH_SET_CONFIGURATION(1); /* Select device configuration 1 */
ms523 0:5934350323b2 414 if (rc != OK) {
ms523 0:5934350323b2 415 PRINT_Err(rc);
ms523 0:5934350323b2 416 }
ms523 0:5934350323b2 417 Host_DelayMS(100); /* Some devices may require this delay */
ms523 0:5934350323b2 418 return (rc);
ms523 0:5934350323b2 419 }
ms523 0:5934350323b2 420
ms523 0:5934350323b2 421 /*
ms523 0:5934350323b2 422 **************************************************************************************************************
ms523 0:5934350323b2 423 * RECEIVE THE CONTROL INFORMATION
ms523 0:5934350323b2 424 *
ms523 0:5934350323b2 425 * Description: This function is used to receive the control information
ms523 0:5934350323b2 426 *
ms523 0:5934350323b2 427 * Arguments : bm_request_type
ms523 0:5934350323b2 428 * b_request
ms523 0:5934350323b2 429 * w_value
ms523 0:5934350323b2 430 * w_index
ms523 0:5934350323b2 431 * w_length
ms523 0:5934350323b2 432 * buffer
ms523 0:5934350323b2 433 *
ms523 0:5934350323b2 434 * Returns : OK if Success
ms523 0:5934350323b2 435 * ERROR if Failed
ms523 0:5934350323b2 436 *
ms523 0:5934350323b2 437 **************************************************************************************************************
ms523 0:5934350323b2 438 */
ms523 0:5934350323b2 439
ms523 0:5934350323b2 440 USB_INT32S Host_CtrlRecv ( USB_INT08U bm_request_type,
ms523 0:5934350323b2 441 USB_INT08U b_request,
ms523 0:5934350323b2 442 USB_INT16U w_value,
ms523 0:5934350323b2 443 USB_INT16U w_index,
ms523 0:5934350323b2 444 USB_INT16U w_length,
ms523 0:5934350323b2 445 volatile USB_INT08U *buffer)
ms523 0:5934350323b2 446 {
ms523 0:5934350323b2 447 USB_INT32S rc;
ms523 0:5934350323b2 448
ms523 0:5934350323b2 449
ms523 0:5934350323b2 450 Host_FillSetup(bm_request_type, b_request, w_value, w_index, w_length);
ms523 0:5934350323b2 451 rc = Host_ProcessTD(EDCtrl, TD_SETUP, TDBuffer, 8);
ms523 0:5934350323b2 452 if (rc == OK) {
ms523 0:5934350323b2 453 if (w_length) {
ms523 0:5934350323b2 454 rc = Host_ProcessTD(EDCtrl, TD_IN, TDBuffer, w_length);
ms523 0:5934350323b2 455 }
ms523 0:5934350323b2 456 if (rc == OK) {
ms523 0:5934350323b2 457 rc = Host_ProcessTD(EDCtrl, TD_OUT, NULL, 0);
ms523 0:5934350323b2 458 }
ms523 0:5934350323b2 459 }
ms523 0:5934350323b2 460 return (rc);
ms523 0:5934350323b2 461 }
ms523 0:5934350323b2 462
ms523 0:5934350323b2 463 /*
ms523 0:5934350323b2 464 **************************************************************************************************************
ms523 0:5934350323b2 465 * SEND THE CONTROL INFORMATION
ms523 0:5934350323b2 466 *
ms523 0:5934350323b2 467 * Description: This function is used to send the control information
ms523 0:5934350323b2 468 *
ms523 0:5934350323b2 469 * Arguments : None
ms523 0:5934350323b2 470 *
ms523 0:5934350323b2 471 * Returns : OK if Success
ms523 0:5934350323b2 472 * ERR_INVALID_BOOTSIG if Failed
ms523 0:5934350323b2 473 *
ms523 0:5934350323b2 474 **************************************************************************************************************
ms523 0:5934350323b2 475 */
ms523 0:5934350323b2 476
ms523 0:5934350323b2 477 USB_INT32S Host_CtrlSend ( USB_INT08U bm_request_type,
ms523 0:5934350323b2 478 USB_INT08U b_request,
ms523 0:5934350323b2 479 USB_INT16U w_value,
ms523 0:5934350323b2 480 USB_INT16U w_index,
ms523 0:5934350323b2 481 USB_INT16U w_length,
ms523 0:5934350323b2 482 volatile USB_INT08U *buffer)
ms523 0:5934350323b2 483 {
ms523 0:5934350323b2 484 USB_INT32S rc;
ms523 0:5934350323b2 485
ms523 0:5934350323b2 486
ms523 0:5934350323b2 487 Host_FillSetup(bm_request_type, b_request, w_value, w_index, w_length);
ms523 0:5934350323b2 488
ms523 0:5934350323b2 489 rc = Host_ProcessTD(EDCtrl, TD_SETUP, TDBuffer, 8);
ms523 0:5934350323b2 490 if (rc == OK) {
ms523 0:5934350323b2 491 if (w_length) {
ms523 0:5934350323b2 492 rc = Host_ProcessTD(EDCtrl, TD_OUT, TDBuffer, w_length);
ms523 0:5934350323b2 493 }
ms523 0:5934350323b2 494 if (rc == OK) {
ms523 0:5934350323b2 495 rc = Host_ProcessTD(EDCtrl, TD_IN, NULL, 0);
ms523 0:5934350323b2 496 }
ms523 0:5934350323b2 497 }
ms523 0:5934350323b2 498 return (rc);
ms523 0:5934350323b2 499 }
ms523 0:5934350323b2 500
ms523 0:5934350323b2 501 /*
ms523 0:5934350323b2 502 **************************************************************************************************************
ms523 0:5934350323b2 503 * FILL SETUP PACKET
ms523 0:5934350323b2 504 *
ms523 0:5934350323b2 505 * Description: This function is used to fill the setup packet
ms523 0:5934350323b2 506 *
ms523 0:5934350323b2 507 * Arguments : None
ms523 0:5934350323b2 508 *
ms523 0:5934350323b2 509 * Returns : OK if Success
ms523 0:5934350323b2 510 * ERR_INVALID_BOOTSIG if Failed
ms523 0:5934350323b2 511 *
ms523 0:5934350323b2 512 **************************************************************************************************************
ms523 0:5934350323b2 513 */
ms523 0:5934350323b2 514
ms523 0:5934350323b2 515 void Host_FillSetup (USB_INT08U bm_request_type,
ms523 0:5934350323b2 516 USB_INT08U b_request,
ms523 0:5934350323b2 517 USB_INT16U w_value,
ms523 0:5934350323b2 518 USB_INT16U w_index,
ms523 0:5934350323b2 519 USB_INT16U w_length)
ms523 0:5934350323b2 520 {
ms523 0:5934350323b2 521 int i;
ms523 0:5934350323b2 522 for (i=0;i<w_length;i++)
ms523 0:5934350323b2 523 TDBuffer[i] = 0;
ms523 0:5934350323b2 524
ms523 0:5934350323b2 525 TDBuffer[0] = bm_request_type;
ms523 0:5934350323b2 526 TDBuffer[1] = b_request;
ms523 0:5934350323b2 527 WriteLE16U(&TDBuffer[2], w_value);
ms523 0:5934350323b2 528 WriteLE16U(&TDBuffer[4], w_index);
ms523 0:5934350323b2 529 WriteLE16U(&TDBuffer[6], w_length);
ms523 0:5934350323b2 530 }
ms523 0:5934350323b2 531
ms523 0:5934350323b2 532
ms523 0:5934350323b2 533
ms523 0:5934350323b2 534 /*
ms523 0:5934350323b2 535 **************************************************************************************************************
ms523 0:5934350323b2 536 * INITIALIZE THE TRANSFER DESCRIPTOR
ms523 0:5934350323b2 537 *
ms523 0:5934350323b2 538 * Description: This function initializes transfer descriptor
ms523 0:5934350323b2 539 *
ms523 0:5934350323b2 540 * Arguments : Pointer to TD structure
ms523 0:5934350323b2 541 *
ms523 0:5934350323b2 542 * Returns : None
ms523 0:5934350323b2 543 *
ms523 0:5934350323b2 544 **************************************************************************************************************
ms523 0:5934350323b2 545 */
ms523 0:5934350323b2 546
ms523 0:5934350323b2 547 void Host_TDInit (volatile HCTD *td)
ms523 0:5934350323b2 548 {
ms523 0:5934350323b2 549
ms523 0:5934350323b2 550 td->Control = 0;
ms523 0:5934350323b2 551 td->CurrBufPtr = 0;
ms523 0:5934350323b2 552 td->Next = 0;
ms523 0:5934350323b2 553 td->BufEnd = 0;
ms523 0:5934350323b2 554 }
ms523 0:5934350323b2 555
ms523 0:5934350323b2 556 /*
ms523 0:5934350323b2 557 **************************************************************************************************************
ms523 0:5934350323b2 558 * INITIALIZE THE ENDPOINT DESCRIPTOR
ms523 0:5934350323b2 559 *
ms523 0:5934350323b2 560 * Description: This function initializes endpoint descriptor
ms523 0:5934350323b2 561 *
ms523 0:5934350323b2 562 * Arguments : Pointer to ED strcuture
ms523 0:5934350323b2 563 *
ms523 0:5934350323b2 564 * Returns : None
ms523 0:5934350323b2 565 *
ms523 0:5934350323b2 566 **************************************************************************************************************
ms523 0:5934350323b2 567 */
ms523 0:5934350323b2 568
ms523 0:5934350323b2 569 void Host_EDInit (volatile HCED *ed)
ms523 0:5934350323b2 570 {
ms523 0:5934350323b2 571
ms523 0:5934350323b2 572 ed->Control = 0;
ms523 0:5934350323b2 573 ed->TailTd = 0;
ms523 0:5934350323b2 574 ed->HeadTd = 0;
ms523 0:5934350323b2 575 ed->Next = 0;
ms523 0:5934350323b2 576 }
ms523 0:5934350323b2 577
ms523 0:5934350323b2 578 /*
ms523 0:5934350323b2 579 **************************************************************************************************************
ms523 0:5934350323b2 580 * INITIALIZE HOST CONTROLLER COMMUNICATIONS AREA
ms523 0:5934350323b2 581 *
ms523 0:5934350323b2 582 * Description: This function initializes host controller communications area
ms523 0:5934350323b2 583 *
ms523 0:5934350323b2 584 * Arguments : Pointer to HCCA
ms523 0:5934350323b2 585 *
ms523 0:5934350323b2 586 * Returns :
ms523 0:5934350323b2 587 *
ms523 0:5934350323b2 588 **************************************************************************************************************
ms523 0:5934350323b2 589 */
ms523 0:5934350323b2 590
ms523 0:5934350323b2 591 void Host_HCCAInit (volatile HCCA *hcca)
ms523 0:5934350323b2 592 {
ms523 0:5934350323b2 593 USB_INT32U i;
ms523 0:5934350323b2 594
ms523 0:5934350323b2 595
ms523 0:5934350323b2 596 for (i = 0; i < 32; i++) {
ms523 0:5934350323b2 597
ms523 0:5934350323b2 598 hcca->IntTable[i] = 0;
ms523 0:5934350323b2 599 hcca->FrameNumber = 0;
ms523 0:5934350323b2 600 hcca->DoneHead = 0;
ms523 0:5934350323b2 601 }
ms523 0:5934350323b2 602
ms523 0:5934350323b2 603 }
ms523 0:5934350323b2 604
ms523 0:5934350323b2 605 /*
ms523 0:5934350323b2 606 **************************************************************************************************************
ms523 0:5934350323b2 607 * WAIT FOR WDH INTERRUPT
ms523 0:5934350323b2 608 *
ms523 0:5934350323b2 609 * Description: This function is infinite loop which breaks when ever a WDH interrupt rises
ms523 0:5934350323b2 610 *
ms523 0:5934350323b2 611 * Arguments : None
ms523 0:5934350323b2 612 *
ms523 0:5934350323b2 613 * Returns : None
ms523 0:5934350323b2 614 *
ms523 0:5934350323b2 615 **************************************************************************************************************
ms523 0:5934350323b2 616 */
ms523 0:5934350323b2 617
ms523 0:5934350323b2 618 void Host_WDHWait (void)
ms523 0:5934350323b2 619 {
ms523 0:5934350323b2 620 while (!HOST_WdhIntr)
ms523 0:5934350323b2 621 __WFI();
ms523 0:5934350323b2 622
ms523 0:5934350323b2 623 HOST_WdhIntr = 0;
ms523 0:5934350323b2 624 }
ms523 0:5934350323b2 625
ms523 0:5934350323b2 626 /*
ms523 0:5934350323b2 627 **************************************************************************************************************
ms523 0:5934350323b2 628 * READ LE 32U
ms523 0:5934350323b2 629 *
ms523 0:5934350323b2 630 * Description: This function is used to read an unsigned integer from a character buffer in the platform
ms523 0:5934350323b2 631 * containing little endian processor
ms523 0:5934350323b2 632 *
ms523 0:5934350323b2 633 * Arguments : pmem Pointer to the character buffer
ms523 0:5934350323b2 634 *
ms523 0:5934350323b2 635 * Returns : val Unsigned integer
ms523 0:5934350323b2 636 *
ms523 0:5934350323b2 637 **************************************************************************************************************
ms523 0:5934350323b2 638 */
ms523 0:5934350323b2 639
ms523 0:5934350323b2 640 USB_INT32U ReadLE32U (volatile USB_INT08U *pmem)
ms523 0:5934350323b2 641 {
ms523 0:5934350323b2 642 USB_INT32U val = *(USB_INT32U*)pmem;
ms523 0:5934350323b2 643 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 644 return __REV(val);
ms523 0:5934350323b2 645 #else
ms523 0:5934350323b2 646 return val;
ms523 0:5934350323b2 647 #endif
ms523 0:5934350323b2 648 }
ms523 0:5934350323b2 649
ms523 0:5934350323b2 650 /*
ms523 0:5934350323b2 651 **************************************************************************************************************
ms523 0:5934350323b2 652 * WRITE LE 32U
ms523 0:5934350323b2 653 *
ms523 0:5934350323b2 654 * Description: This function is used to write an unsigned integer into a charecter buffer in the platform
ms523 0:5934350323b2 655 * containing little endian processor.
ms523 0:5934350323b2 656 *
ms523 0:5934350323b2 657 * Arguments : pmem Pointer to the charecter buffer
ms523 0:5934350323b2 658 * val Integer value to be placed in the charecter buffer
ms523 0:5934350323b2 659 *
ms523 0:5934350323b2 660 * Returns : None
ms523 0:5934350323b2 661 *
ms523 0:5934350323b2 662 **************************************************************************************************************
ms523 0:5934350323b2 663 */
ms523 0:5934350323b2 664
ms523 0:5934350323b2 665 void WriteLE32U (volatile USB_INT08U *pmem,
ms523 0:5934350323b2 666 USB_INT32U val)
ms523 0:5934350323b2 667 {
ms523 0:5934350323b2 668 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 669 *(USB_INT32U*)pmem = __REV(val);
ms523 0:5934350323b2 670 #else
ms523 0:5934350323b2 671 *(USB_INT32U*)pmem = val;
ms523 0:5934350323b2 672 #endif
ms523 0:5934350323b2 673 }
ms523 0:5934350323b2 674
ms523 0:5934350323b2 675 /*
ms523 0:5934350323b2 676 **************************************************************************************************************
ms523 0:5934350323b2 677 * READ LE 16U
ms523 0:5934350323b2 678 *
ms523 0:5934350323b2 679 * Description: This function is used to read an unsigned short integer from a charecter buffer in the platform
ms523 0:5934350323b2 680 * containing little endian processor
ms523 0:5934350323b2 681 *
ms523 0:5934350323b2 682 * Arguments : pmem Pointer to the charecter buffer
ms523 0:5934350323b2 683 *
ms523 0:5934350323b2 684 * Returns : val Unsigned short integer
ms523 0:5934350323b2 685 *
ms523 0:5934350323b2 686 **************************************************************************************************************
ms523 0:5934350323b2 687 */
ms523 0:5934350323b2 688
ms523 0:5934350323b2 689 USB_INT16U ReadLE16U (volatile USB_INT08U *pmem)
ms523 0:5934350323b2 690 {
ms523 0:5934350323b2 691 USB_INT16U val = *(USB_INT16U*)pmem;
ms523 0:5934350323b2 692 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 693 return __REV16(val);
ms523 0:5934350323b2 694 #else
ms523 0:5934350323b2 695 return val;
ms523 0:5934350323b2 696 #endif
ms523 0:5934350323b2 697 }
ms523 0:5934350323b2 698
ms523 0:5934350323b2 699 /*
ms523 0:5934350323b2 700 **************************************************************************************************************
ms523 0:5934350323b2 701 * WRITE LE 16U
ms523 0:5934350323b2 702 *
ms523 0:5934350323b2 703 * Description: This function is used to write an unsigned short integer into a charecter buffer in the
ms523 0:5934350323b2 704 * platform containing little endian processor
ms523 0:5934350323b2 705 *
ms523 0:5934350323b2 706 * Arguments : pmem Pointer to the charecter buffer
ms523 0:5934350323b2 707 * val Value to be placed in the charecter buffer
ms523 0:5934350323b2 708 *
ms523 0:5934350323b2 709 * Returns : None
ms523 0:5934350323b2 710 *
ms523 0:5934350323b2 711 **************************************************************************************************************
ms523 0:5934350323b2 712 */
ms523 0:5934350323b2 713
ms523 0:5934350323b2 714 void WriteLE16U (volatile USB_INT08U *pmem,
ms523 0:5934350323b2 715 USB_INT16U val)
ms523 0:5934350323b2 716 {
ms523 0:5934350323b2 717 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 718 *(USB_INT16U*)pmem = (__REV16(val) & 0xFFFF);
ms523 0:5934350323b2 719 #else
ms523 0:5934350323b2 720 *(USB_INT16U*)pmem = val;
ms523 0:5934350323b2 721 #endif
ms523 0:5934350323b2 722 }
ms523 0:5934350323b2 723
ms523 0:5934350323b2 724 /*
ms523 0:5934350323b2 725 **************************************************************************************************************
ms523 0:5934350323b2 726 * READ BE 32U
ms523 0:5934350323b2 727 *
ms523 0:5934350323b2 728 * Description: This function is used to read an unsigned integer from a charecter buffer in the platform
ms523 0:5934350323b2 729 * containing big endian processor
ms523 0:5934350323b2 730 *
ms523 0:5934350323b2 731 * Arguments : pmem Pointer to the charecter buffer
ms523 0:5934350323b2 732 *
ms523 0:5934350323b2 733 * Returns : val Unsigned integer
ms523 0:5934350323b2 734 *
ms523 0:5934350323b2 735 **************************************************************************************************************
ms523 0:5934350323b2 736 */
ms523 0:5934350323b2 737
ms523 0:5934350323b2 738 USB_INT32U ReadBE32U (volatile USB_INT08U *pmem)
ms523 0:5934350323b2 739 {
ms523 0:5934350323b2 740 USB_INT32U val = *(USB_INT32U*)pmem;
ms523 0:5934350323b2 741 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 742 return val;
ms523 0:5934350323b2 743 #else
ms523 0:5934350323b2 744 return __REV(val);
ms523 0:5934350323b2 745 #endif
ms523 0:5934350323b2 746 }
ms523 0:5934350323b2 747
ms523 0:5934350323b2 748 /*
ms523 0:5934350323b2 749 **************************************************************************************************************
ms523 0:5934350323b2 750 * WRITE BE 32U
ms523 0:5934350323b2 751 *
ms523 0:5934350323b2 752 * Description: This function is used to write an unsigned integer into a charecter buffer in the platform
ms523 0:5934350323b2 753 * containing big endian processor
ms523 0:5934350323b2 754 *
ms523 0:5934350323b2 755 * Arguments : pmem Pointer to the charecter buffer
ms523 0:5934350323b2 756 * val Value to be placed in the charecter buffer
ms523 0:5934350323b2 757 *
ms523 0:5934350323b2 758 * Returns : None
ms523 0:5934350323b2 759 *
ms523 0:5934350323b2 760 **************************************************************************************************************
ms523 0:5934350323b2 761 */
ms523 0:5934350323b2 762
ms523 0:5934350323b2 763 void WriteBE32U (volatile USB_INT08U *pmem,
ms523 0:5934350323b2 764 USB_INT32U val)
ms523 0:5934350323b2 765 {
ms523 0:5934350323b2 766 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 767 *(USB_INT32U*)pmem = val;
ms523 0:5934350323b2 768 #else
ms523 0:5934350323b2 769 *(USB_INT32U*)pmem = __REV(val);
ms523 0:5934350323b2 770 #endif
ms523 0:5934350323b2 771 }
ms523 0:5934350323b2 772
ms523 0:5934350323b2 773 /*
ms523 0:5934350323b2 774 **************************************************************************************************************
ms523 0:5934350323b2 775 * READ BE 16U
ms523 0:5934350323b2 776 *
ms523 0:5934350323b2 777 * Description: This function is used to read an unsigned short integer from a charecter buffer in the platform
ms523 0:5934350323b2 778 * containing big endian processor
ms523 0:5934350323b2 779 *
ms523 0:5934350323b2 780 * Arguments : pmem Pointer to the charecter buffer
ms523 0:5934350323b2 781 *
ms523 0:5934350323b2 782 * Returns : val Unsigned short integer
ms523 0:5934350323b2 783 *
ms523 0:5934350323b2 784 **************************************************************************************************************
ms523 0:5934350323b2 785 */
ms523 0:5934350323b2 786
ms523 0:5934350323b2 787 USB_INT16U ReadBE16U (volatile USB_INT08U *pmem)
ms523 0:5934350323b2 788 {
ms523 0:5934350323b2 789 USB_INT16U val = *(USB_INT16U*)pmem;
ms523 0:5934350323b2 790 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 791 return val;
ms523 0:5934350323b2 792 #else
ms523 0:5934350323b2 793 return __REV16(val);
ms523 0:5934350323b2 794 #endif
ms523 0:5934350323b2 795 }
ms523 0:5934350323b2 796
ms523 0:5934350323b2 797 /*
ms523 0:5934350323b2 798 **************************************************************************************************************
ms523 0:5934350323b2 799 * WRITE BE 16U
ms523 0:5934350323b2 800 *
ms523 0:5934350323b2 801 * Description: This function is used to write an unsigned short integer into the charecter buffer in the
ms523 0:5934350323b2 802 * platform containing big endian processor
ms523 0:5934350323b2 803 *
ms523 0:5934350323b2 804 * Arguments : pmem Pointer to the charecter buffer
ms523 0:5934350323b2 805 * val Value to be placed in the charecter buffer
ms523 0:5934350323b2 806 *
ms523 0:5934350323b2 807 * Returns : None
ms523 0:5934350323b2 808 *
ms523 0:5934350323b2 809 **************************************************************************************************************
ms523 0:5934350323b2 810 */
ms523 0:5934350323b2 811
ms523 0:5934350323b2 812 void WriteBE16U (volatile USB_INT08U *pmem,
ms523 0:5934350323b2 813 USB_INT16U val)
ms523 0:5934350323b2 814 {
ms523 0:5934350323b2 815 #ifdef __BIG_ENDIAN
ms523 0:5934350323b2 816 *(USB_INT16U*)pmem = val;
ms523 0:5934350323b2 817 #else
ms523 0:5934350323b2 818 *(USB_INT16U*)pmem = (__REV16(val) & 0xFFFF);
ms523 0:5934350323b2 819 #endif
ms523 0:5934350323b2 820 }