Hi,

Found a problem that comes with patch 7 and glibc multiarch builds.

As soon as HWCAP_SPARC_CRYPTO is visible, glibc chooses the niagara4
routines (SPARC T4 and later), and on the sun4u model with +crypto they
die with SIGILL.

glibc's niagara4 memcpy/memset use block-init stores (ASI 0xe2,
ASI_BLK_INIT_QUAD_LDD_P). gen_st_asi() only accepts that store on CPUs
with CPU_FEATURE_HYPV.

Note that this does not reproduce with Debian's sparc64 glibc, without
multiarch. I reproduced with Gentoo stage3, built with -mcpu=ultrasparc
and multiarch glibc 2.44.

A small change to translate.c, function gen_st_asi(), fixes the
problem.

diff --git a/target/sparc/translate.c b/target/sparc/translate.c
index 921ffd2d1b..931fc006ce 100644
--- a/target/sparc/translate.c
+++ b/target/sparc/translate.c
@@ -1863,8 +1863,12 @@ static void gen_st_asi(DisasContext *dc,
DisasASI *da, TCGv src, TCGv addr)
         if (TARGET_LONG_BITS == 32) {
             gen_exception(dc, TT_ILL_INSN);
             break;
-        } else if (!(dc->def->features & CPU_FEATURE_HYPV)) {
-            /* Pre OpenSPARC CPUs don't have these */
+        } else if (!(dc->def->features &
+                    (CPU_FEATURE_HYPV | CPU_FEATURE_CRYPTO))) {
+            /*
+             * Pre-OpenSPARC CPUs lack block-init stores. Crypto
instructions
+             * imply T4 or later, which supports them.
+             */
             gen_exception(dc, TT_ILL_INSN);
             break;
         }

My kernel tests missed this, so will improve my testing routines going
forward. Sorry about this extra noise.

The fix is queued for v3.

/Stian

On Wed, 2026-10-21 at 08:46 +0200, Stian Halseth wrote:
> Set HWCAP_SPARC_CRYPTO in AT_HWCAP like Linux does on real hardware
> that supports it. qemu-sparc64 defaults to "TI UltraSparc II",
> which has no crypto feature, so it must be enabled explicitly,
> e.g. -cpu TI-UltraSparc-II,+crypto
> 
> Reviewed-by: Philippe Mathieu-Daudé <[email protected]>
> Signed-off-by: Stian Halseth <[email protected]>
> ---
>  linux-user/sparc/elfload.c | 1 +
>  1 file changed, 1 insertion(+)
> 
> diff --git a/linux-user/sparc/elfload.c b/linux-user/sparc/elfload.c
> index 181f1e00b5..0412741285 100644
> --- a/linux-user/sparc/elfload.c
> +++ b/linux-user/sparc/elfload.c
> @@ -90,6 +90,7 @@ abi_ulong get_elf_hwcap(CPUState *cs)
>      r |= features & CPU_FEATURE_FMAF ? HWCAP_SPARC_FMAF : 0;
>      r |= features & CPU_FEATURE_VIS3 ? HWCAP_SPARC_VIS3 : 0;
>      r |= features & CPU_FEATURE_IMA ? HWCAP_SPARC_IMA : 0;
> +    r |= features & CPU_FEATURE_CRYPTO ? HWCAP_SPARC_CRYPTO : 0;
>  #endif
>  
>      return r;

Attachment: signature.asc
Description: This is a digitally signed message part

Reply via email to