Bug 509572 - s390x: Overhaul BFP testsuite
Summary: s390x: Overhaul BFP testsuite
Status: RESOLVED FIXED
Alias: None
Product: valgrind
Classification: Developer tools
Component: general (other bugs)
Version First Reported In: unspecified
Platform: Other Linux
: NOR normal
Target Milestone: ---
Assignee: Florian Krohm
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2025-09-16 22:15 UTC by Florian Krohm
Modified: 2025-09-26 21:55 UTC (History)
0 users

See Also:
Latest Commit:
Version Fixed In:
Sentry Crash Report:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Florian Krohm 2025-09-16 22:15:51 UTC
I plan to overhaul BFP testcases.

The key observation (and that is no surprise at all) is that for
many BFP insns the following holds:

If guest code contains BFP insn XYZ then at the end of the VEX pipeline
insn XYZ will be emitted for it. We also know that the IR optimisers won't
touch floating point IROps.

Today our testing looks like this (from fpconv.stdout.exp):

----- int32_t -> double
cdfbr 0 -> 0.000000
cdfbr 1 -> 1.000000
cdfbr -1 -> -1.000000
cdfbr 42 -> 42.000000
cdfbr 32767 -> 32767.000000
cdfbr -32768 -> -32768.000000
cdfbr 2147483647 -> 2147483647.000000
cdfbr -2147483648 -> -2147483648.000000

This is not interesting at all. We're not interested
- to verify that hardware works correctly
- to find suitable width and precision for printf format strings (depending
  on the floating point value)
- finding bugs in printf implementation

In other words, all those values above are boring.

What we *do* want to know is whether for a given BFP insn XYZ the
very same insn is emitted in the end.

How do we do that? Using cdfbr as the example:

1) Create a testcase template:
   auxprogs/s390-runone -t > foo.c
2) Replace the FIXME line with an asm stmt containing the insn we want to test:
   sed -i "s/^.*FIXME.*/  asm volatile (\"cdfbr %f0,%f1\");/"  foo.c
3) Compile foo.c into an executable "foo" not requiring the dynamic
   loader. The executable will have exactly one superblock.
   auxprogs/s390-runone foo.c
4) Run valgrind, trace IR generation and assembly and filter the output:
   coregrind/valgrind --tool=none --trace-notbelow=0 --trace-flags=10000001 ./foo 2>&1 | egrep "(Front|Assembly|cdfbr)"

This will print:

------------------------ Front end ------------------------
cdfbr     %f0,%r1
------------------------ Assembly ------------------------
cdfbr     %f7,%r5

Voila.

For non-commutative binary operators having testcases that write out register
contents is a good thing because it allows to find operand order errors.

Everything I said about BFP also holds for DFP.
And I bet it also holds for other architectures.
Comment 1 Florian Krohm 2025-09-17 09:49:46 UTC
A related bugs is https://bugs.kde.org/show_bug.cgi?id=306098
Comment 2 Florian Krohm 2025-09-19 13:02:37 UTC
Some more obervations in no particular order:

We need sizeof(long double) == 128 to be able to test 128-bit BFP
The GCC I'm using (11.4.0) says:

'-mlong-double-64'
'-mlong-double-128'
     These switches control the size of 'long double' type.  A size of
     64 bits makes the 'long double' type equivalent to the 'double'
     type.  This is the default.

So we need to add -mlong-double-128 when compiling because we cannot assume that GCC has been
configured --with-long-double-128.    if HAS_MLONG_DOUBLE_128 ...

----------
For some insns the behaviour depends on whether or not the floating-point extension is
installed. That is a royal pain to distinguish. I am going to make all testcases assume that
it is installed.
---------

Another thing.. We ought to check for correct computation of condition codes. Those get
computed from the cc thunk in the guest state. Affected insns are:
- ADD
- COMPARE
- COMPARE AND SIGNAL
- CONVERT TO FIXED
- CONVERT TO LOGICAL
- DIVIDE TO INTEGER
- LOAD AND TEST
- LOAD COMPLEMENT
- LOAD NEGATIVE
- LOAD POSITIVE
- SUBTRACT
 - TEST DATA CLASS
Comment 3 Florian Krohm 2025-09-26 21:55:45 UTC
Now fixed.
9a1dbff3812a71ea556b9d80056a11ca8ff88023
78f1569e2235796256742d7c75763034677065af
b1f875b63d6a07115dfba571c6dcc1f280c0b1f4
2c79953bd75b4c9bb36a4ff4ccfa3675e1aa7e36
7d9005f4912fa02eb48dcf578f40c035d8cc851b
73ece460ef7e891b404576fd7cc8bd92f4f753ed
6190acedb1d5f1e8a3365e8affcf8ce5c0beac0f
69e67dadf5572b5e6521da2b87633d503f1d597b
ce0b91e1e49af679c1cbd51d88b5a95df7fc3c29
d8cf0a84b26ff1ed1b5a9560bfbe5bf476f10c3a
18c5454874d9193fb422832523925406f1d32b80
c574f5eb10d06b491512806354f8d15c3d3e020a
1109ef57b23cf84be551cb9d25373a8169bedce4