From 62cfd38241000dfb6fbfa8deaaf940fcf400ac31 Mon Sep 17 00:00:00 2001 From: patacongo Date: Tue, 7 Aug 2012 23:51:47 +0000 Subject: [PATCH] Add a USB0 device header file for LPC43 git-svn-id: https://nuttx.svn.sourceforge.net/svnroot/nuttx/trunk@5016 7fd9a85b-ad96-42d3-883c-3090e2eb8679 --- nuttx/ChangeLog | 10 +- nuttx/Documentation/NuttShell.html | 8 +- nuttx/Documentation/NuttX.html | 14 +- nuttx/Documentation/NuttXDemandPaging.html | 1350 ++++++++++---------- nuttx/Documentation/NuttxPortingGuide.html | 4 +- nuttx/Documentation/NxWidgets.html | 2 +- nuttx/ReleaseNotes | 14 +- nuttx/TODO | 2 +- nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.c | 4 +- nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.h | 98 ++ 10 files changed, 801 insertions(+), 705 deletions(-) create mode 100644 nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.h diff --git a/nuttx/ChangeLog b/nuttx/ChangeLog index 614381c900..107a426d6f 100644 --- a/nuttx/ChangeLog +++ b/nuttx/ChangeLog @@ -816,7 +816,7 @@ and (2) it requires symbol table arguments. * lib/: Add fileno() * examples/ostest: Several of the tests used a big, hard-coded stack size - when creating test threads (16Kb stacksize). The stack size should + when creating test threads (16K stacksize). The stack size should be controlled by the .config file or the OSTest won't work on platforms with memory constraints. * netutils/thttpd: An initial port of Jeff Poskanzer's THTTPD HTTP server. @@ -1369,10 +1369,10 @@ out instead. This improves behavior, for example, on the first GET request from a browser. * arch/arm/src/lpc17xx/lpc17_emacram.h and lpc17_allocateheap.c: The Ethernet - logic was using all of AHB SRAM Bank0 for Ethernet packet buffers (16Kb). An + logic was using all of AHB SRAM Bank0 for Ethernet packet buffers (16K). An option was added to limit the amount of SRAM used for packet buffering and to re-use any extra Bank0 memory for heap. configs/olimex-lpc1766stk/nettest - now uses only 8Kb at the beginning of Bank0; the 8Kb at the end of Bank0 is + now uses only 8K at the beginning of Bank0; the 8K at the end of Bank0 is included in the heap * arch/arm/src/lpc17xx/lpc17_ssp.c: Fix compilation errors when SSP1 is selected. @@ -1785,7 +1785,7 @@ that support 16-bit addressability have smaller overhead than devices that support 32-bit addressability. However, there are many MCUs that support 32-bit addressability *but* have internal SRAM of size - less than or equal to 64Kb. In this case, CONFIG_MM_SMALL can be + less than or equal to 64K. In this case, CONFIG_MM_SMALL can be defined so that those MCUs will also benefit from the smaller, 16- bit-based allocation overhead. * lib/string/lib_strndup.c: Add standard strndup() library function. @@ -1846,7 +1846,7 @@ * arch/sim/src/up_romgetc.c: Used to test the basic logic to access strings without directly de-referencing a string pointer. * arch/avr/src/avr/up_romget.c: Used to access strings that lie in the first - 64Kb of FLASH (But I still haven't figured out how to get strings to reside in + 64K of FLASH (But I still haven't figured out how to get strings to reside in FLASH without using the PROGMEM attribute). * configs/teensy/src/up_spi.c: Correct reading of SD CD and WP pins (was reading the wrong register. AVR SPI now appears to be functional. diff --git a/nuttx/Documentation/NuttShell.html b/nuttx/Documentation/NuttShell.html index a92cbadd8e..ca7e826279 100644 --- a/nuttx/Documentation/NuttShell.html +++ b/nuttx/Documentation/NuttShell.html @@ -8,7 +8,7 @@

NuttShell (NSH)

-

Last Updated: August 3, 2012

+

Last Updated: August 7, 2012

@@ -1210,7 +1210,7 @@ losetup [-o ] [-r] <dev-path> <file-path>

Synopsis. Setup the loop device at <dev-path> to access the file at <file-path> as a block device. - In the following example a 256Kb file is created (dd) and losetup is + In the following example a 256K file is created (dd) and losetup is used to make the file accessible as a block device. A FAT file system is created (mkfatfs) and mounted (mount). Files can then be managed on the loop-mounted file. @@ -3148,7 +3148,7 @@ endef

  • - The make file then defines the application name (hello), the task priority (default), and the stack size that will be allocated in the task runs (2Kb). + The make file then defines the application name (hello), the task priority (default), and the stack size that will be allocated in the task runs (2K).

       APPNAME         = hello
      @@ -3160,7 +3160,7 @@ STACKSIZE       = 2048
           

      And finally, the Makefile invokes the REGISTER macro to added the hello_main() named application. Then, when the system build completes, the hello command can be executed from the NSH command line. - When the hello command is executed, it will start the task with entry point hello_main() with the default priority and with a stack size of 2Kb. + When the hello command is executed, it will start the task with entry point hello_main() with the default priority and with a stack size of 2K.

         .context:
        diff --git a/nuttx/Documentation/NuttX.html b/nuttx/Documentation/NuttX.html
        index ed994d69b9..b7026f8965 100644
        --- a/nuttx/Documentation/NuttX.html
        +++ b/nuttx/Documentation/NuttX.html
        @@ -858,9 +858,9 @@
             

        Using a variety of technologies, NuttX can scale from the very tiny to the moderate-size system. I have executed NuttX with some simple applications - in as little as 32Kb total memory (code and data). - On the other hand, typical, richly featured NuttX builds require more like 64Kb - (and if all of the features are used, this can push 100Kb). + in as little as 32K total memory (code and data). + On the other hand, typical, richly featured NuttX builds require more like 64K + (and if all of the features are used, this can push 100K).

        @@ -2028,8 +2028,8 @@ Micropendous 3 AT9USB64x and AT9USB6128x. This port of NuttX to the Opendous Micropendous 3 board. The Micropendous3 is may be populated with an AT90USB646, 647, 1286, or 1287. I have only the AT90USB647 - version for testing. This version have very limited memory resources: 64Kb of - FLASH and 4Kb of SRAM. + version for testing. This version have very limited memory resources: 64K of + FLASH and 4K of SRAM.

          @@ -2085,7 +2085,7 @@

          Most NuttX test applications are console-oriented with lots of strings used for printf and debug output. - These strings are all stored in SRAM now due to these data accessing issues and even the smallest console-oriented applications can quickly fill a 4-8Kb memory. + These strings are all stored in SRAM now due to these data accessing issues and even the smallest console-oriented applications can quickly fill a 4-8K memory. So, in order for the AVR port to be useful, one of two things would need to be done:

            @@ -2917,7 +2917,7 @@ if [ -x "$WINELOADER" ]; then exec "$WINELOADER" "$appname" "$@"; fi

        87C52 A reduced functionality OS test for the 8052 target requires only - about 18-19Kb: + about 18-19K:

         Stack starts at: 0x21 (sp set to 0x20) with 223 bytes available.
        diff --git a/nuttx/Documentation/NuttXDemandPaging.html b/nuttx/Documentation/NuttXDemandPaging.html
        index 3246e070d0..c238161a82 100644
        --- a/nuttx/Documentation/NuttXDemandPaging.html
        +++ b/nuttx/Documentation/NuttXDemandPaging.html
        @@ -1,675 +1,675 @@
        -
        -
        -On-Demand Paging
        -
        -
        -

        - - - - -
        -

        On-Demand Paging

        -

        >>> Under Construction <<<

        -

        Last Updated: August 12, 2010

        -
        -

        - - - - - -
        -

        Table of Contents

        -
        - -
        - - - - - - - - - - -
        - - - - - - - - - - - - - -
        - Introduction -
          - Overview -
          - Terminology -
        -
        - - - - - - - - - - - - - - - - - - - - - - - - - -
        - NuttX Common Logic Design Description -
          - Initialization -
          - Page Faults -
          - Fill Initiation -
          - Fill Complete -
          - Task Resumption -
        -
        - - - - - - - - - - - - - -
        - Architecture-Specific Support Requirements -
          - Memory Organization -
          - Architecture-Specific Functions -
        -
        - - - - - -
        -

        Introduction

        -
        -

        Overview

        - -

        - This document summarizes the design of NuttX on-demand paging. - This feature permits embedded MCUs with some limited RAM space to execute large programs from some non-random access media. - This feature was first discussed in this email thread: - http://tech.groups.yahoo.com/group/nuttx/message/213. -

        -

        - What kind of platforms can support NuttX on-demang paging? -

          -
        1. - The MCU should have some large, probably low-cost non-volatile storage such as serial FLASH or an SD card. - This storage probably does not support non-random access (otherwise, why not just execute the program directly on the storage media). - SD and serial FLASH are inexpensive and do not require very many pins and SPI support is prevalent in just about all MCUs. - This large serial FLASH would contain a big program. Perhaps a program of several megabytes in size. -
        2. -
        3. - The MCU must have a (relatively) small block of fast SRAM from which it can execute code. - A size of, say 256Kb (or 192Kb as in the NXP LPC3131) would be sufficient for many applications. -
        4. -
        5. - The MCU has an MMU (again like the NXP LPC3131). -
        6. -
        -

        -

        - If the platform meets these requirement, then NuttX can provide on-demand paging: - It can copy .text from the large program in non-volatile media into RAM as needed to execute a huge program from the small RAM. -

        - -

        Terminology

        - -
        -
        g_waitingforfill
        -
        An OS list that is used to hold the TCBs of tasks that are waiting for a page fill.
        -
        g_pftcb
        -
        A variable that holds a reference to the TCB of the thread that is currently be re-filled.
        -
        g_pgworker
        -
        The process ID of of the thread that will perform the page fills.
        -
        pg_callback()
        -
        The callback function that is invoked from a driver when the fill is complete.
        -
        pg_miss()
        -
        The function that is called from architecture-specific code to handle a page fault.
        -
        TCB
        -
        Task Control Block
        -
        - - - - - -
        -

        NuttX Common Logic Design Description

        -
        - - -

        Initialization

        - -

        - The following declarations will be added. -

          -
        • - g_waitingforfill. - A doubly linked list that will be used to implement a prioritized list of the TCBs of tasks that are waiting for a page fill. -
        • -
        • - g_pgworker. - The process ID of of the thread that will perform the page fills -
        • -
        -

        -

        - During OS initialization in sched/os_start.c, the following steps - will be performed: -

          -
        • - The g_waitingforfill queue will be initialized. -
        • -
        • - The special, page fill worker thread, will be started. - The pid of the page will worker thread will be saved in g_pgworker. - Note that we need a special worker thread to perform fills; - we cannot use the "generic" worker thread facility because we cannot be - assured that all actions called by that worker thread will always be resident in memory. -
        • -
        -

        -

        - Declarations for g_waitingforfill, g_pgworker, and other - internal, private definitions will be provided in sched/pg_internal.h. - All public definitions that should be used by the architecture-specific code will be available - in include/nuttx/page.h. - Most architecture-specific functions are declared in include/nuttx/arch.h, - but for the case of this paging logic, those architecture specific functions are instead declared in include/nuttx/page.h. -

        - -

        Page Faults

        - -

        - Page fault exception handling. - Page fault handling is performed by the function pg_miss(). - This function is called from architecture-specific memory segmentation - fault handling logic. This function will perform the following - operations: -

          -
        1. - Sanity checking. - This function will ASSERT if the currently executing task is the page fill worker thread. - The page fill worker thread is how the the page fault is resolved and all logic associated with the page fill worker - must be "locked" and always present in memory. -
        2. -
        3. - Block the currently executing task. - This function will call up_block_task() to block the task at the head of the ready-to-run list. - This should cause an interrupt level context switch to the next highest priority task. - The blocked task will be marked with state TSTATE_WAIT_PAGEFILL and will be retained in the g_waitingforfill prioritized task list. -
        4. -
        5. - Boost the page fill worker thread priority. - Check the priority of the task at the head of the g_waitingforfill list. - If the priority of that task is higher than the current priority of the page fill worker thread, then boost the priority of the page fill worker thread to that priority. - Thus, the page fill worker thread will always run at the priority of the highest priority task that is waiting for a fill. -
        6. -
        7. - Signal the page fill worker thread. - Is there a page already being filled? - If not then signal the page fill worker thread to start working on the queued page fill requests. -
        8. -
        -

        -

        - When signaled from pg_miss(), the page fill worker thread will be awakenend and will initiate the fill operation. -

        -

        - Input Parameters. - None -- The head of the ready-to-run list is assumed to be that task that caused the exception. - The current task context should already be saved in the TCB of that task. - No additional inputs are required. -

        -

        - Assumptions. -

          -
        • - It is assumed that this function is called from the level of an exception handler and that all interrupts are disabled. -
        • -
        • - The pg_miss() must be "locked" in memory. - Calling pg_miss() cannot cause a nested page fault. -
        • -
        • - It is assumed that currently executing task (the one at the head of the ready-to-run list) is the one that cause the fault. - This will always be true unless the page fault occurred in an interrupt handler. - Interrupt handling logic must always be available and "locked" into memory so that page faults never come from interrupt handling. -
        • -
        • - The architecture-specific page fault exception handling has already verified that the exception did not occur from interrupt/exception handling logic. -
        • -
        • - As mentioned above, the task causing the page fault must not be the page fill worker thread because that is the only way to complete the page fill. -
        • -
        -

        - -

        Fill Initiation

        - -

        - The page fill worker thread will be awakened on one of three conditions: -

          -
        • - When signaled by pg_miss(), the page fill worker thread will be awakenend (see above), -
        • -
        • - From pg_callback() after completing last fill (when CONFIG_PAGING_BLOCKINGFILL is defined... see below), or -
        • -
        • - A configurable timeout expires with no activity. - This timeout can be used to detect failure conditions such things as fills that never complete. -
        • -
        -

        - -

        - The page fill worker thread will maintain a static variable called _TCB *g_pftcb. - If no fill is in progress, g_pftcb will be NULL. - Otherwise, it will point to the TCB of the task which is receiving the fill that is in progess. -

        -
          - NOTE: - I think that this is the only state in which a TCB does not reside in some list. - Here is it in limbo, outside of the normally queuing while the page file is in progress. - While here, it will be marked with TSTATE_TASK_INVALID. -
        - -

        - When awakened from pg_miss(), no fill will be in progress and g_pftcb will be NULL. - In this case, the page fill worker thread will call pg_startfill(). - That function will perform the following operations: -

          -
        • - Call the architecture-specific function up_checkmapping() to see if the page fill - still needs to be performed. - In certain conditions, the page fault may occur on several threads and be queued multiple times. - In this corner case, the blocked task will simply be restarted (see the logic below for the - case of normal completion of the fill operation). -
        • -
        • - Call up_allocpage(tcb, &vpage). - This architecture-specific function will set aside page in memory and map to virtual address (vpage). - If all available pages are in-use (the typical case), - this function will select a page in-use, un-map it, and make it available. -
        • -
        • - Call the architecture-specific function up_fillpage(). - Two versions of the up_fillpage function are supported -- a blocking and a non-blocking version based upon the configuratin setting CONFIG_PAGING_BLOCKINGFILL. -
            -
          • - If CONFIG_PAGING_BLOCKINGFILL is defined, then up_fillpage is blocking call. - In this case, up_fillpage() will accept only (1) a reference to the TCB that requires the fill. - Architecture-specific context information within the TCB will be sufficient to perform the fill. - And (2) the (virtual) address of the allocated page to be filled. - The resulting status of the fill will be provided by return value from up_fillpage(). -
          • -
          • - If CONFIG_PAGING_BLOCKINGFILL is defined, then up_fillpage is non-blocking call. - In this case up_fillpage() will accept an additional argument: - The page fill worker thread will provide a callback function, pg_callback. - This function is non-blocking, it will start an asynchronous page fill. - After calling the non-blocking up_fillpage(), the page fill worker thread will wait to be signaled for the next event -- the fill completion event. - The callback function will be called when the page fill is finished (or an error occurs). - The resulting status of the fill will be providing as an argument to the callback functions. - This callback will probably occur from interrupt level. -
          -
        • -
        -

        -

        - In any case, while the fill is in progress, other tasks may execute. - If another page fault occurs during this time, the faulting task will be blocked, its TCB will be added (in priority order) to g_waitingforfill, and the priority of the page worker task may be boosted. - But no action will be taken until the current page fill completes. - NOTE: The IDLE task must also be fully locked in memory. - The IDLE task cannot be blocked. - It the case where all tasks are blocked waiting for a page fill, the IDLE task must still be available to run. -

        - The architecture-specific functions, up_checkmapping(), up_allocpage(tcb, &vpage) and up_fillpage(page, pg_callback) - will be prototyped in include/nuttx/arch.h -

        - -

        Fill Complete

        - -

        - For the blocking up_fillpage(), the result of the fill will be returned directly from the call to up_fillpage. -

        -

        - For the non-blocking up_fillpage(), the architecture-specific driver call the pg_callback() that was provided to up_fillpage() when the fill completes. - In this case, the pg_callback() will probably be called from driver interrupt-level logic. - The driver will provide the result of the fill as an argument to the callback function. - NOTE: pg_callback() must also be locked in memory. -

        -

        - In this non-blocking case, the callback pg_callback() will perform the following operations when it is notified that the fill has completed: -

          -
        • - Verify that g_pftcb is non-NULL. -
        • -
        • - Find the higher priority between the task waiting for the fill to complete in g_pftcb and the task waiting at the head of the g_waitingforfill list. - That will be the priority of he highest priority task waiting for a fill. -
        • -
        • - If this higher priority is higher than current page fill worker thread, then boost worker thread's priority to that level. - Thus, the page fill worker thread will always run at the priority of the highest priority task that is waiting for a fill. -
        • -
        • - Save the result of the fill operation. -
        • -
        • - Signal the page fill worker thread. -
        • -
        -

        - -

        Task Resumption

        - -

        - For the non-blocking up_fillpage(), the page fill worker thread will detect that the page fill is complete when it is awakened with g_pftcb non-NULL and fill completion status from pg_callback. - In the non-blocking case, the page fill worker thread will know that the page fill is complete when up_fillpage() returns. -

        -

        - In this either, the page fill worker thread will: -

          -
        • - Verify consistency of state information and g_pftcb. -
        • -
        • - Verify that the page fill completed successfully, and if so, -
        • -
        • - Call up_unblocktask(g_pftcb) to make the task that just received the fill ready-to-run. -
        • -
        • - Check if the g_waitingforfill list is empty. - If not: -
            -
          • - Remove the highest priority task waiting for a page fill from g_waitingforfill, -
          • -
          • - Save the task's TCB in g_pftcb, -
          • -
          • - If the priority of the thread in g_pftcb, is higher in priority than the default priority of the page fill worker thread, then set the priority of the page fill worker thread to that priority. -
          • -
          • - Call pg_startfill() which will start the next fill (as described above). -
          • -
          -
        • -
        • - Otherwise, -
            -
          • - Set g_pftcb to NULL. -
          • -
          • - Restore the default priority of the page fill worker thread. -
          • -
          • - Wait for the next fill related event (a new page fault). -
          • -
          -
        • -
        -

        - - - - - -
        -

        Architecture-Specific Support Requirements

        -
        - -

        Memory Organization

        - -

        - Memory Regions. - Chip specific logic will map the virtual and physical address spaces into three general regions: -

          -
        1. - A .text region containing "locked-in-memory" code that is always avaialable and will never cause a page fault. - This locked memory is loaded at boot time and remains resident for all time. - This memory regions must include: -
            -
          • - All logic for all interrupt pathes. - All interrupt logic must be locked in memory because the design present here will not support page faults from interrupt handlers. - This includes the page fault handling logic and pg_miss() that is called from the page fault handler. - It also includes the pg_callback() function that wakes up the page fill worker thread - and whatever architecture-specific logic that calls pg_callback(). -
          • -
          • - All logic for the IDLE thread. - The IDLE thread must always be ready to run and cannot be blocked for any reason. -
          • -
          • - All of the page fill worker thread must be locked in memory. - This thread must execute in order to unblock any thread waiting for a fill. - It this thread were to block, there would be no way to complete the fills! -
          -
        2. -
        3. - A .text region containing pages that can be assigned allocated, mapped to various virtual addresses, and filled from some mass storage medium. -
        4. -
        5. - And a fixed RAM space for .bss, .text, and .heap. -
        6. -
        -

        -

        - This memory organization is illustrated in the following table. - Notice that: -

          -
        • - There is a one-to-one relationship between pages in the virtual address space and between pages of .text in the non-volatile mass storage device. -
        • -
        • - There are, however, far fewer physical pages available than virtual pages. - Only a subset of physical pages will be mapped to virtual pages at any given time. - This mapping will be performed on-demand as needed for program execution. -
        -

        - -
        - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
        SRAMVirtual Address SpaceNon-Volatile Storage
         DATA 
         Virtual Page n (n > m)Stored Page n
         Virtual Page n-1Stored Page n-1
        DATA......
        Physical Page m (m < n)......
        Physical Page m-1......
        .........
        Physical Page 1Virtual Page 1Stored Page 1
        Locked MemoryLocked MemoryMemory Resident
        - -

        - Example. - As an example, suppose that the size of the SRAM is 192Kb (as in the NXP LPC3131). And suppose further that: -

          -
        • - The size of the locked, memory resident .text area is 32Kb, and -
        • -
        • - The size of the DATA area is 64Kb. -
        • -
        • - The size of one, managed page is 1Kb. -
        • -
        • - The size of the whole .text image on the non-volatile, mass storage device is 1024Kb. -
        • -
        -

        - Then, the size of the locked, memory resident code is 32Kb (m=32 pages). - The size of the physical page region is 96Kb (96 pages), and the - size of the data region is 64 pages. - And the size of the virtual paged region must then be greater than or equal to (1024-32) or 992 pages (n). -

        - -

        - Building the Locked, In-Memory Image. - One way to accomplish this would be a two phase link: -

          -
        • - In the first phase, create a partially linked objected containing all interrupt/exception handling logic, the page fill worker thread plus all parts of the IDLE thread (which must always be available for execution). -
        • -
        • - All of the .text and .rodata sections of this partial link should be collected into a single section. -
        • -
        • - The second link would link the partially linked object along with the remaining object to produce the final binary. - The linker script should position the "special" section so that it lies in a reserved, "non-swappable" region. -
        -

        - -

        Architecture-Specific Functions

        - -

        - Most standard, architecture-specific functions are declared in include/nuttx/arch.h. - However, for the case of this paging logic, the architecture specific functions are declared in include/nuttx/page.h. - Standard, architecture-specific functions that should already be provided in the architecture port. - The following are used by the common paging logic: -

        -
          -
          - void up_block_task(FAR _TCB *tcb, tstate_t task_state); -
          -
          - The currently executing task at the head of the ready to run list must be stopped. - Save its context and move it to the inactive list specified by task_state. - This function is called by the on-demand paging logic in order to block the task that requires the - page fill, and to -
          -
          - void up_unblock_task(FAR _TCB *tcb); -
          -
          - A task is currently in an inactive task list but has been prepped to execute. - Move the TCB to the ready-to-run list, restore its context, and start execution. - This function will be called -
          -
        - -

        - New, additional functions that must be implemented just for on-demand paging support: -

        - -
          -
          - int up_checkmapping(FAR _TCB *tcb); -
          -
          - The function up_checkmapping() returns an indication if the page fill still needs to performed or not. - In certain conditions, the page fault may occur on several threads and be queued multiple times. - This function will prevent the same page from be filled multiple times. -
          -
          - int up_allocpage(FAR _TCB *tcb, FAR void *vpage); -
          -
          - This architecture-specific function will set aside page in memory and map to its correct virtual address. - Architecture-specific context information saved within the TCB will provide the function with the information needed to identify the virtual miss address. - This function will return the allocated physical page address in vpage. - The size of the underlying physical page is determined by the configuration setting CONFIG_PAGING_PAGESIZE. - NOTE: This function must always return a page allocation. - If all available pages are in-use (the typical case), then this function will select a page in-use, un-map it, and make it available. -
          -
          int up_fillpage(FAR _TCB *tcb, FAR const void *vpage, void (*pg_callback)(FAR _TCB *tcb, int result)); -
          - The actual filling of the page with data from the non-volatile, must be performed by a separate call to the architecture-specific function, up_fillpage(). - This will start asynchronous page fill. - The common paging logic will provide a callback function, pg_callback, that will be called when the page fill is finished (or an error occurs). - This callback is assumed to occur from an interrupt level when the device driver completes the fill operation. - -
        - - - + + +On-Demand Paging + + +

        + + + + +
        +

        On-Demand Paging

        +

        >>> Under Construction <<<

        +

        Last Updated: August 12, 2010

        +
        +

        + + + + + +
        +

        Table of Contents

        +
        + +
        + + + + + + + + + + +
        + + + + + + + + + + + + + +
        + Introduction +
          + Overview +
          + Terminology +
        +
        + + + + + + + + + + + + + + + + + + + + + + + + + +
        + NuttX Common Logic Design Description +
          + Initialization +
          + Page Faults +
          + Fill Initiation +
          + Fill Complete +
          + Task Resumption +
        +
        + + + + + + + + + + + + + +
        + Architecture-Specific Support Requirements +
          + Memory Organization +
          + Architecture-Specific Functions +
        +
        + + + + + +
        +

        Introduction

        +
        +

        Overview

        + +

        + This document summarizes the design of NuttX on-demand paging. + This feature permits embedded MCUs with some limited RAM space to execute large programs from some non-random access media. + This feature was first discussed in this email thread: + http://tech.groups.yahoo.com/group/nuttx/message/213. +

        +

        + What kind of platforms can support NuttX on-demang paging? +

          +
        1. + The MCU should have some large, probably low-cost non-volatile storage such as serial FLASH or an SD card. + This storage probably does not support non-random access (otherwise, why not just execute the program directly on the storage media). + SD and serial FLASH are inexpensive and do not require very many pins and SPI support is prevalent in just about all MCUs. + This large serial FLASH would contain a big program. Perhaps a program of several megabytes in size. +
        2. +
        3. + The MCU must have a (relatively) small block of fast SRAM from which it can execute code. + A size of, say 256K (or 192K as in the NXP LPC3131) would be sufficient for many applications. +
        4. +
        5. + The MCU has an MMU (again like the NXP LPC3131). +
        6. +
        +

        +

        + If the platform meets these requirement, then NuttX can provide on-demand paging: + It can copy .text from the large program in non-volatile media into RAM as needed to execute a huge program from the small RAM. +

        + +

        Terminology

        + +
        +
        g_waitingforfill
        +
        An OS list that is used to hold the TCBs of tasks that are waiting for a page fill.
        +
        g_pftcb
        +
        A variable that holds a reference to the TCB of the thread that is currently be re-filled.
        +
        g_pgworker
        +
        The process ID of of the thread that will perform the page fills.
        +
        pg_callback()
        +
        The callback function that is invoked from a driver when the fill is complete.
        +
        pg_miss()
        +
        The function that is called from architecture-specific code to handle a page fault.
        +
        TCB
        +
        Task Control Block
        +
        + + + + + +
        +

        NuttX Common Logic Design Description

        +
        + + +

        Initialization

        + +

        + The following declarations will be added. +

          +
        • + g_waitingforfill. + A doubly linked list that will be used to implement a prioritized list of the TCBs of tasks that are waiting for a page fill. +
        • +
        • + g_pgworker. + The process ID of of the thread that will perform the page fills +
        • +
        +

        +

        + During OS initialization in sched/os_start.c, the following steps + will be performed: +

          +
        • + The g_waitingforfill queue will be initialized. +
        • +
        • + The special, page fill worker thread, will be started. + The pid of the page will worker thread will be saved in g_pgworker. + Note that we need a special worker thread to perform fills; + we cannot use the "generic" worker thread facility because we cannot be + assured that all actions called by that worker thread will always be resident in memory. +
        • +
        +

        +

        + Declarations for g_waitingforfill, g_pgworker, and other + internal, private definitions will be provided in sched/pg_internal.h. + All public definitions that should be used by the architecture-specific code will be available + in include/nuttx/page.h. + Most architecture-specific functions are declared in include/nuttx/arch.h, + but for the case of this paging logic, those architecture specific functions are instead declared in include/nuttx/page.h. +

        + +

        Page Faults

        + +

        + Page fault exception handling. + Page fault handling is performed by the function pg_miss(). + This function is called from architecture-specific memory segmentation + fault handling logic. This function will perform the following + operations: +

          +
        1. + Sanity checking. + This function will ASSERT if the currently executing task is the page fill worker thread. + The page fill worker thread is how the the page fault is resolved and all logic associated with the page fill worker + must be "locked" and always present in memory. +
        2. +
        3. + Block the currently executing task. + This function will call up_block_task() to block the task at the head of the ready-to-run list. + This should cause an interrupt level context switch to the next highest priority task. + The blocked task will be marked with state TSTATE_WAIT_PAGEFILL and will be retained in the g_waitingforfill prioritized task list. +
        4. +
        5. + Boost the page fill worker thread priority. + Check the priority of the task at the head of the g_waitingforfill list. + If the priority of that task is higher than the current priority of the page fill worker thread, then boost the priority of the page fill worker thread to that priority. + Thus, the page fill worker thread will always run at the priority of the highest priority task that is waiting for a fill. +
        6. +
        7. + Signal the page fill worker thread. + Is there a page already being filled? + If not then signal the page fill worker thread to start working on the queued page fill requests. +
        8. +
        +

        +

        + When signaled from pg_miss(), the page fill worker thread will be awakenend and will initiate the fill operation. +

        +

        + Input Parameters. + None -- The head of the ready-to-run list is assumed to be that task that caused the exception. + The current task context should already be saved in the TCB of that task. + No additional inputs are required. +

        +

        + Assumptions. +

          +
        • + It is assumed that this function is called from the level of an exception handler and that all interrupts are disabled. +
        • +
        • + The pg_miss() must be "locked" in memory. + Calling pg_miss() cannot cause a nested page fault. +
        • +
        • + It is assumed that currently executing task (the one at the head of the ready-to-run list) is the one that cause the fault. + This will always be true unless the page fault occurred in an interrupt handler. + Interrupt handling logic must always be available and "locked" into memory so that page faults never come from interrupt handling. +
        • +
        • + The architecture-specific page fault exception handling has already verified that the exception did not occur from interrupt/exception handling logic. +
        • +
        • + As mentioned above, the task causing the page fault must not be the page fill worker thread because that is the only way to complete the page fill. +
        • +
        +

        + +

        Fill Initiation

        + +

        + The page fill worker thread will be awakened on one of three conditions: +

          +
        • + When signaled by pg_miss(), the page fill worker thread will be awakenend (see above), +
        • +
        • + From pg_callback() after completing last fill (when CONFIG_PAGING_BLOCKINGFILL is defined... see below), or +
        • +
        • + A configurable timeout expires with no activity. + This timeout can be used to detect failure conditions such things as fills that never complete. +
        • +
        +

        + +

        + The page fill worker thread will maintain a static variable called _TCB *g_pftcb. + If no fill is in progress, g_pftcb will be NULL. + Otherwise, it will point to the TCB of the task which is receiving the fill that is in progess. +

        +
          + NOTE: + I think that this is the only state in which a TCB does not reside in some list. + Here is it in limbo, outside of the normally queuing while the page file is in progress. + While here, it will be marked with TSTATE_TASK_INVALID. +
        + +

        + When awakened from pg_miss(), no fill will be in progress and g_pftcb will be NULL. + In this case, the page fill worker thread will call pg_startfill(). + That function will perform the following operations: +

          +
        • + Call the architecture-specific function up_checkmapping() to see if the page fill + still needs to be performed. + In certain conditions, the page fault may occur on several threads and be queued multiple times. + In this corner case, the blocked task will simply be restarted (see the logic below for the + case of normal completion of the fill operation). +
        • +
        • + Call up_allocpage(tcb, &vpage). + This architecture-specific function will set aside page in memory and map to virtual address (vpage). + If all available pages are in-use (the typical case), + this function will select a page in-use, un-map it, and make it available. +
        • +
        • + Call the architecture-specific function up_fillpage(). + Two versions of the up_fillpage function are supported -- a blocking and a non-blocking version based upon the configuratin setting CONFIG_PAGING_BLOCKINGFILL. +
            +
          • + If CONFIG_PAGING_BLOCKINGFILL is defined, then up_fillpage is blocking call. + In this case, up_fillpage() will accept only (1) a reference to the TCB that requires the fill. + Architecture-specific context information within the TCB will be sufficient to perform the fill. + And (2) the (virtual) address of the allocated page to be filled. + The resulting status of the fill will be provided by return value from up_fillpage(). +
          • +
          • + If CONFIG_PAGING_BLOCKINGFILL is defined, then up_fillpage is non-blocking call. + In this case up_fillpage() will accept an additional argument: + The page fill worker thread will provide a callback function, pg_callback. + This function is non-blocking, it will start an asynchronous page fill. + After calling the non-blocking up_fillpage(), the page fill worker thread will wait to be signaled for the next event -- the fill completion event. + The callback function will be called when the page fill is finished (or an error occurs). + The resulting status of the fill will be providing as an argument to the callback functions. + This callback will probably occur from interrupt level. +
          +
        • +
        +

        +

        + In any case, while the fill is in progress, other tasks may execute. + If another page fault occurs during this time, the faulting task will be blocked, its TCB will be added (in priority order) to g_waitingforfill, and the priority of the page worker task may be boosted. + But no action will be taken until the current page fill completes. + NOTE: The IDLE task must also be fully locked in memory. + The IDLE task cannot be blocked. + It the case where all tasks are blocked waiting for a page fill, the IDLE task must still be available to run. +

        + The architecture-specific functions, up_checkmapping(), up_allocpage(tcb, &vpage) and up_fillpage(page, pg_callback) + will be prototyped in include/nuttx/arch.h +

        + +

        Fill Complete

        + +

        + For the blocking up_fillpage(), the result of the fill will be returned directly from the call to up_fillpage. +

        +

        + For the non-blocking up_fillpage(), the architecture-specific driver call the pg_callback() that was provided to up_fillpage() when the fill completes. + In this case, the pg_callback() will probably be called from driver interrupt-level logic. + The driver will provide the result of the fill as an argument to the callback function. + NOTE: pg_callback() must also be locked in memory. +

        +

        + In this non-blocking case, the callback pg_callback() will perform the following operations when it is notified that the fill has completed: +

          +
        • + Verify that g_pftcb is non-NULL. +
        • +
        • + Find the higher priority between the task waiting for the fill to complete in g_pftcb and the task waiting at the head of the g_waitingforfill list. + That will be the priority of he highest priority task waiting for a fill. +
        • +
        • + If this higher priority is higher than current page fill worker thread, then boost worker thread's priority to that level. + Thus, the page fill worker thread will always run at the priority of the highest priority task that is waiting for a fill. +
        • +
        • + Save the result of the fill operation. +
        • +
        • + Signal the page fill worker thread. +
        • +
        +

        + +

        Task Resumption

        + +

        + For the non-blocking up_fillpage(), the page fill worker thread will detect that the page fill is complete when it is awakened with g_pftcb non-NULL and fill completion status from pg_callback. + In the non-blocking case, the page fill worker thread will know that the page fill is complete when up_fillpage() returns. +

        +

        + In this either, the page fill worker thread will: +

          +
        • + Verify consistency of state information and g_pftcb. +
        • +
        • + Verify that the page fill completed successfully, and if so, +
        • +
        • + Call up_unblocktask(g_pftcb) to make the task that just received the fill ready-to-run. +
        • +
        • + Check if the g_waitingforfill list is empty. + If not: +
            +
          • + Remove the highest priority task waiting for a page fill from g_waitingforfill, +
          • +
          • + Save the task's TCB in g_pftcb, +
          • +
          • + If the priority of the thread in g_pftcb, is higher in priority than the default priority of the page fill worker thread, then set the priority of the page fill worker thread to that priority. +
          • +
          • + Call pg_startfill() which will start the next fill (as described above). +
          • +
          +
        • +
        • + Otherwise, +
            +
          • + Set g_pftcb to NULL. +
          • +
          • + Restore the default priority of the page fill worker thread. +
          • +
          • + Wait for the next fill related event (a new page fault). +
          • +
          +
        • +
        +

        + + + + + +
        +

        Architecture-Specific Support Requirements

        +
        + +

        Memory Organization

        + +

        + Memory Regions. + Chip specific logic will map the virtual and physical address spaces into three general regions: +

          +
        1. + A .text region containing "locked-in-memory" code that is always avaialable and will never cause a page fault. + This locked memory is loaded at boot time and remains resident for all time. + This memory regions must include: +
            +
          • + All logic for all interrupt paths. + All interrupt logic must be locked in memory because the design present here will not support page faults from interrupt handlers. + This includes the page fault handling logic and pg_miss() that is called from the page fault handler. + It also includes the pg_callback() function that wakes up the page fill worker thread + and whatever architecture-specific logic that calls pg_callback(). +
          • +
          • + All logic for the IDLE thread. + The IDLE thread must always be ready to run and cannot be blocked for any reason. +
          • +
          • + All of the page fill worker thread must be locked in memory. + This thread must execute in order to unblock any thread waiting for a fill. + It this thread were to block, there would be no way to complete the fills! +
          +
        2. +
        3. + A .text region containing pages that can be assigned allocated, mapped to various virtual addresses, and filled from some mass storage medium. +
        4. +
        5. + And a fixed RAM space for .bss, .text, and .heap. +
        6. +
        +

        +

        + This memory organization is illustrated in the following table. + Notice that: +

          +
        • + There is a one-to-one relationship between pages in the virtual address space and between pages of .text in the non-volatile mass storage device. +
        • +
        • + There are, however, far fewer physical pages available than virtual pages. + Only a subset of physical pages will be mapped to virtual pages at any given time. + This mapping will be performed on-demand as needed for program execution. +
        +

        + +
        + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
        SRAMVirtual Address SpaceNon-Volatile Storage
         DATA 
         Virtual Page n (n > m)Stored Page n
         Virtual Page n-1Stored Page n-1
        DATA......
        Physical Page m (m < n)......
        Physical Page m-1......
        .........
        Physical Page 1Virtual Page 1Stored Page 1
        Locked MemoryLocked MemoryMemory Resident
        + +

        + Example. + As an example, suppose that the size of the SRAM is 192K (as in the NXP LPC3131). And suppose further that: +

          +
        • + The size of the locked, memory resident .text area is 32K, and +
        • +
        • + The size of the DATA area is 64K. +
        • +
        • + The size of one, managed page is 1K. +
        • +
        • + The size of the whole .text image on the non-volatile, mass storage device is 1024K. +
        • +
        +

        + Then, the size of the locked, memory resident code is 32K (m=32 pages). + The size of the physical page region is 96K (96 pages), and the + size of the data region is 64 pages. + And the size of the virtual paged region must then be greater than or equal to (1024-32) or 992 pages (n). +

        + +

        + Building the Locked, In-Memory Image. + One way to accomplish this would be a two phase link: +

          +
        • + In the first phase, create a partially linked objected containing all interrupt/exception handling logic, the page fill worker thread plus all parts of the IDLE thread (which must always be available for execution). +
        • +
        • + All of the .text and .rodata sections of this partial link should be collected into a single section. +
        • +
        • + The second link would link the partially linked object along with the remaining object to produce the final binary. + The linker script should position the "special" section so that it lies in a reserved, "non-swappable" region. +
        +

        + +

        Architecture-Specific Functions

        + +

        + Most standard, architecture-specific functions are declared in include/nuttx/arch.h. + However, for the case of this paging logic, the architecture specific functions are declared in include/nuttx/page.h. + Standard, architecture-specific functions that should already be provided in the architecture port. + The following are used by the common paging logic: +

        +
          +
          + void up_block_task(FAR _TCB *tcb, tstate_t task_state); +
          +
          + The currently executing task at the head of the ready to run list must be stopped. + Save its context and move it to the inactive list specified by task_state. + This function is called by the on-demand paging logic in order to block the task that requires the + page fill, and to +
          +
          + void up_unblock_task(FAR _TCB *tcb); +
          +
          + A task is currently in an inactive task list but has been prepped to execute. + Move the TCB to the ready-to-run list, restore its context, and start execution. + This function will be called +
          +
        + +

        + New, additional functions that must be implemented just for on-demand paging support: +

        + +
          +
          + int up_checkmapping(FAR _TCB *tcb); +
          +
          + The function up_checkmapping() returns an indication if the page fill still needs to performed or not. + In certain conditions, the page fault may occur on several threads and be queued multiple times. + This function will prevent the same page from be filled multiple times. +
          +
          + int up_allocpage(FAR _TCB *tcb, FAR void *vpage); +
          +
          + This architecture-specific function will set aside page in memory and map to its correct virtual address. + Architecture-specific context information saved within the TCB will provide the function with the information needed to identify the virtual miss address. + This function will return the allocated physical page address in vpage. + The size of the underlying physical page is determined by the configuration setting CONFIG_PAGING_PAGESIZE. + NOTE: This function must always return a page allocation. + If all available pages are in-use (the typical case), then this function will select a page in-use, un-map it, and make it available. +
          +
          int up_fillpage(FAR _TCB *tcb, FAR const void *vpage, void (*pg_callback)(FAR _TCB *tcb, int result)); +
          + The actual filling of the page with data from the non-volatile, must be performed by a separate call to the architecture-specific function, up_fillpage(). + This will start asynchronous page fill. + The common paging logic will provide a callback function, pg_callback, that will be called when the page fill is finished (or an error occurs). + This callback is assumed to occur from an interrupt level when the device driver completes the fill operation. + +
        + + + diff --git a/nuttx/Documentation/NuttxPortingGuide.html b/nuttx/Documentation/NuttxPortingGuide.html index e605dd109d..a339b3a990 100644 --- a/nuttx/Documentation/NuttxPortingGuide.html +++ b/nuttx/Documentation/NuttxPortingGuide.html @@ -3935,7 +3935,7 @@ build 16-bit addressability have smaller overhead than devices that support 32-bit addressability. However, there are many MCUs that support 32-bit addressability but have internal SRAM - of size less than or equal to 64Kb. In this case, CONFIG_MM_SMALL + of size less than or equal to 64K. In this case, CONFIG_MM_SMALL can be defined so that those MCUs will also benefit from the smaller, 16-bit-based allocation overhead. @@ -4740,7 +4740,7 @@ build
      • CONFIG_P14201_FRAMEBUFFER: If defined, accesses will be performed using an in-memory copy of the OLEDs GDDRAM. - This cost of this buffer is 128 * 96 / 2 = 6Kb. + This cost of this buffer is 128 * 96 / 2 = 6K. If this is defined, then the driver will be fully functional. If not, then it will have the following limitations:
          diff --git a/nuttx/Documentation/NxWidgets.html b/nuttx/Documentation/NxWidgets.html index cef99d4943..1678d9ebe7 100755 --- a/nuttx/Documentation/NxWidgets.html +++ b/nuttx/Documentation/NxWidgets.html @@ -33,7 +33,7 @@
        • Small Footprint. NXWidgets is tailored for use MCUs in embedded applications. It is ideally suited for mid- and upper-range of most MCU families. - A complete NXWidgets is possible in as little as 40Kb of FLASH and maybe 4Kb of SRAM. + A complete NXWidgets is possible in as little as 40K of FLASH and maybe 4K of SRAM.
        • Output Devices. NXWidgets will work on the high-end frame buffer devices as well as on LCDs connected via serial or parallel ports to a small MCU. diff --git a/nuttx/ReleaseNotes b/nuttx/ReleaseNotes index 8c6ae0ccb8..26af0e38d4 100644 --- a/nuttx/ReleaseNotes +++ b/nuttx/ReleaseNotes @@ -1668,7 +1668,7 @@ Important bugfixes included: And feature enhancements: * The LPC176x Ethernet driver was using all of AHB SRAM Bank0 for - Ethernet packet buffers (16Kb). An option was added to limit + Ethernet packet buffers (16K). An option was added to limit the amount of SRAM used for packet buffering and to re-use any extra Bank0 memory for heap. @@ -2022,7 +2022,7 @@ and is available for download from the SourceForge website. The * A PCI-based E1000 Ethernet driver (contributed by Yu Qiang) * New C library functions: inet_addr() (contributed by Yu Qiang), strndup(), asprintf() - * Reduced memory allocation overhead for MCUs with small heaps (<64Kb). + * Reduced memory allocation overhead for MCUs with small heaps (<64K). * fdopen() now works with socket descriptors allowing standard buffered C functions to be used for network communications. * The NSH ifconfig command can now be used to set or change the @@ -2062,7 +2062,7 @@ they are, ordered from the least to the most complete: This port of NuttX to the Amber Web Server from SoC Robotics (http://www.soc-robotics.com/index.htm). Is only partially in place. The Amber Web Server is based on an Atmel ATMega128 - (128Kb FLASH but only 4Kb of SRAM). + (128K FLASH but only 4K of SRAM). STATUS: Work on this port has stalled due to toolchain issues. It is complete, but untested. @@ -2073,7 +2073,7 @@ they are, ordered from the least to the most complete: Micropendous3 may be populated with an AT90USB646, 647, 1286, or 1287. See http://code.google.com/p/opendous/. I have only the AT90USB647 version for testing. This version has very - limited memory resources: 64Kb of FLASH and 4Kb of SRAM. + limited memory resources: 64K of FLASH and 4K of SRAM. STATUS: The basic port was released in NuttX-6.5. This basic port consists only of a "Hello, World!!" example that demonstrates @@ -2085,8 +2085,8 @@ they are, ordered from the least to the most complete: This is a port of NuttX to the PJRC Teensy++ 2.0 board. This board was developed by PJRC (http://pjrc.com/teensy/). The - Teensy++ 2.0 is based on an Atmel AT90USB1286 MCU with 128Kb - of FLASH and 8Kb of SRAM; a little more room to move than the + Teensy++ 2.0 is based on an Atmel AT90USB1286 MCU with 128K + of FLASH and 8K of SRAM; a little more room to move than the AT90USB647. STATUS: The basic port was released in NuttX-6.5. This basic @@ -2109,7 +2109,7 @@ integrated into the normal, general purpose OS. Most NuttX test applications are console-oriented with lots of strings used for printf and debug output. These strings are all stored in SRAM now due to these data accessing issues and even the -smallest console-oriented applications can quickly fill a 4-8Kb +smallest console-oriented applications can quickly fill a 4-8K memory. So, in order for the AVR port to be useful, one of two things would need to be done: diff --git a/nuttx/TODO b/nuttx/TODO index 7ffcb9ca80..f9fc558eab 100644 --- a/nuttx/TODO +++ b/nuttx/TODO @@ -1819,7 +1819,7 @@ o mc68hc1x (arch/hc) Description: There is no script for building in banked mode (more correctly, there is a script, but logic inside the script has not yet been implemented). It would be necessary to implement banked mode to able to access more - the 48Kb of FLASH. + the 48K of FLASH. Status: Open. Priority: Medium/Low diff --git a/nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.c b/nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.c index 40233ec0f6..2ce19a3250 100644 --- a/nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.c +++ b/nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.c @@ -69,9 +69,7 @@ #include "up_arch.h" #include "up_internal.h" -#include "lpc43_usbotg.h" -#include "lpc43_evntrtr.h" -#include "lpc43_syscreg.h" +#include "lpc43_usb0dev.h" /******************************************************************************* * Definitions diff --git a/nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.h b/nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.h new file mode 100644 index 0000000000..97076cd802 --- /dev/null +++ b/nuttx/arch/arm/src/lpc43xx/lpc43_usb0dev.h @@ -0,0 +1,98 @@ +/************************************************************************************ + * arch/arm/src/lpc43xx/lpc43_usbdev.h + * + * Copyright (C) 2009, 2011 Gregory Nutt. All rights reserved. + * Author: Gregory Nutt + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in + * the documentation and/or other materials provided with the + * distribution. + * 3. Neither the name NuttX nor the names of its contributors may be + * used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS + * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT + * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS + * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE + * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, + * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, + * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS + * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED + * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN + * ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + ************************************************************************************/ + +#ifndef __ARCH_ARM_SRC_LPC43XX_LPC32_USB0DEV_H +#define __ARCH_ARM_SRC_LPC43XX_LPC32_USB0DEV_H + +/************************************************************************************ + * Included Files + ************************************************************************************/ + +#include +#include +#include + +#include "chip.h" +#include "chip/lpc43_usb0.h" + +/************************************************************************************ + * Public Functions + ************************************************************************************/ + +#ifndef __ASSEMBLY__ + +#undef EXTERN +#if defined(__cplusplus) +#define EXTERN extern "C" +extern "C" { +#else +#define EXTERN extern +#endif + +/************************************************************************************ + * Name: lpc43_usbpullup + * + * Description: + * If USB is supported and the board supports a pullup via GPIO (for USB software + * connect and disconnect), then the board software must provide lpc43_pullup. + * See include/nuttx/usb/usbdev.h for additional description of this method. + * Alternatively, if no pull-up GPIO the following EXTERN can be redefined to be + * NULL. + * + ************************************************************************************/ + +EXTERN int lpc43_usbpullup(FAR struct usbdev_s *dev, bool enable); + +/************************************************************************************ + * Name: lpc43_usbsuspend + * + * Description: + * Board logic must provide the lpc43_usbsuspend logic if the USBDEV driver is + * used. This function is called whenever the USB enters or leaves suspend mode. + * This is an opportunity for the board logic to shutdown clocks, power, etc. + * while the USB is suspended. + * + ************************************************************************************/ + +EXTERN void lpc43_usbsuspend(FAR struct usbdev_s *dev, bool resume); + +#undef EXTERN +#if defined(__cplusplus) +} +#endif + +#endif /* __ASSEMBLY__ */ +#endif /* __ARCH_ARM_SRC_LPC43XX_LPC32_USB0DEV_H */ +