Skip to content

flowswitch/elf-data-compress

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

3 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Bare metal ELF section compression tool

This tool implements data/bss sections compile-time compression and runtime decompression similar to a feature found in commercial ARM toolchains (IAR, ARM Compiler).

How it works

Compile time

  • LD linker (directed by a modified .ld script) creates an additional .idata section containing data/bss ranges table and a free space to place the init data generated by the tool later
  • the compressor tool gets data/bss ranges
  • tries various compression algorithms on each section to find best ones
  • builds an init image consisting of addresses+methods table, decompressors code, compressed data
  • places the init image into .idata section (overwriting the linker-provided table)
  • shrinks the .idata section to the actual size (an ELF file itself is not shrunk for now, but the ELF to bin/hex conversion by objcopy uses shrunk size)
  • marks data/bss section as non-loadable (to exclude from bin/hex conversion)
  • writes the output ELF image

The decompressor code for each algorithm is either taken from tool's .bin files compiled for a particular arch or is identified inside the user's app code and referenced by pointer (thus occupying zero additional space).

Runtime

A custom init code (should be executed before main(), normally called right after SystemInit()) iterates over the data/bss table, gets source/destination/size/decompressor values for each section and calls the decompressor function

Included compression algorithms

  • zero - fills the dst with zeroes, uses no compressed data. Reuses memset/memclr functions from the "main" code
  • fill - fills the dst with byte value specified in src. Reuses memset function from the "main" code
  • PackBits - a slightly modified PackBits algorithm. Efficient on data with long repetitions of the same byte
  • LZ77RLE - an LZ77 combined with RLE compression of repeated zeroes. Uses the same packed data format as produced by some versions or IAR and AC. Efficient on data with repeating byte patterns and long runs of 00 bytes.
  • copy - worst case, no compression, just copy the data as is. Reuses memcpy function from the "main" code

Sample code

The sample code is a modified Alex Taradov's STM32G071 starter project with the following changes:

  • linker script: don't place .data load image into flash, generate .idata section placeholder
  • C startup code: process .idata init table
  • main: added dummy initialized/uninitialized arrays to place some content into .data/.bss
  • Makefile: additional build step to invoke the compressor tool

Build

Requirements: arm-none-eabi-gcc toolchain in $PATH

  • build decompressors by invoking make in compression
  • build the sample code by invoking make in sample/make. The intermediate noncompressed ELF will be output to build/Demo.elf'. The compressed ELF will be output to build/Demo.comp.elf. Try arm-none-eabi-readelf -e` on both of them to see the difference

About

Bare metal ELF section compression tool

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published