[tsan] Calibrate jmp_buf pointer mangling (#216558)
glibc 2.44 moved the pointer guard out of the TCB and added the
x86-style rotation on other mangling targets. TSan hardcodes the old
guard locations and transformations, so longjmp interception can no
longer recover the saved stack pointer.
Derive the identity, XOR, or XOR-and-rotate scheme from two _setjmp
probes at different stack depths. This supports old and new glibc and
preserves bionic lazy initialization without depending on private guard
storage.
Developed with Fable/Sol. Tested locally on 64-bit Arch Linux, which
already ships glibc 2.44. Without this change, eight existing TSan tests
fail with `ThreadSanitizer: can't find longjmp buf`; with it, the full
`check-tsan` suite passes.
Fixes #216004.
[Matrix] Create the copy alloca once in getNonAliasingPointer (NFC). (#237455)
Both the different address space path and the runtime alias check path
create the same alloca in the entry block. Create it once up front.
[KnownFPClass][NFC] Apply denormal modes inside KnownFPClass functions (#237084)
Converts remaining `KnownFPClass` functions over to the
`applyInputDenormalMode` and `applyOutputDenormalMode` helpers. This
also switches `isKnownNeverLogicalZero(Mode)` to `isKnownNever(fcZero)`.
`KnownFPClass::canonicalize` will be handled in a separate PR.
[KnownFPClass] Rule out non-zero finite results for fmul and fdiv (#231052)
Follow up to https://github.com/llvm/llvm-project/pull/229638
A normal or subnormal result of `fmul`/`fdiv` requires both operands to
be non-zero finite values. In other words, we don't care if either side
could be zero, inf, or NaN when ruling out normal/subnormal values.
Revert "[LV] Model memory runtime checks for inner loops of loop nests in VPlan." (#237453)
Reverts llvm/llvm-project#232794
Breaks bots, see llvm/llvm-project#232794.
[MIR] Round-trip the "func" kind of inline asm operand flags
An x86 inline asm call or jmp whose target is a function, given as a "p"
operand or as a "*m" operand that ISel turns into an address, gets a flag
of kind Func. Like a Mem flag, it carries a memory constraint. But
getKindName() returned "mem" for it, and the MIR printer printed the
constraint only for a Mem flag. So this:
call void asm sideeffect "call ${0:P}", "p,~{dirflag},~{fpsr},~{flags}"(ptr @g)
was printed as:
INLINEASM &"call ${0:P}", sideeffect attdialect, mem ops:5, target-flags(x86-plt) @g, 1, $noreg, 0, $noreg, ...
which parses back as a Mem flag with no constraint. Printing that again
hits llvm_unreachable, and the asm printer asserts in PrintMemReference()
instead of emitting "callq g at PLT". MachineInstr::print() also printed the
constraint as a register class (e.g. "mem:GR8_NOREX").
[4 lines not shown]
[MIR] Move the "func" kind round trip to its own PR
Round-tripping the "func" kind of inline asm operand flags is separate
from serializing the operand count, so it moves to its own PR, stacked
on this one, with more tests.
Assisted-by: Claude Opus 5.5
[LV] Invalidate interleave-groups with gaps if for early-exit loops. (#237409)
If the loop exits from a block other than the latch, the scalar
iteration reserved for the exit may leave the loop before reaching the
grouped accesses.
Invalidate interleave groups in the case, to avoid mis-compile.
Fixes https://github.com/llvm/llvm-project/issues/237192.
[Clang][Offload] Request canonical target IDs in --should-extract (#232148)
The linker wrapper extracts device code from a static library only when
a `--should-extract` value matches the device image's arch label
exactly. The label is the canonical target ID, with features sorted, but
`--should-extract` used the raw `--offload-arch` value. So
`--offload-arch=gfx908:xnack+:sramecc-` labeled the device image
`gfx908:sramecc-:xnack+` but requested `gfx908:xnack+:sramecc-`. Add a
`getCanonicalTargetID` helper that takes a raw target ID, and use it for
both the label and `--should-extract`.
[BOLT][AArch64] Keep the addend when relaxing LDR (literal) (#236975)
`createAdrpLdr()` took only the symbol out of the LDR (literal) operand
and built the ADRP+LDR pair with addend 0. For a literal inside a sized
data object symbolized as object + offset, the relaxed load would read
the start of the object instead of the literal.
`undoAdrpAddRelaxation()` already carries the addend; this makes the LDR
path do the same.
Assited-by: Opus-5.5
[BOLT] Place callee-saved restores before conditional tail calls in shrink wrapping (#236434)
Fixes https://github.com/llvm/llvm-project/issues/236353
## Problem
`-frame-opt=hot` (shrink wrapping) combined with
`-indirect-call-promotion=all`
miscompiles CPython 3.12. Shrink wrapping computes the dominance
frontier of
the save point to determine restore placement. Conditional tail calls
introduced by IndirectCallPromotion exit the function via an edge to an
external
symbol that is not represented as a CFG successor, so they never appear
in the
dominance frontier. As a result no restore is emitted on the promoted
tail-call
path, leaking a clobbered callee-saved register to the caller.
[24 lines not shown]
[RISCV] Make $rs an output of PseudoTAILReg. (#237443)
It's used as the temporary register for the AUIPC when expanded so it
should be an output.
Assisted-by: Claude
[RISCV] Add Defs to PseudoTAIL and PseudoTAILX7.
Annonyingly PseudoTAIL can def either X6 or X7 depending on Zicfilp
and the version of the assembler being used.
Part of fixing #235697.
[libunwind] Support extended amd64 segment registers on FreeBSD (#237265)
Raise the amd64 DWARF register limit to 59 and add RFLAGS, all six
segment selectors, FS.base, and GS.base to the register model. Capture
the extended state and restore it when resuming, using setcontext on
FreeBSD to restore selectors and bases together. Pack the state into the
existing context buffers without changing their public sizes or the
Windows XMM offsets.
Add tests for register access, signal-frame CFI recovery, register
bounds, and resume behavior.
Assisted-by: GPT
Check stack are register context in ThreadPlanCallFunction::DoTakedown (#217759)
I get a couple of crashes a year in ThreadPlanCallFunction::DoTakedown
on the line where we get the PC from the thread. It looks like the
RegisterContext (or maybe GetStackFrameAtIndex(0)) are returning null.
The crashes are when the UI calls UnwindInnermostFrame so I know that
thread has to be valid. So the only possibilities I can think of are
that we couldn't reconstruct the stack frame at index 0 or its register
context. I don't know how that would happen, but there's no harm in
being more careful accessing the register context.
[RISCV] Make $rs an output of PseudoTAILReg.
It's used as the temporary register for the AUIPC when expanded
so it should be an output.
Assisted-by: Claude
[tsan] Increase per-thread held lock limit in DeadlockDetectorTLS to 512 (#232882)
When running under ThreadSanitizer with deadlock detection enabled
(`detect_deadlocks=1`), `DeadlockDetectorTLS::addLock` enforces a hard
limit on the number of distinct locks a single thread may hold
simultaneously via `CHECK_LT(n_all_locks_,
ARRAY_SIZE(all_locks_with_contexts_))`.
Although #116409 previously raised this limit from 64 to 128, workloads
that initialize large RPC frameworks, worker pools, or sharded data
structures (such as C++ extensions under free-threaded Python) can hold
more than 128 locks simultaneously on one thread during initialization,
triggering a fatal `CHECK` failure.
Increase `all_locks_with_contexts_` capacity from 128 to 512. Each
`LockWithContext` entry is 8 bytes (`u32 lock; u32 stk;`), adding 3 KB
per heap-allocated `DDLogicalThread` when `detect_deadlocks=1` while
remaining well below `TwoLevelBitVector` capacity (`DDBV::kSize`, which
is 4096 on 64-bit platforms and 1024 on 32-bit platforms).
[3 lines not shown]
[ci] Collect profiles in the LLVM test-suite LNT runs on Linux
Run the test-suite with `--use-perf all` on Linux, which collects profiling
data and submits it to LNT. Bump both machines since the version of the
test suite also changes.
Assisted by Claude
[SHT_LLVM_BB_ADDR_MAP] Emit the function GUID for local-linkage functions (#237345)
Add the `-basic-block-address-map-emit-func-guid` flag to emit the
function GUID (the `FuncGUID` feature added in #231675) in the
SHT_LLVM_BB_ADDR_MAP section. The GUID is only emitted for functions
with local linkage, whose symbol names may not be unique across
translation units. Other functions can be identified by their symbol
names, so the feature bit is left unset for them.
The GUID assigned by AssignGUIDPass (`!guid` metadata) is used when
available. Otherwise, it is computed from the module's source file name
and the function's current name, since AssignGUIDPass only runs in the
(Thin)LTO pre-link pipelines.
This also bumps the emitted SHT_LLVM_BB_ADDR_MAP version to 6, which is
required for the FuncGUID feature.
Assisted-by: Claude Opus 5.5