Source: freehsm-c Followup-For: Bug #1149536 X-Debbugs-Cc: [email protected], [email protected] User: [email protected] Usertags: amd64 Control: tags -1 ftbfs
Hi, The attached debdiff against 2.0.0-1 makes freehsm-c build on the 64-bit non-x86 architectures and stops trying on 32-bit ones: * fcf-protection-only-where-supported.patch: -fcf-protection=full is x86-only; the Makefile now probes the compiler and only adds it when it is accepted. This is #1144631. * elf-headers-unaligned-read.patch: find_section_offset() cast the file buffer to Elf64_Ehdr/Elf64_Shdr pointers, which -Werror=cast-align rejects on riscv64. It now copies the headers with memcpy. * debian/control: restrict Architecture to 64-bit architectures. Upstream does not support 32-bit at all, the integrity check only parses ELF64 (https://github.com/afchine1337/freehsm/issues/2). Both patches are also proposed upstream: https://github.com/afchine1337/freehsm/pull/18 Testing: 2.0.0-2 with the debdiff builds on amd64 in a forky container, with -fcf-protection=full still used there, and upstream's test-integrity passes with the ELF change. The same changes applied to 1.6.0 in Ubuntu (1.6.0-1ubuntu1) built in the Ubuntu archive on amd64, arm64, ppc64el, riscv64 and s390x. Regards, Sebastien -- System Information: Debian Release: forky/sid APT prefers resolute-updates APT policy: (500, 'resolute-updates'), (500, 'resolute-security'), (500, 'resolute'), (100, 'resolute-backports') Architecture: amd64 (x86_64) Kernel: Linux 7.0.0-38-generic (SMP w/16 CPU threads; PREEMPT) Kernel taint flags: TAINT_PROPRIETARY_MODULE, TAINT_WARN, TAINT_OOT_MODULE Locale: LANG=fr_FR.UTF-8, LC_CTYPE=fr_FR.UTF-8 (charmap=UTF-8), LANGUAGE not set Shell: /bin/sh linked to /usr/bin/dash Init: systemd (via /run/systemd/system) LSM: AppArmor: enabled
diff -Nru freehsm-c-2.0.0/debian/changelog freehsm-c-2.0.0/debian/changelog --- freehsm-c-2.0.0/debian/changelog 2026-09-03 22:05:46.000000000 +0200 +++ freehsm-c-2.0.0/debian/changelog 2026-10-09 16:15:39.000000000 +0200 @@ -1,3 +1,16 @@ +freehsm-c (2.0.0-2) UNRELEASED; urgency=medium + + * d/p/fcf-protection-only-where-supported.patch: only use -fcf- + protection=full when the compiler supports it, fixing the build on + non-x86 architectures (Closes: #1144631). + * d/p/elf-headers-unaligned-read.patch: read ELF headers with memcpy + instead of casting the buffer, fixing -Werror=cast-align on riscv64. + * d/control: restrict to 64-bit architectures; upstream does not + support 32-bit (https://github.com/afchine1337/freehsm/issues/2) + (Closes: #1149536). + + -- Sebastien Bacher <[email protected]> Fri, 09 Oct 2026 16:15:39 +0200 + freehsm-c (2.0.0-1) unstable; urgency=medium * Refresh d/patches diff -Nru freehsm-c-2.0.0/debian/control freehsm-c-2.0.0/debian/control --- freehsm-c-2.0.0/debian/control 2026-09-03 22:05:46.000000000 +0200 +++ freehsm-c-2.0.0/debian/control 2026-10-09 16:15:39.000000000 +0200 @@ -13,7 +13,7 @@ Vcs-Git: https://salsa.debian.org/debian/freehsm-c.git Package: freehsm-c -Architecture: any +Architecture: amd64 arm64 ppc64el riscv64 s390x loong64 mips64el sparc64 alpha ia64 Section: libs Multi-Arch: no Description: PKCS#11 module re-implementing FreeHSM Soft HSM diff -Nru freehsm-c-2.0.0/debian/patches/elf-headers-unaligned-read.patch freehsm-c-2.0.0/debian/patches/elf-headers-unaligned-read.patch --- freehsm-c-2.0.0/debian/patches/elf-headers-unaligned-read.patch 1970-01-01 01:00:00.000000000 +0100 +++ freehsm-c-2.0.0/debian/patches/elf-headers-unaligned-read.patch 2026-10-09 16:15:39.000000000 +0200 @@ -0,0 +1,74 @@ +Description: integrity: read ELF headers with memcpy instead of casting the buffer + find_section_offset() cast the file buffer to Elf64_Ehdr / Elf64_Shdr + pointers. The section header table offset comes from the file, so those + pointers are not guaranteed to be aligned, and on strict-alignment + targets such as riscv64 -Wcast-align (an error with -Werror) rejects + the casts: + . + src/fhsm_integrity.c: error: cast increases required alignment of + target type [-Werror=cast-align] + . + Copy the ELF header and each section header into local structs with + memcpy, which is valid whatever the alignment. While there, reject an + unexpected e_shentsize and sh_name values pointing outside the section + name string table. + . + The result is unchanged for valid files: test-integrity passes + (unsigned, signed and tampered cases). +Author: Sebastien Bacher <[email protected]> +Bug-Debian: https://bugs.debian.org/1149536 +Forwarded: https://github.com/afchine1337/freehsm/pull/18 +Last-Update: 2026-10-09 +--- +Index: freehsm-c-2.0.0/src/fhsm_integrity.c +=================================================================== +--- freehsm-c-2.0.0.orig/src/fhsm_integrity.c ++++ freehsm-c-2.0.0/src/fhsm_integrity.c +@@ -174,24 +174,33 @@ static int find_section_offset(const uin + const char *name, + size_t *out_off, size_t *out_len) + { ++ /* Copy the headers out with memcpy instead of casting into the ++ * buffer: casting a uint8_t pointer to Elf64_Ehdr / Elf64_Shdr is ++ * rejected by -Wcast-align on strict-alignment targets (riscv64), ++ * and the section table offset comes from the file. */ ++ Elf64_Ehdr eh; ++ Elf64_Shdr shstr, sh; + if (map_len < sizeof(Elf64_Ehdr)) return -1; +- const Elf64_Ehdr *eh = (const Elf64_Ehdr *)map; +- if (memcmp(eh->e_ident, ELFMAG, SELFMAG) != 0) return -1; +- if (eh->e_ident[EI_CLASS] != ELFCLASS64) return -1; +- if (eh->e_shoff == 0 || eh->e_shnum == 0) return -1; +- if (eh->e_shoff + (size_t)eh->e_shnum * eh->e_shentsize > map_len) return -1; ++ memcpy(&eh, map, sizeof eh); ++ if (memcmp(eh.e_ident, ELFMAG, SELFMAG) != 0) return -1; ++ if (eh.e_ident[EI_CLASS] != ELFCLASS64) return -1; ++ if (eh.e_shoff == 0 || eh.e_shnum == 0) return -1; ++ if (eh.e_shentsize != sizeof(Elf64_Shdr)) return -1; ++ if (eh.e_shoff + (size_t)eh.e_shnum * eh.e_shentsize > map_len) return -1; + +- const Elf64_Shdr *sh = (const Elf64_Shdr *)(map + eh->e_shoff); +- if (eh->e_shstrndx >= eh->e_shnum) return -1; +- const Elf64_Shdr *shstr = &sh[eh->e_shstrndx]; +- if (shstr->sh_offset + shstr->sh_size > map_len) return -1; +- const char *strtab = (const char *)(map + shstr->sh_offset); ++ const uint8_t *shtab = map + eh.e_shoff; ++ if (eh.e_shstrndx >= eh.e_shnum) return -1; ++ memcpy(&shstr, shtab + (size_t)eh.e_shstrndx * sizeof(Elf64_Shdr), sizeof shstr); ++ if (shstr.sh_offset + shstr.sh_size > map_len) return -1; ++ const char *strtab = (const char *)(map + shstr.sh_offset); + +- for (uint16_t i = 0; i < eh->e_shnum; ++i) { +- const char *n = strtab + sh[i].sh_name; ++ for (uint16_t i = 0; i < eh.e_shnum; ++i) { ++ memcpy(&sh, shtab + (size_t)i * sizeof(Elf64_Shdr), sizeof sh); ++ if (sh.sh_name >= shstr.sh_size) return -1; ++ const char *n = strtab + sh.sh_name; + if (strcmp(n, name) == 0) { +- *out_off = sh[i].sh_offset; +- *out_len = sh[i].sh_size; ++ *out_off = sh.sh_offset; ++ *out_len = sh.sh_size; + return 0; + } + } diff -Nru freehsm-c-2.0.0/debian/patches/fcf-protection-only-where-supported.patch freehsm-c-2.0.0/debian/patches/fcf-protection-only-where-supported.patch --- freehsm-c-2.0.0/debian/patches/fcf-protection-only-where-supported.patch 1970-01-01 01:00:00.000000000 +0100 +++ freehsm-c-2.0.0/debian/patches/fcf-protection-only-where-supported.patch 2026-10-09 16:15:39.000000000 +0200 @@ -0,0 +1,36 @@ +Description: build: only use -fcf-protection=full where the compiler supports it + -fcf-protection=full enables Intel CET and only exists on x86. On every + other architecture GCC fails with: + . + cc1: error: '-fcf-protection=full' is not supported for this target + . + so the module does not build on arm64, ppc64el, riscv64 or s390x. + . + Probe the compiler once and only add the flag when it is accepted. On + x86 the flags are unchanged. + . +Author: Sebastien Bacher <[email protected]> +Bug-Debian: https://bugs.debian.org/1144631 +Forwarded: https://github.com/afchine1337/freehsm/pull/18 +Last-Update: 2026-10-09 +--- +Index: freehsm-c-2.0.0/Makefile +=================================================================== +--- freehsm-c-2.0.0.orig/Makefile ++++ freehsm-c-2.0.0/Makefile +@@ -43,9 +43,14 @@ WARN_FLAGS = \ + -Wnull-dereference -Wdouble-promotion -Wconversion \ + -Wno-sign-conversion -Wno-unused-parameter + ++# -fcf-protection=full (Intel CET) only exists on x86; GCC rejects it as ++# "not supported for this target" everywhere else. Only use it when the ++# compiler accepts it. ++CF_PROTECTION_FLAG := $(shell $(CC) -Werror -fcf-protection=full -x c -c /dev/null -o /dev/null >/dev/null 2>&1 && echo -fcf-protection=full) ++ + HARDEN_FLAGS = \ + -fstack-protector-strong -D_FORTIFY_SOURCE=2 -fPIC \ +- -fstack-clash-protection -fcf-protection=full \ ++ -fstack-clash-protection $(CF_PROTECTION_FLAG) \ + -fvisibility=hidden -fno-strict-aliasing \ + -fno-omit-frame-pointer \ + -DOPENSSL_API_COMPAT=0x30000000L diff -Nru freehsm-c-2.0.0/debian/patches/series freehsm-c-2.0.0/debian/patches/series --- freehsm-c-2.0.0/debian/patches/series 2026-09-03 22:05:46.000000000 +0200 +++ freehsm-c-2.0.0/debian/patches/series 2026-10-09 16:15:30.000000000 +0200 @@ -1 +1,3 @@ inject-compiler-linker-flags.patch +fcf-protection-only-where-supported.patch +elf-headers-unaligned-read.patch

