This discussion has been locked.
You can no longer post new replies to this discussion. If you have a question you can start a new discussion

USB Host HID Class Example for LPC2468

Hello,

I am hoping to setup my LPC2468 to act as a USB Host and to work with the HID Class. I am wondering if anyone has suggestions on example code or reading material?

I have gotten Keil's USB HID Client working on my hardware, and have been looking through the Host Lite Mass Storage example provided by Keil/Nxp/OnChip.

Any suggestions would be greatly appreciated.

Thank you,
Eric

  • Hello Eric,

    I asked Keil support a while ago the very same question. They said that they have indeed plans to implement the host-side software, but did not say "it will happen within x months/releases".
    The best thing to do, I think, is to use an external hardware to get the job done. See www.ftdichip.com/FTProducts.htm
    www.ftdichip.com/FTProducts.htm
    or www.8052.com/.../168057 etc.

  • Is the target HID device a specific one?
    Or, do you want to accept any HID devices?

    NXP Host Lite example provides enough functions to enumerate any device.
    Also, functions for control/bulk/interrupt transfer are available.

    For a specific HID device, these functions accomplish the work.
    But for any HID device, you have to make up a parser of HID report descriptor.

    Tsuneo

  • Tsuneo,

    Thank you for your reply -- I'd like to follow your suggestion of getting NXP Host Lite to work for my purposes.

    The device I am connecting is specific, in fact it is another LPC2468 running a modified version of Keil's HID Client example. This device has an interrupt IN endpoint and an interrupt OUT endpoint (both endpoint 1) that I would like to use for transferring the data. The IN report and OUT report size are each 64 bytes (and I do not need a feature report). The end point descriptors request to be polled every 8ms.

    Is there any chance you can give me some guidance on modifying NXP Host Lite to communicate with this device? It seems like the main task is to add the support of interrupt transfers - as it looks like Host Lite is setup only for Control and Bulk transfers.

    I realize that it may be too much for me to ask you to tell me literally what to modify in Host Lite, but maybe you could suggest something of a check list of items that I must add/modify? (Certainly, if you feel like typing in some literal changes, I would appreciate that - whichever is more practical for you)

    A couple questions:
    1) For the Interrupt transfers, do I have to set up a timer to that asks for an IN report every 8ms -- or is this something that I can configure the Host Interface to do automatically?

    2) Is the polling interval a hard and fast rule, or is it more of a suggestion? (ie, if the device requests to be polled every 8 ms, but I find this to be too big of a performance drag on the host, can I decide to poll it every 16 ms?)

    Thank you for any guidance you have the time to give!

    -----------------------------------------

    Tamir, I am glad to hear that you have put in a request to Keil asking for more USB Host examples.

    -Eric

  • Ah, NXP host lite doesn't support interrupt and isoc transfer fully.
    But the handling of interrupt is almost same as bulk, except for its scheduling. You'll easily add interrupt transfer support to host lite.

    OHCI spec
    The host controller (HC) on LPC2468 follows OHCI spec. The spec is downloaded from the link on USB.org
    www.usb.org/.../

    I found many bugs on the original OHCI spec, which have been left unrevised so long. This Renesas app note includes the OHCI spec, in which most of bugs are revised. I recommend you to refer both documents side by side.

    SH7727 USB Host Module Application Note
    documentation.renesas.com/.../rej05b0015_sh7727.pdf
    Section 2, Overview of the Open Host Controller Interface (OpenHCI) Specification

    Scheduling of interrupt transfer
    The polling interval of interrupt transfer is fixed on OHCI;
    1, 2, 4, 8, 16 and 32 ms.
    Your host firmware selects one of interval from this series, so that the interval is less than and nearest to the bInterval field of the target endpoint. This limitation comes from the structure of OHCI HC; 32 members of periodic table (HccaInterruptTable).

    These chapters on the OHCI spec explains the way how the HC handles periodic (interrupt and isoc) using this list.
    3.3.2 Data Structures
    4.4.2.1 HccaInterruptTable

    For an IN interrupt endpoint of 8 ms interval on the host lite,
    1) Firmware reserves an HCED (EDIntIn) and HCTD structures on the memory.
    2) Fill EDIntIn structure just after enumeration, according to the endpoint descriptor of the target device. Link above HCTD to EDIntIn.
    3) Insert the pointer to EDIntIn into hcca->IntTable[] at the index of 0, 8, 16, 24
    4) Set HcPeriodicStart to 0x2A2F
    5) Set HcControl.PeriodicListEnable bit

    For another OUT interrupt endpoint, another HCED and HCTD structures are reserved and initialized.
    a) you may append this ED to EDIntIn.Next. This results the OUT transaction is scheduled just after the IN transaction.
    OR
    b) you may insert the schedule to new series on the hcca->IntTable[], for example, index of 1, 9, 17, 25

    The rest of transaction handling is almost same as bulk one.

    HID host driver always polls the interrupt IN endpoint. You have to recover the interrupt TD immediately after its completion, for next poll.
    On the other hand, interrupt OUT endpoint is used just on demand from host application. sKip bit of HCED.Control enables the transaction without changing the HCED/HCTD structures so much.

    Tsuneo

  • Tsuneo,

    Thank you so much! This is really great.

    -Eric

  • In above post, I said that the English version of "SH7727 USB Host Module Application Note" includes revised OHCI spec. But it is wrong.

    The revised OHCI spec is included just in Japanese-translated version of the appnote, not in English version.

    Japanese version of above appnote
    documentation.renesas.com/.../rjj05b0015_sh7727.pdf

    Sorry for my mistake.

    I hope Renesas reflects the revision to the English version, too, for the benefit of us all.

    Tsuneo

  • Tsuneo,

    Your advice has been great. I have things up and running with Interrupt transfers.

    However, I am noticing a strange problem that occasionally occurs. My interrupt IN endpoint stops working, but my interrupt OUT endpoint continues to operate. What I mean by not working, is that the host controller stops servicing the endpoint. The IN endpoint HALT bit and SKIP bit are both not set. TailTd != HeadTd, and yet the transfer descriptor is not serviced. Meanwhile, every time I attached a TD onto the OUT endpoint, it is immediately serviced. Is there a control register or bit somewhere that could cause this problem?

    Here are the register values for my IN endpoint (taken in debug mode when the IN endpoint stopped being serviced):

    Control = 0x00401081
    TailTd = 0x7fd00160
    HeadTd = 0x7fd00150
    Next = 0
    

    Register values for the TD being pointed to by HeadTd (taken in debug mode when the IN endpoint stopped being serviced):

    Control = 0x00100000
    CurrBufPtr = 0x7fd00400
    Next = 0x7fd00160
    BufEnd = 0x7fd0043f
    

    Also, I have verified that the Interrupt Table in the Hcca is correct:

    IntTable[0] = &ED_IN
    IntTable[1] = &ED_OUT
    IntTable[8] = &ED_IN
    IntTable[9] = &ED_OUT
    IntTable[16] = &ED_IN
    IntTable[17] = &ED_OUT
    IntTable[24] = &ED_IN
    IntTable[25] = &ED_OUT
    

    This problem seems to happen when I disconnect the USB cable during when a transfer is in progress. When I reconnect the cable, if the problem is going to happen, the IN endpoint will work for a few TDs and then stop. Once the problem has happened, it doesn't matter if I disconnect and reconnect the cable -- the problem will occur again. Furthermore, if I power-cycle the USB host, the problem does not go away. HOWEVER, if I power-cycle the client, the problem does go away.

    Both the client and the host are running on an LPC2468.

    Any thoughts would be greatly appreciated!

    Thanks,
    Eric

  • Ah, okay, so I determined the problem: my client wasn't sending data (oops!). But this raises an interesting question:

    My understanding of the USB OHCI spec is that regardless of if a periodic (interrupt) IN endpoint receives data, it's TD will be processed, declared completed and placed on the done head. (ie, my understanding was that as soon as the Host Controller gets to servicing the periodic IN endpoint, it attempts a read from the USB client, and then regardless of whether or not the client had data to send, it would retire the TD to the Hcca->Done list).

    However, what appears to be happening is that the Host Controller does not decide retire the TD to the Hcca->Done list until some data actually comes in. So, since my USB client had no data to send, it appears that the IN TD was not being placed on the Hcca->Done list.

    Is this the way the OCHI USB HC is supposed to behave?

    Thank you,
    Eric

  • try key in

    OpenHCI-HIDSampleCo

    in the Google Search, you can down load my free sample code "OpenHCI-HIDSampleCode.zip".

    S. K. Lin