In the article Platform Builder: Setting Default Memory Divisions, I discussed using pOEMCalcFSPages() or pfnCalcFSPages() to set the memory division between storage and program memory. In that article I presented the following function:
DWORD OEMCalcFSPages(DWORD dwMemPages, DWORD dwDefaultFSPages)
                DWORD Percent = 50;
                return ( dwMemPages * Percent ) / 100;
Then I suggested that with enough knowledge of your BSP and an imagination, you could dynamically set the percent value instead of using a hardcoded value. In this article, I thought that I would explore how this could be handled in a BSP to allow the bootloader to pass a percent value to the OS.
If the bootloader is going to pass a value to the OS we need a method to do this. Now if these were applications running within the OS we might think about using  sockets, message queues or maybe a memory mapped file. But these tools aren’t available if for no other reason when the bootloader is running, the OS isn’t. We can think about memory mapped files though, but in a simpler form which would be just memory mapped data.
To understand this better, let’s look at the CEPC BSP. The CEPC BSP already memory maps data to communicate between the bootloader and the OS. CEPC does this with a data structure, BSP_ARGS, which it allocates space in RAM to use. The following explains how CEPC sets up the memory mapping:
·         The BSP_ARGS structure is defined in the CSP in bootargs.h.
·         The address of BSP_ARGS is defined in the CSP in bootargs.h as BOOT_ARG_PTR_LOCATION
·         In config.bib the BSP_ARGS address space is documented by establishing a RESERVED section
·         The boot.bib files don’t documented the BSP_ARGS address space, which would be good to do
·         The bootloaders (BIOSLoader, EBoot and Sboot) initialize a pointer to the address that will be used
·         The kernel reads the data from BOOT_ARGS when OEMInitDebugSerial() runs
BSP_ARGS is used primarily to pass display and debug information from the bootloader to the kernel. But that doesn’t mean that it cannot be extended to do more.
Other BSPs may use a structure with a different name, or not have a structure for this purpose at all.
In the case of setting the memory division percent, we could add a member to the BSP_ARGS structure and provide a mechanism in the bootloader to initialize the value. When changing BSP_ARGS, it is important to watch the size of the structure. CEPC maps 256 bytes for the structure, so if the structure becomes larger than 256 bytes the data would be in memory space that is being used for other purposes.
BSP_ARGS can also be used for the kernel to communicate to the bootloader. A member could be included in BSP_ARGS that tells the bootloader how to behave on the next boot. This only works for soft resets though and the bootloader must not clear BSP_ARGS before the member is read. For this to work well, BSP_ARGS must have some value in it that can be used to verify that values in BSP_ARGS are valid.
Copyright © 2009 – Bruce Eitman
All Rights Reserved