The null-deref-1.c testcase (from compiler-rt null_deref.cc) fails on s390x with -march=zEC12.
The problem is that sanitizer_common and asan doesn't care about important difference in PCs in backtraces.
Most of the PCs are return addresses after calls, and as such for unwind info as well as source locations (symbolization)
it is desirable to apply StackTrace::GetPreviousInstructionPc on them (though it is questionable if it should be applied
also to the addresses actually printed in the backtrace, e.g. GDB prints the return addresses instead), because at
the return address might be e.g. already start of a different function or unrelated code (especially for noreturn functions,
but generally you want the location of the call, not whatever instruction is after it too).
But, for synchronously delivered signals, such as SIGSEGV and various others, the PC you get from unwind info
or from siginfo of the fatal signal is not any kind of return pc, but the start of the instruction that couldn't be executed
because it faulted. If such instruction e.g. happens to be the very first one in the function, by subtracting one you might
appear in a completely unrelated function. And in any case, you want the location of the faulting instruction, not whatever
appears before it.
The unwinder has for many years a new API I've added, _Unwind_GetIPInfo, which has an extra argument that tells
what kind of PC it returns, if it is a PC after a call insn or PC before faulting instruction (signal frame).
Unfortunately right now the sanitizer backtrace code has recording of PCs into an array and calling
StackTrace::GetPreviousInstructionPc as separate steps quite far away, where all context is lost.
This patch is a hack, basically for PCs from the second category (i.e. which point before the faulting instruction)
it adds a small number to those so that when StackTrace::GetPreviousInstructionPc is called, it will return
the address of the faulting instruction rather than something before it. The printed hex PCs will be then
correct for these and still bogus (pointing to inside the call insn) otherwise (the latter as before).
If we want to fix that, I think we'd need to record the flags what kind of PCs it is in trace_buffer or in array next to it,
and then always use the PCs from the trace_buffer as is for printing, and for the return addresses
only use StackTrace::GetPreviousInstructionPc for symbolization purposes.