LPCOpen USB example - hardfault using custom hardware

cancel
Showing results for 
Show  only  | Search instead for 
Did you mean: 

LPCOpen USB example - hardfault using custom hardware

1,858 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by DennisFrie on Sat Jul 05 12:09:00 MST 2014
Hi guys
I'm trying to verify the USB-interface on a platform with LPC1548.

Using LPCOpen and the LPCXpresso 1549 dev. board, the USB examples works as expected.
However, when testing with the custom hardware, I get a hardfault error, that I simply can't find.

Example used:
usbd_rom_cdc

Changed in sysinit.c
In Board_SetupMuxing I've removed all pin-configs and only use:
Chip_IOCON_PinMuxSet(LPC_IOCON, 1, 6, (IOCON_MODE_PULLDOWN | IOCON_DIGMODE_EN)); // USB_VBUS on custrom hardware
Chip_IOCON_PinMuxSet(LPC_IOCON, 1, 11, (IOCON_MODE_PULLDOWN | IOCON_DIGMODE_EN)); // USB_VBUS on LPCXpresso dev board

//Chip_SWM_MovablePinAssign(SWM_USB_VBUS_I, 38); // For testing custom hardware
Chip_SWM_MovablePinAssign(SWM_USB_VBUS_I, 43); // For testing on dev. board 


In main:
Board_init removed and only Chip_GPIO_Init(LPC_GPIO) called.

Testing with the dev. the code runs just fine and USB is detected when connected.
When using the custom hardware, the initialization ends in a hardfault error.

This is the last function called, that seems to be causing the problem:
ret = vcom_init(g_hUsb, &desc, &usb_param);

More specific in that function, this is the last call that happens before the hardfault
ret = USBD_API->cdc->init(hUsb, &cdc_param, &g_vCOM.hCdc);

Any good suggestions as to what I'm missing here?
Project settings have been changed to LPC1548 as microcontroller, which loads just fine on LPC1549.

Code copy-pasted here just for quick reference.
Main function:
int main(void)
{
USBD_API_INIT_PARAM_T usb_param;
USB_CORE_DESCS_T desc;
ErrorCode_t ret = LPC_OK;
uint32_t prompt = 0, rdCnt = 0;

SystemCoreClockUpdate();
/* Initialize board and chip */
//Board_Init();

Chip_GPIO_Init(LPC_GPIO);

/* enable clocks */
Chip_USB_Init();

/* initialize USBD ROM API pointer. */
g_pUsbApi = (const USBD_API_T *) LPC_ROM_API->pUSBD;

/* initialize call back structures */
memset((void *) &usb_param, 0, sizeof(USBD_API_INIT_PARAM_T));
usb_param.usb_reg_base = LPC_USB0_BASE;
/*WORKAROUND for artf44835 ROM driver BUG:
    Code clearing STALL bits in endpoint reset routine corrupts memory area
    next to the endpoint control data. For example When EP0, EP1_IN, EP1_OUT,
    EP2_IN are used we need to specify 3 here. But as a workaround for this
    issue specify 4. So that extra EPs control structure acts as padding buffer
    to avoid data corruption. Corruption of padding memory doesn’t affect the
    stack/program behaviour.
 */
usb_param.max_num_ep = 3 + 1;
usb_param.mem_base = USB_STACK_MEM_BASE;
usb_param.mem_size = USB_STACK_MEM_SIZE;

/* Set the USB descriptors */
desc.device_desc = (uint8_t *) &USB_DeviceDescriptor[0];
desc.string_desc = (uint8_t *) &USB_StringDescriptor[0];
/* Note, to pass USBCV test full-speed only devices should have both
   descriptor arrays point to same location and device_qualifier set to 0.
 */
desc.high_speed_desc = (uint8_t *) &USB_FsConfigDescriptor[0];
desc.full_speed_desc = (uint8_t *) &USB_FsConfigDescriptor[0];
desc.device_qualifier = 0;

/* USB Initialization */
ret = USBD_API->hw->Init(&g_hUsb, &desc, &usb_param);
if (ret == LPC_OK) {

/* Init VCOM interface */
ret = vcom_init(g_hUsb, &desc, &usb_param);
if (ret == LPC_OK) {
/*  enable USB interrupts */
NVIC_EnableIRQ(USB0_IRQn);
/* now connect */
USBD_API->hw->Connect(g_hUsb, 1);
}

}


vcom_init function
/* Virtual com port init routine */
ErrorCode_t vcom_init(USBD_HANDLE_T hUsb, USB_CORE_DESCS_T *pDesc, USBD_API_INIT_PARAM_T *pUsbParam)
{
USBD_CDC_INIT_PARAM_T cdc_param;
ErrorCode_t ret = LPC_OK;
uint32_t ep_indx;

g_vCOM.hUsb = hUsb;
memset((void *) &cdc_param, 0, sizeof(USBD_CDC_INIT_PARAM_T));
cdc_param.mem_base = pUsbParam->mem_base;
cdc_param.mem_size = pUsbParam->mem_size;
cdc_param.cif_intf_desc = (uint8_t *) find_IntfDesc(pDesc->high_speed_desc, CDC_COMMUNICATION_INTERFACE_CLASS);
cdc_param.dif_intf_desc = (uint8_t *) find_IntfDesc(pDesc->high_speed_desc, CDC_DATA_INTERFACE_CLASS);
cdc_param.SetLineCode = VCOM_SetLineCode;

ret = USBD_API->cdc->init(hUsb, &cdc_param, &g_vCOM.hCdc);

if (ret == LPC_OK) {
/* allocate transfer buffers */
g_vCOM.rx_buff = (uint8_t *) cdc_param.mem_base;
cdc_param.mem_base += VCOM_RX_BUF_SZ;
cdc_param.mem_size -= VCOM_RX_BUF_SZ;

/* register endpoint interrupt handler */
ep_indx = (((USB_CDC_IN_EP & 0x0F) << 1) + 1);
ret = USBD_API->core->RegisterEpHandler(hUsb, ep_indx, VCOM_bulk_in_hdlr, &g_vCOM);
if (ret == LPC_OK) {
/* register endpoint interrupt handler */
ep_indx = ((USB_CDC_OUT_EP & 0x0F) << 1);
ret = USBD_API->core->RegisterEpHandler(hUsb, ep_indx, VCOM_bulk_out_hdlr, &g_vCOM);

}
/* update mem_base and size variables for cascading calls. */
pUsbParam->mem_base = cdc_param.mem_base;
pUsbParam->mem_size = cdc_param.mem_size;
}

return ret;
}
Labels (1)
0 Kudos
Reply
8 Replies

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by DennisFrie on Sun Jul 06 16:40:17 MST 2014
I think you just saved my day, that explains the behavior I've seen. I didn't notice the difference in USB memory allocation between LPC1549 and LPC1548.

I will get it tested asap and report back.

Much appreciated, thanks!
0 Kudos
Reply

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by Tsuneo on Sun Jul 06 09:24:32 MST 2014
LPC1548 has reduced SRAM size than LPC1549

LPC1549 : 0x0200 0000 - 0x0200 8FFF  36K Bytes
LPC1548 : 0x0200 0000 - 0x0200 4FFF  20K Bytes

The USB stack working space, passed to the ROM driver, should be moved to the lower address.
Otherwise, you'll see HardFault (access to absent memory) in the ROM driver.

In this version of LPCOpen (v2.08c),
http://www.lpcware.com/system/files/lpcopen_2_08c_lpcxpresso_nxp_lpcxpresso_1549.zip

the stack working space is defined in this macro,
lpcopen_2_08c_lpcxpresso_nxp_lpcxpresso_1549\usbd_rom_cdc\example\inc\app_usbd_cfg.h

#define USB_STACK_MEM_BASE      0x02008000

Move it to 0x02004000

Tsuneo
0 Kudos
Reply

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by DennisFrie on Sat Jul 05 14:32:33 MST 2014
I have pull-up on both PIO1_11 and PIO1_9 :)
Gotta admit, I haven't tried the dev. board with modifications on PIO1_11/9
0 Kudos
Reply

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by LabRat on Sat Jul 05 14:25:47 MST 2014
Doesn't look too wrong...

Is there no pull-up at PIO1_11 (ISP_1)? 

Did you try the original sample & board without connected V_BUS and pull-up at PIO1_11 and PIO1_9 (ISP_0)?
0 Kudos
Reply

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by DennisFrie on Sat Jul 05 14:08:35 MST 2014
It works just fine with the dev. board here too, but for some reason, it causes hardfault with my own hardware. Except for USB the hardware have been working perfect so far.

The USB-interface is more or less the same as the dev. board, I don't see anything obvious that would cause this problem
[img]https://dl.dropboxusercontent.com/u/3947315/USB_part.png[/img]
0 Kudos
Reply

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by LabRat on Sat Jul 05 13:54:28 MST 2014
IIRC I've used this sample with my own (1549-LQFP64) boards in March without problems...

Just tried the original sample with my board and original LPCXpresso board library. Working without problems...

Perhaps you want to post USB part of your board schematic....
0 Kudos
Reply

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by DennisFrie on Sat Jul 05 13:42:52 MST 2014
Thanks for your quick reply
It's a LQFP64 too, so the difference between the 2 micro controllers should be minimal.

Atm I'm use the example sketch included in LPCOpen "usbd_rom_cdc", which seems to be a normal c-project.

Not quite sure I follow in regard to USB_IRQ naming, unless I'm mistaken, everything in that regard is exactly the same for LPC1549 and LPC1548?
Also, the hardfault happens before the IRQ is enabled.
0 Kudos
Reply

1,497 Views
lpcware
NXP Employee
NXP Employee
Content originally posted in LPCWare by LabRat on Sat Jul 05 13:24:42 MST 2014

Quote: DennisFrie
I'm trying to verify the USB-interface on a platform with LPC1548.



LQFP48, LQFP64 or LQFP100  :quest:  :quest:  :quest:

Is it a C++ project?

Did you compare Startup USB-IRQ name and function USB-IRQ name already?
0 Kudos
Reply