Skip to content

Deny partial -Z stack-protector by default in all editions - #157941

Open
arielb1 wants to merge 1 commit into
rust-lang:mainfrom
arielb1:deny-partial-stack-protector
Open

Deny partial -Z stack-protector by default in all editions#157941
arielb1 wants to merge 1 commit into
rust-lang:mainfrom
arielb1:deny-partial-stack-protector

Conversation

@arielb1

@arielb1 arielb1 commented Jun 15, 2026

Copy link
Copy Markdown
Contributor

This enables RFC 3855 for stack-protector. With this PR, uses of stack-protector that only have it enabled for a subset of the crates within a process need to pass -Z allow-partial-mitigations=stack-protector as well.

This was not done in #149357 to allow for a smooth transition period.

cc the stack-protector tracking issue at #114903.

r? @rcvalle (do we need any special protocol for the breaking change?)

@rustbot rustbot added A-LLVM Area: Code generation parts specific to LLVM. Both correctness bugs and optimization-related issues. S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. labels Jun 15, 2026
@rustbot

This comment has been minimized.

@arielb1
arielb1 force-pushed the deny-partial-stack-protector branch from cffa608 to 1a9ed85 Compare June 15, 2026 21:47
@rustbot

This comment has been minimized.

@arielb1
arielb1 force-pushed the deny-partial-stack-protector branch from 1a9ed85 to 5e3dc2c Compare June 15, 2026 21:51
@rustbot

This comment has been minimized.

@arielb1
arielb1 force-pushed the deny-partial-stack-protector branch from 5e3dc2c to 42cf0c9 Compare June 15, 2026 21:52
@rust-log-analyzer

This comment has been minimized.

@arielb1
arielb1 force-pushed the deny-partial-stack-protector branch from 42cf0c9 to 7312a2c Compare June 15, 2026 22:47
@rustbot

rustbot commented Jun 15, 2026

Copy link
Copy Markdown
Collaborator

Some changes occurred in tests/codegen-llvm/stack-protector.rs

cc @rust-lang/project-exploit-mitigations, @rcvalle

@rustbot rustbot added the PG-exploit-mitigations Project group: Exploit mitigations label Jun 15, 2026
This enables RFC 3855 for stack-protector. With this PR, uses of stack-protector
that only have it enabled for a subset of the crates within a process need to pass
`-Z allow-partial-mitigations=stack-protector` as well.

This was not done in issue 149357 to allow for a smooth transition period.

cc the stack-protector tracking issue at issue 114903.
@arielb1
arielb1 force-pushed the deny-partial-stack-protector branch from 7312a2c to 5edba65 Compare June 15, 2026 22:57
@rust-bors

rust-bors Bot commented Jul 13, 2026

Copy link
Copy Markdown
Contributor

☔ The latest upstream changes (presumably #159246) made this pull request unmergeable. Please resolve the merge conflicts by rebasing.

@apiraino

Copy link
Copy Markdown
Contributor

Visited during triage on Zulip.

(do we need any special protocol for the breaking change?)

The lang FCP is enough so this PR can be just reviewed.

cc @rcvalle when you have time (or free to reroll another reviewer)

thanks!

bgonz808 added a commit to bgonz808/hp-thermal that referenced this pull request Aug 25, 2026
…coverage (#314)

* harden: /CETCOMPAT (backward-edge CFI) + machine-enforced mitigation coverage

Two additions, both from the nightly-feature research, and both made ENFORCED rather than
merely set — a mitigation we asked for is not a mitigation we have.

/CETCOMPAT — the missing half of control-flow integrity. `control-flow-guard=checks` has
protected indirect CALLS since the beginning; nothing protected RETURNS. /CETCOMPAT marks
the image compatible with the CPU's hardware shadow stack, which keeps a protected copy of
return addresses and faults on divergence. That is the direct answer to ROP, which CFG does
not address.

  * STABLE — a plain linker flag, no nightly needed.
  * Measured cost: 0 bytes.
  * COMPATIBILITY, since it is a fair question: it is a MARK, not a requirement. Microsoft's
    docs describe it as telling the linker to "mark the binary as CET Shadow Stack-
    compatible". Windows enables shadow stacks only where CPU and OS support them AND the
    image opts in; on hardware without CET there is nothing to enable. Every x86_64 CPU
    still runs the binary — the ones with CET run it with more protection. x64-only per the
    same docs, which is our only target.

-Z deny-partial-mitigations=stack-protector,control-flow-guard — turns a comment into an
invariant. The config asserted "build-std rebuilds std with it too, so protection is
whole-binary". That was true and unverified. Now the build FAILS if any crate in the graph,
std included, is compiled without those mitigations. Partial application is the dangerous
case precisely because the binary carries the flag and the reassurance while leaving gaps.
Upstream intends this as the default (rust-lang/rust#157941); adopting it now means passing
by construction rather than by luck.

ENFORCEMENT, not just configuration. CET does NOT live in the optional header's
DllCharacteristics like ASLR/DEP/CFG — it travels in a debug-directory entry of type 20
(IMAGE_DEBUG_TYPE_EX_DLLCHARACTERISTICS), so it needed its own reader. CET_COMPAT is now
measured structurally and ratcheted with the rest: lose it and the gate fires. Recorded
under its own name rather than folded into CONTROL_FLOW_GUARD because the two are
independently settable and defend opposite edges — collapsing them would let one vanish
while the manifest still looked complete.

Verified in both directions, per the #303 lesson: the decoder reports CET_COMPAT absent on
every binary built so far (none used the flag), and unit tests pin the positive case,
including that an unrelated extended bit must not read as CET.

EXPECTED on the next build: the caps gate will fire with "hardening CHANGED: binary has
CET_COMPAT, manifest does not declare it". That is the ratchet working; the manifest is
deliberately not pre-updated, because it should describe measured reality rather than assert
a posture ahead of measuring it.

OS-SCOPING, since it was asked: no change needed. These flags live under
[target.x86_64-pc-windows-msvc], so they are already applied per-target by construction. A
future Linux target would carry its own section and would not inherit any of this.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

* harden: record CET_COMPAT for hp-thermal — the sign-off on a measured change

The caps ratchet fired on the first build with the new flags, as predicted:

    verify-caps: FAIL - 1 manifest violation(s) for hp-thermal:
      - hardening CHANGED: binary has CET_COMPAT, manifest does not declare it

Three things are established by that single line, none of which were true before:

  1. /CETCOMPAT ACTUALLY LANDED. The reader had only ever been exercised in the negative
     direction, because no binary we had built carried the flag. It now reports the bit on a
     real artifact, so the positive path is proven on something other than a unit test.
  2. deny-partial-mitigations PASSED. The build succeeded, which means every crate in the
     graph -- std and its dependencies included -- really is compiled with stack-protector
     and control-flow-guard. The config has claimed whole-binary coverage for a long time;
     that claim is now machine-checked rather than asserted.
  3. The ratchet caught a posture change on the first opportunity, which is what it is for.

Recording CET_COMPAT is the sign-off. Exactly ONE violation was reported: the import surface
did not move, so the two new flags changed protection without changing what the binary
reaches for.

Scope note: this covers hp-thermal only. The producer's RUSTFLAGS for the tool fleet do not
yet include /CETCOMPAT, so the tools still have forward-edge CFI and no backward edge.
Extending it there costs a full producer run and re-bless of all six digests, so it is left
as a deliberate follow-up rather than folded in here.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

A-LLVM Area: Code generation parts specific to LLVM. Both correctness bugs and optimization-related issues. PG-exploit-mitigations Project group: Exploit mitigations S-waiting-on-review Status: Awaiting review from the assignee but also interested parties. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants