From f14ea70dac7c0aeab840cda017d2891c488d8e25 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Timm=20B=C3=A4der?= Date: Wed, 21 Sep 2022 09:18:31 +0200 Subject: [PATCH] Ship brp-llvm-compile-lto-elf script Resolves: rhbz#2022522 --- brp-llvm-compile-lto-elf | 52 +++++++++++++++++++ macros | 3 ++ redhat-rpm-config.spec | 8 ++- .../brp-llvm-compile-lto-elf-test-lib.c | 5 ++ .../brp-llvm-compile-lto-elf-test-lib.h | 1 + .../brp-llvm-compile-lto-elf-test-lib.spec | 34 ++++++++++++ .../brp-llvm-compile-lto-elf-test.c | 6 +++ .../brp-llvm-compile-lto-elf-test.spec | 24 +++++++++ tests/brp-llvm-compile-lto-elf/main.fmf | 8 +++ tests/brp-llvm-compile-lto-elf/runtest.sh | 17 ++++++ 10 files changed, 157 insertions(+), 1 deletion(-) create mode 100755 brp-llvm-compile-lto-elf create mode 100644 tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.c create mode 100644 tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.h create mode 100644 tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.spec create mode 100644 tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.c create mode 100644 tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.spec create mode 100644 tests/brp-llvm-compile-lto-elf/main.fmf create mode 100755 tests/brp-llvm-compile-lto-elf/runtest.sh diff --git a/brp-llvm-compile-lto-elf b/brp-llvm-compile-lto-elf new file mode 100755 index 0000000..7eb53a1 --- /dev/null +++ b/brp-llvm-compile-lto-elf @@ -0,0 +1,52 @@ +#!/usr/bin/bash -eu + + +if [ -z "$RPM_BUILD_ROOT" ] || [ "$RPM_BUILD_ROOT" = "/" ]; then + exit 0 +fi + +CLANG_FLAGS=$@ +NCPUS=${RPM_BUILD_NCPUS:-1} + +check_convert_bitcode () { + local file_name=$(realpath ${1}) + local file_type=$(file ${file_name}) + + shift + CLANG_FLAGS="$@" + + if [[ "${file_type}" == *"LLVM IR bitcode"* ]]; then + # Check the output of llvm-strings for the command line, which is in the LLVM bitcode because + # we pass -frecord-gcc-switches. + # Check for a line that has "-flto" after (or without) "-fno-lto". + llvm-strings ${file_name} | while read line ; do + flto=$(echo $line | grep -o -b -e -flto | tail -n 1 | cut -d : -f 1) + fnolto=$(echo $line | grep -o -b -e -fno-lto | tail -n 1 | cut -d : -f 1) + + if test -n "$flto" && { test -z "$fnolto" || test "$flto" -gt "$fnolto"; } ; then + echo "Compiling LLVM bitcode file ${file_name}." + clang ${CLANG_FLAGS} -fno-lto -Wno-unused-command-line-argument \ + -x ir ${file_name} -c -o ${file_name} + break + fi + done + elif [[ "${file_type}" == *"current ar archive"* ]]; then + echo "Unpacking ar archive ${file_name} to check for LLVM bitcode components." + # create archive stage for objects + local archive_stage=$(mktemp -d) + local archive=${file_name} + pushd ${archive_stage} + ar x ${archive} + for archived_file in $(find -not -type d); do + check_convert_bitcode ${archived_file} ${CLANG_FLAGS} + echo "Repacking ${archived_file} into ${archive}." + ar r ${archive} ${archived_file} + done + popd + fi +} + +echo "Checking for LLVM bitcode artifacts" +export -f check_convert_bitcode +find "$RPM_BUILD_ROOT" -type f -name "*.[ao]" -print0 | \ + xargs -0 -r -n1 -P$NCPUS sh -c "check_convert_bitcode \$@ $CLANG_FLAGS" ARG0 diff --git a/macros b/macros index 70b343e..74e9bf3 100644 --- a/macros +++ b/macros @@ -233,6 +233,8 @@ print(result) # __brp_mangle_shebangs_exclude_from_file - file from which to get files to ignore %__brp_mangle_shebangs /usr/lib/rpm/redhat/brp-mangle-shebangs %{?__brp_mangle_shebangs_exclude:--shebangs "%{?__brp_mangle_shebangs_exclude}"} %{?__brp_mangle_shebangs_exclude_file:--shebangs-from "%{__brp_mangle_shebangs_exclude_file}"} %{?__brp_mangle_shebangs_exclude_from:--files "%{?__brp_mangle_shebangs_exclude_from}"} %{?__brp_mangle_shebangs_exclude_from_file:--files-from "%{__brp_mangle_shebangs_exclude_from_file}"} +%__brp_llvm_compile_lto_elf /usr/lib/rpm/redhat/brp-llvm-compile-lto-elf %{build_cflags} %{build_ldflags} + %__os_install_post \ %{?__brp_ldconfig} \ %{?__brp_compress} \ @@ -249,6 +251,7 @@ print(result) %{nil} %__spec_install_post\ + %[ "%{toolchain}" == "clang" ? "%{?__brp_llvm_compile_lto_elf}" : "%{nil}" ] \ %{?__debug_package:%{__debug_install_post}}\ %{__arch_install_post}\ %{__os_install_post}\ diff --git a/redhat-rpm-config.spec b/redhat-rpm-config.spec index cb21d27..4387c3e 100644 --- a/redhat-rpm-config.spec +++ b/redhat-rpm-config.spec @@ -6,7 +6,7 @@ Summary: Red Hat specific rpm configuration files Name: redhat-rpm-config -Version: 196 +Version: 197 Release: 1%{?dist} # No version specified. License: GPL+ @@ -59,6 +59,9 @@ Source202: brp-python-bytecompile # https://github.com/fedora-python/marshalparser Source203: brp-fix-pyc-reproducibility +# for converting llvm LTO bitcode objects into ELF +Source204: brp-llvm-compile-lto-elf + # Dependency generator scripts (deprecated) Source300: find-provides Source304: find-requires @@ -213,6 +216,9 @@ install -p -m 644 -t %{buildroot}%{_rpmluadir}/fedora/srpm forge.lua %doc buildflags.md %changelog +* Wed Sep 21 2022 Timm Bäder - 197-1 +- Ship brp-llvm-compile-lto-elf script + * Mon Jun 27 2022 Nick Clifton - 196-1 - Pass "--remove section .gnu.build.attributes" to the find-debuginfo script. - Resolves: rhbz#2099613 diff --git a/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.c b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.c new file mode 100644 index 0000000..851790f --- /dev/null +++ b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.c @@ -0,0 +1,5 @@ +#include + +void hello(void) { + printf("Hello, world!\n"); +} diff --git a/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.h b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.h new file mode 100644 index 0000000..ef77476 --- /dev/null +++ b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.h @@ -0,0 +1 @@ +void hello(void); diff --git a/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.spec b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.spec new file mode 100644 index 0000000..d8bfb32 --- /dev/null +++ b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test-lib/brp-llvm-compile-lto-elf-test-lib.spec @@ -0,0 +1,34 @@ +Name: brp-llvm-compile-lto-elf-test-lib +Version: 1 +Release: 1 +Summary: Library package for testing brp-llvm-compile-lto-elf +License: MIT + +BuildRequires: clang binutils +Source0: %{name}.c +Source1: %{name}.h + +# FIXME: I'm not sure why this doesn't work +%undefine _package_note_file + +%global toolchain clang + +%description +%{summary} + +%build + +clang ${CFLAGS} -c %{SOURCE0} -o lib.o +ar cr %{name}.a lib.o +ranlib %{name}.a + +%install +mkdir -p %{buildroot}%{_libdir} +mkdir -p %{buildroot}%{_includedir} + +%{__install} -p -m 644 -t %{buildroot}%{_libdir} %{name}.a +%{__install} -p -m 644 -t %{buildroot}%{_includedir} %{SOURCE1} + +%files +%{_libdir}/%{name}.a +%{_includedir}/%{name}.h diff --git a/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.c b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.c new file mode 100644 index 0000000..eab7d69 --- /dev/null +++ b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.c @@ -0,0 +1,6 @@ +#include + +int main(int argc, char **argv) { + hello(); + return 0; +} diff --git a/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.spec b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.spec new file mode 100644 index 0000000..a43e545 --- /dev/null +++ b/tests/brp-llvm-compile-lto-elf/brp-llvm-compile-lto-elf-test/brp-llvm-compile-lto-elf-test.spec @@ -0,0 +1,24 @@ +Name: brp-llvm-compile-lto-elf-test +Version: 1 +Release: 1 +Summary: Library package for testing brp-llvm-compile-lto-elf +License: MIT + +BuildRequires: gcc +BuildRequires: brp-llvm-compile-lto-elf-test-lib + +Source0: %{name}.c + +# FIXME: I'm not sure why this doesn't work +%undefine _package_note_file + + +%description +%{summary} + +%build +gcc ${CFLAGS} -c %{SOURCE0} -o %{name}.o +gcc ${LDFLAGS} %{name}.o %{_libdir}/%{name}-lib.a -o %{name} + +%check +./%{name} | grep "Hello, world!" diff --git a/tests/brp-llvm-compile-lto-elf/main.fmf b/tests/brp-llvm-compile-lto-elf/main.fmf new file mode 100644 index 0000000..ada5230 --- /dev/null +++ b/tests/brp-llvm-compile-lto-elf/main.fmf @@ -0,0 +1,8 @@ +Summary: Test that the brp-llvm-compile-lto-elf script is working correctly + +require: + - dnf-plugins-core + - redhat-rpm-config + - rpm-build + +test: ./runtest.sh diff --git a/tests/brp-llvm-compile-lto-elf/runtest.sh b/tests/brp-llvm-compile-lto-elf/runtest.sh new file mode 100755 index 0000000..1690d65 --- /dev/null +++ b/tests/brp-llvm-compile-lto-elf/runtest.sh @@ -0,0 +1,17 @@ +#!/bin/bash + +set -ex + +lib_dir=brp-llvm-compile-lto-elf-test-lib +lib_spec=$lib_dir/brp-llvm-compile-lto-elf-test-lib.spec + +dnf -y build-dep $lib_spec +rpmbuild --define "_sourcedir ." --define "_builddir ./$lib_dir" --define "_rpmdir ." -bb $lib_spec + +dnf -y install ./`rpm --eval '%{_arch}'`/*.rpm + +test_dir=brp-llvm-compile-lto-elf-test +test_spec=$test_dir/brp-llvm-compile-lto-elf-test.spec + +dnf -y build-dep $test_spec +rpmbuild --define "_sourcedir ." --define "_builddir ./$test_dir" -bi $test_spec