| .. _optimization_tools: |
| |
| Optimization Tools |
| ################## |
| |
| The available optimization tools let you analyse :ref:`footprint_tools` |
| and :ref:`data_structures` using different build system targets. |
| |
| .. _footprint_tools: |
| |
| Footprint and Memory Usage |
| ************************** |
| |
| The build system offers 3 targets to view and analyse RAM, ROM and stack usage |
| in generated images. The tools run on the final image and give information |
| about size of symbols and code being used in both RAM and ROM. Additionally, |
| with features available through the compiler, we can also generate worst-case |
| stack usage analysis. |
| |
| Some of the tools mentioned in this section are organizing their output based |
| on the physical organization of the symbols. As some symbols might be external |
| to the project's tree structure, or might lack metadata needed to display them |
| by name, the following top-level containers are used to group such symbols: |
| |
| * Hidden - The RAM and ROM reports list all processing symbols with no matching |
| mapped files in the Hidden category. |
| |
| This means that the file for the listed symbol was not added to the metadata file, |
| was empty, or was undefined. The tool was unable to get the name |
| of the function for the given symbol nor identify where it comes from. |
| |
| * No paths - The RAM and ROM reports list all processing symbols with relative paths |
| in the No paths category. |
| |
| This means that the listed symbols cannot be placed in the tree structure |
| of the report at an absolute path under one specific file. The tool was able |
| to get the name of the function, but it was unable to identify where it comes from. |
| |
| .. note:: |
| |
| You can have multiple cases of the same function, and the No paths category |
| will list the sum of these in one entry. |
| |
| |
| Build Target: ram_report |
| ======================== |
| |
| List all compiled objects and their RAM usage in a tabular form with bytes |
| per symbol and the percentage it uses. The data is grouped based on the file |
| system location of the object in the tree and the file containing the symbol. |
| |
| Use the ``ram_report`` target with your board, as in the following example. |
| |
| .. zephyr-app-commands:: |
| :tool: all |
| :app: samples/hello_world |
| :board: reel_board |
| :goals: ram_report |
| |
| These commands will generate something similar to the output below:: |
| |
| Path Size % Address |
| ======================================================================================== |
| Root 4637 100.00% - |
| ├── (hidden) 4 0.09% - |
| ├── (no paths) 2748 59.26% - |
| │ ├── _cpus_active 4 0.09% 0x20000314 |
| │ ├── _kernel 32 0.69% 0x20000318 |
| │ ├── _sw_isr_table 384 8.28% 0x00006474 |
| │ ├── cli.1 16 0.35% 0x20000254 |
| │ ├── on.2 4 0.09% 0x20000264 |
| │ ├── poll_out_lock.0 4 0.09% 0x200002d4 |
| │ ├── z_idle_threads 128 2.76% 0x20000120 |
| │ ├── z_interrupt_stacks 2048 44.17% 0x20000360 |
| │ └── z_main_thread 128 2.76% 0x200001a0 |
| ├── WORKSPACE 184 3.97% - |
| │ └── modules 184 3.97% - |
| │ └── hal 184 3.97% - |
| │ └── nordic 184 3.97% - |
| │ └── nrfx 184 3.97% - |
| │ └── drivers 184 3.97% - |
| │ └── src 184 3.97% - |
| │ ├── nrfx_clock.c 8 0.17% - |
| │ │ └── m_clock_cb 8 0.17% 0x200002e4 |
| │ ├── nrfx_gpiote.c 132 2.85% - |
| │ │ └── m_cb 132 2.85% 0x20000060 |
| │ ├── nrfx_ppi.c 4 0.09% - |
| │ │ └── m_channels_allocated 4 0.09% 0x200000e4 |
| │ └── nrfx_twim.c 40 0.86% - |
| │ └── m_cb 40 0.86% 0x200002ec |
| └── ZEPHYR_BASE 1701 36.68% - |
| ├── arch 5 0.11% - |
| │ └── arm 5 0.11% - |
| │ └── core 5 0.11% - |
| │ ├── mpu 1 0.02% - |
| │ │ └── arm_mpu.c 1 0.02% - |
| │ │ └── static_regions_num 1 0.02% 0x20000348 |
| │ └── tls.c 4 0.09% - |
| │ └── z_arm_tls_ptr 4 0.09% 0x20000240 |
| ├── drivers 258 5.56% - |
| │ ├── ... ... ...% |
| ======================================================================================== |
| 4637 |
| |
| |
| Build Target: rom_report |
| ======================== |
| |
| List all compiled objects and their ROM usage in a tabular form with bytes |
| per symbol and the percentage it uses. The data is grouped based on the file |
| system location of the object in the tree and the file containing the symbol. |
| |
| Use the ``rom_report`` target with your board, as in the following example. |
| |
| .. zephyr-app-commands:: |
| :tool: all |
| :app: samples/hello_world |
| :board: reel_board |
| :goals: rom_report |
| |
| These commands will generate something similar to the output below:: |
| |
| Path Size % Address |
| ======================================================================================== |
| Root 27828 100.00% - |
| ├── ... ... ...% |
| └── ZEPHYR_BASE 13558 48.72% - |
| ├── arch 1766 6.35% - |
| │ └── arm 1766 6.35% - |
| │ └── core 1766 6.35% - |
| │ ├── cortex_m 1020 3.67% - |
| │ │ ├── fault.c 620 2.23% - |
| │ │ │ ├── bus_fault.constprop.0 108 0.39% 0x00000749 |
| │ │ │ ├── mem_manage_fault.constprop.0 120 0.43% 0x000007b5 |
| │ │ │ ├── usage_fault.constprop.0 84 0.30% 0x000006f5 |
| │ │ │ ├── z_arm_fault 292 1.05% 0x0000082d |
| │ │ │ └── z_arm_fault_init 16 0.06% 0x00000951 |
| │ │ ├── ... ... ...% |
| ├── boards 32 0.11% - |
| │ └── arm 32 0.11% - |
| │ └── reel_board 32 0.11% - |
| │ └── board.c 32 0.11% - |
| │ ├── __init_board_reel_board_init 8 0.03% 0x000063e4 |
| │ └── board_reel_board_init 24 0.09% 0x00000ed5 |
| ├── build 194 0.70% - |
| │ └── zephyr 194 0.70% - |
| │ ├── isr_tables.c 192 0.69% - |
| │ │ └── _irq_vector_table 192 0.69% 0x00000040 |
| │ └── misc 2 0.01% - |
| │ └── generated 2 0.01% - |
| │ └── configs.c 2 0.01% - |
| │ └── _ConfigAbsSyms 2 0.01% 0x00005945 |
| ├── drivers 6282 22.57% - |
| │ ├── ... ... ...% |
| ======================================================================================== |
| 21652 |
| |
| Build Target: puncover |
| ====================== |
| |
| This target uses a third-party tool called puncover which can be found at |
| https://github.com/HBehrens/puncover. When this target is built, it will |
| launch a local web server which will allow you to open a web client and browse |
| the files and view their ROM, RAM, and stack usage. |
| |
| Before you can use this |
| target, install the puncover Python module:: |
| |
| pip3 install git+https://github.com/HBehrens/puncover --user |
| |
| .. warning:: |
| |
| This is a third-party tool that might or might not be working at any given |
| time. Please check the GitHub issues, and report new problems to the |
| project maintainer. |
| |
| After you installed the Python module, use ``puncover`` target with your board, |
| as in the following example. |
| |
| .. zephyr-app-commands:: |
| :tool: all |
| :app: samples/hello_world |
| :board: reel_board |
| :goals: puncover |
| |
| |
| To view worst-case stack usage analysis, build this with the |
| :kconfig:option:`CONFIG_STACK_USAGE` enabled. |
| |
| .. zephyr-app-commands:: |
| :tool: all |
| :app: samples/hello_world |
| :board: reel_board |
| :goals: puncover |
| :gen-args: -DCONFIG_STACK_USAGE=y |
| |
| |
| .. _data_structures: |
| |
| Data Structures |
| **************** |
| |
| |
| Build Target: pahole |
| ===================== |
| |
| Poke-a-hole (pahole) is an object-file analysis tool to find the size of |
| the data structures, and the holes caused due to aligning the data |
| elements to the word-size of the CPU by the compiler. |
| |
| Poke-a-hole (pahole) must be installed prior to using this target. It can be |
| obtained from https://git.kernel.org/pub/scm/devel/pahole/pahole.git and is |
| available in the dwarves package in both fedora and ubuntu:: |
| |
| sudo apt-get install dwarves |
| |
| Alternatively, you can get it from fedora:: |
| |
| sudo dnf install dwarves |
| |
| After you installed the package, use ``pahole`` target with your board, |
| as in the following example. |
| |
| .. zephyr-app-commands:: |
| :tool: all |
| :app: samples/hello_world |
| :board: reel_board |
| :goals: pahole |
| |
| Pahole will generate something similar to the output below in the console:: |
| |
| /* Used at: zephyr/isr_tables.c */ |
| /* <80> ../include/sw_isr_table.h:30 */ |
| struct _isr_table_entry { |
| void * arg; /* 0 4 */ |
| void (*isr)(void *); /* 4 4 */ |
| |
| /* size: 8, cachelines: 1, members: 2 */ |
| /* last cacheline: 8 bytes */ |
| }; |
| /* Used at: zephyr/isr_tables.c */ |
| /* <eb> ../include/arch/arm/aarch32/cortex_m/mpu/arm_mpu_v7m.h:134 */ |
| struct arm_mpu_region_attr { |
| uint32_t rasr; /* 0 4 */ |
| |
| /* size: 4, cachelines: 1, members: 1 */ |
| /* last cacheline: 4 bytes */ |
| }; |
| /* Used at: zephyr/isr_tables.c */ |
| /* <112> ../include/arch/arm/aarch32/cortex_m/mpu/arm_mpu.h:24 */ |
| struct arm_mpu_region { |
| uint32_t base; /* 0 4 */ |
| const char * name; /* 4 4 */ |
| arm_mpu_region_attr_t attr; /* 8 4 */ |
| |
| /* size: 12, cachelines: 1, members: 3 */ |
| /* last cacheline: 12 bytes */ |
| }; |
| ... |
| ... |