Function Multi-Versioning for GNU Guix
This repository contains an experiment to implement automatic function multi-versioning (FMV) for GNU Guix packages, inspired by Clear Linux’ tutorial.
FMV is a technique whereby the compiler generates code for different instruction set architecture (ISA) extensions; at run time, the loader automatically chooses the implementation that performs best on the host CPU. Read Pre-built binaries vs. performance for background info.
Overview
To give it a spin, try running:
GUIX_FMV_PACKAGE=gsl guix build -f function-multi-versioning.scm
For the chosen package (GSL by default), it will perform the following steps:
- Build the package with GCC’s
-fopt-info-vec
option and grab the source code location of all vectorization opportunities. - Compute a patch that adds =target_clones= attributes on the relevant functions.
- Rebuild the package with that patch.
The resulting binary contains several versions of the functions:
$ objdump -t $(GUIX_FMV_PACKAGE=gsl guix build -f function-multi-versioning.scm)/lib/libgsl.so | grep avx | head 000000000009a480 l F .text 00000000000003f5 bspline_pppack_bsplvd.avx2.0 000000000009a880 l F .text 0000000000000400 bspline_pppack_bsplvd.arch_skylake_avx512.1 000000000009b080 l F .text 0000000000000113 gsl_bspline_knots_uniform.avx2.0 000000000009b1a0 l F .text 00000000000000d8 gsl_bspline_knots_uniform.arch_skylake_avx512.1 000000000009b3a0 l F .text 000000000000012b gsl_bspline_knots.avx2.0 000000000009b4d0 l F .text 000000000000012b gsl_bspline_knots.arch_skylake_avx512.1 000000000009be70 l F .text 0000000000000125 gsl_bspline_eval.avx2.0 000000000009bfa0 l F .text 0000000000000125 gsl_bspline_eval.arch_skylake_avx512.1 000000000009f120 l F .text 0000000000000071 avl_t_copy.avx2.0 000000000009f1a0 l F .text 0000000000000071 avl_t_copy.arch_skylake_avx512.1
Binary Size
The binary is larger. With FMV for avx2
and skylake-avx512
, it is
almost twice as big as the original binary:
$ size /gnu/store/xq64iaxx2gmlcgnipj31wjxlf1yd2g2p-gsl-2.6/lib/libgsl.so text data bss dec hex filename 2899152 84112 864 2984128 2d88c0 /gnu/store/xq64iaxx2gmlcgnipj31wjxlf1yd2g2p-gsl-2.6/lib/libgsl.so $ size /gnu/store/s14ldmmlmig1pgwc49ci7lsp651zllgb-gsl-2.6/lib/libgsl.so text data bss dec hex filename 5600712 85256 912 5686880 56c660 /gnu/store/s14ldmmlmig1pgwc49ci7lsp651zllgb-gsl-2.6/lib/libgsl.so
Performance
WIP
Integration
If robust enough, this transformation could be made available as a package transformation option.