Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix nrf52 layout #98

Merged
merged 5 commits into from
Nov 22, 2019
Merged

fix nrf52 layout #98

merged 5 commits into from
Nov 22, 2019

Conversation

fhars
Copy link
Contributor

@fhars fhars commented Oct 14, 2019

It looks like the application start address on nRF52 has moved upwards
by 64kB since the library was tested the last time.

It looks like the application start address on nRF52 has moved upwards
by 64kB since the library was tested the last time.
README.md Outdated Show resolved Hide resolved
@gendx
Copy link
Contributor

gendx commented Oct 14, 2019

Since you mentioned the NRF52840-DK board on tock/tock#1402, I'm wondering if there's a difference between nrf52 and nrf52840 w.r.t. layout, given that Tock defines two boards (https://github.com/tock/tock/tree/master/boards/nordic/nrf52dk and https://github.com/tock/tock/tree/master/boards/nordic/nrf52840dk).

I don't have an "nRF52-DK" board to test on, but maybe there needs to be two different layouts, i.e. nrf52_layout.ld and nrf52840_layout.ld?

@fhars
Copy link
Contributor Author

fhars commented Oct 14, 2019

I can't see any fundamental difference between the two boards when deploying libtock-c applications. libtock-rs applications work fine with the new layout on the nRK52-DK and immediately hardfault on an nrf52840-DK. Nothing happens on both boards with the old layout (not surprisingly, the nRF52840-DK always had the program origin at 0x30000, and the nRF52-DK since tock/tock@bf71fff4c). So the layout is correct, for sufficiently small values of "correct", applications shouldn't have to care about board specific layouts except for #28.

@fhars
Copy link
Contributor Author

fhars commented Oct 14, 2019

The SRAM is somewhere else on the nRF52840-DK, so it does need it's own layout file after all while relocation doesn't work.

nrf52840_layout.ld Outdated Show resolved Hide resolved
@gendx
Copy link
Contributor

gendx commented Oct 15, 2019

As far as I understand, there are multiple factors affecting the location of the SRAM symbol (where the app memory is located in RAM).

  • The SRAM itself starts from 0x20000000. The beginning of this address space is used by the kernel. Depending on how many drivers are loaded on a specific board, (52840 has more than 52), the kernel uses more or less space. This kernel memory space is however fixed, as the only way for the kernel to dynamically allocate memory is via grants in applications.
  • The application memory is then loaded above that. Because of constraints in the Cortex-M3 memory protection unit, only a power-of-two size can be allocated for the app (https://github.com/tock/tock/blob/master/arch/cortex-m3/src/mpu.rs#L342), and the app memory's start address must be aligned on this power-of-two. There also seems to be a minimal alignment for MPU (8KB it seems). This means that acceptable memory ranges are of the form e.g. 0x20002000 - 0x20004000 or 0x20004000 - 0x20008000 or 0x20008000 - 0x20010000, etc.

One can increase the memory available for an app by increasing the heap size (--app-heap parameter for elf2tab, and related tweaks in the entry point code). So given a board, depending on the application, the start address can be different! This also means that with the current implementation of Tock, a single app can use at most half of the RAM (assuming a power-of-two RAM size), even if the kernel uses much less than that.

This means that there is no one true value for the SRAM, it depends on the application. A long-term way to fix this would be to have relocation working properly, i.e. fixing #28. In the meantime, I guess we can use a "baseline" SRAM value, i.e. the smallest that fits the kernel memory and a simple app (e.g. blink) with the default --app-heap value.

@fhars
Copy link
Contributor Author

fhars commented Oct 15, 2019

As far as I understand it, the SRAM for the first application will always start a the lowest possible loaction (currently 0x20004000 for the nRF52840), so the value should work for all applications as long as the application is installed as the first application on the board. If you want to install an application written in rust in another position, you will indeed need a custom layout for every combination of apps you have installed before...

@gendx
Copy link
Contributor

gendx commented Oct 15, 2019

As far as I understand it, the SRAM for the first application will always start a the lowest possible loaction (currently 0x20004000 for the nRF52840), [...]

Not exactly. The memory address for each app is computed in Process::create (here https://github.com/tock/tock/blob/master/kernel/src/process.rs#L1169-L1184), and depends on min_app_ram_size defined in the TBF header of the application. This TBF field can itself be set via --app-heap of elf2tab.

The allocate_app_memory_region of the Cortex-M3 MPU will then round the memory to a power of two (https://github.com/tock/tock/blob/master/arch/cortex-m3/src/mpu.rs#L461) and then align the memory region accordingly (https://github.com/tock/tock/blob/master/arch/cortex-m3/src/mpu.rs#L475-L478).

You can check this behavior by increasing the --app-heap in elf2tab and e.g. triggering a panic (https://github.com/tock/libtock-rs/blob/master/examples/panic.rs) to have the kernel print the memory layout of the app.

@fhars
Copy link
Contributor Author

fhars commented Oct 16, 2019

OK, so the build script should do the following: build the code, run arm-none-eabi-objdump on the output and check the .data and .bss sizes, if they are larger than 8k generate a new layout, rewrite .cargo/config, and rebuild. Uhhhh... no.

But if it is documented, it is no longer a bug, but a feature.

someone(TM) really should do somting about issue 28.
@fhars
Copy link
Contributor Author

fhars commented Oct 16, 2019

No, github, "someone should fix" does not mean that it is fixed.

@alevy
Copy link
Member

alevy commented Nov 1, 2019

@fhars what is the state of this PR? Is this is a state to be reviewed and merged from your perspective?

@torfmaster
Copy link
Collaborator

I tested it and it works. The hardware_tests are green except for "gpio out" which is not working anymore after updating the kernel, so I would not merge. One way to fix this would be to select a working kernel version which is also compatible with the changes in this PR.

README.md Outdated Show resolved Hide resolved
MEMORY {
/* The application region is 64 bytes (0x40) */
FLASH (rx) : ORIGIN = 0x00030040, LENGTH = 0x000CFFC0
SRAM (rwx) : ORIGIN = 0x20004000, LENGTH = 62K
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think the SRAM length is correct. Isn't there more memory than that on the nRF52840-DK?

@Woyten
Copy link
Contributor

Woyten commented Nov 18, 2019

I would like to merge this PR very soon. As the nrf52840 has never been supported by libtock-rs, it would be okay for me if the board is not perfectly described regarding memory layout.

@Woyten Woyten merged commit 6c38aa1 into tock:master Nov 22, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants