Use DEH-backed green armor class in P_TouchSpecialThing#139
Merged
Conversation
Agent-Logs-Url: https://github.com/sunsided/room/sessions/459b1093-feb2-4ba6-8124-91f7ab52ba3c Co-authored-by: sunsided <495335+sunsided@users.noreply.github.com>
Copilot
AI
changed the title
[WIP] Fix hardcoded green armor class in P_TouchSpecialThing
Use DEH-backed green armor class in May 21, 2026
P_TouchSpecialThing
There was a problem hiding this comment.
Pull request overview
This PR fixes a behavioral mismatch in the Doom gameplay port by ensuring the green armor pickup (SPR_ARM1) uses a DEH-backed armor class value instead of a hardcoded 1, matching the upstream C logic and enabling runtime overrides to flow through the pickup path.
Changes:
- Add a
#[no_mangle] pub static mut deh_green_armor_classglobal initialized fromDEH_DEFAULT_GREEN_ARMOR_CLASS. - Update
P_TouchSpecialThingso the green armor pickup callsP_GiveArmor(player, deh_green_armor_class). - Add a unit test asserting the global defaults to the DEH constant and remove the stale FIXME about the previous hardcoding.
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Auto-generated GitNexus summary refreshed after re-analyze.
…in pickup paths Address PR #139 review feedback and reduce raw-pointer use in the pickup helpers. What: - Add DEH-tunable runtime globals matching upstream Chocolate Doom `p_inter.c`: `deh_max_health`, `deh_max_armor`, `deh_blue_armor_class`, `deh_max_soulsphere`, `deh_soulsphere_health`, `deh_megasphere_health`. Pickup paths (SPR_ARM2 / BON1 / BON2 / SOUL / MEGA) now read the runtime globals instead of `DEH_DEFAULT_*` constants, and the megasphere armor call drops the hardcoded `2`. - Drop the stale FIXME doc block on `P_TouchSpecialThing`: the `toucher->health <= 0` guard is already in the function body. - Expand the global-defaults unit test to cover every new `deh_*` static. - Convert pickup-path raw pointers to references inside `P_TouchSpecialThing`, `P_GiveAmmo`, `P_GiveWeapon`, `P_GiveBody`, `P_GiveArmor`, `P_GiveCard`, and `P_GivePower`. The `extern "C"` signatures still take `*mut PlayerT` / `*mut mobj_t`; the bodies bind `&mut` once after entry and use field access via `.`. Raw pointers are still passed to FFI helper calls. Why: - Match upstream behavior so DEHacked overrides flow through every pickup, not only green armor. - Improve doc accuracy after the dead-toucher guard was added in #128. - Reduce raw-pointer dereferences in the hot pickup paths so the borrow checker covers the common case while keeping the C ABI intact.
…or-class-hardcode # Conflicts: # room/src/doom/p_inter.rs
…ve aliasing UB Address PR #139 review feedback flagging undefined behavior: holding `&mut PlayerT` derived from a raw pointer while calling an `extern "C"` helper that re-derives `&mut PlayerT` from the same raw pointer creates overlapping mutable references and violates Rust's aliasing rules. What: - Add Rust-only inner functions taking `&mut PlayerT`: `p_give_ammo`, `p_give_weapon`, `p_give_body`, `p_give_armor`, `p_give_card`, `p_give_power`. - Reduce each `extern "C" fn P_Give*` to a thin shim that does the single `&mut *player` deref and delegates. - `p_give_weapon` and `p_give_power` now call the inner `p_give_*` helpers directly, passing the existing `&mut PlayerT` instead of reborrowing through the raw pointer. - `P_TouchSpecialThing` holds `&mut PlayerT` for the long-lived binding and uses the inner helpers, so no second `&mut PlayerT` is ever derived. `special` and `toucher` go back to raw `*mut` dereferences because `P_RemoveMobj` (an `extern "C"` helper that reborrows) is called against `special` in the epilogue. Why: - The previous "one top-level binding" pattern compiled but was UB under Stacked / Tree Borrows: every nested FFI call reborrowed the same `*mut PlayerT`, producing two live `&mut PlayerT` to the same memory. - Funneling the single `&mut PlayerT` through Rust-side helpers keeps the borrow checker covering the hot pickup paths while leaving the C ABI surface unchanged.
…ts to locals Address two PR #139 review comments. What: - Revert the megasphere (`SPR_MEGA`) armor grant to a hardcoded `2`. Upstream `p_inter.c` documents this explicitly: "We always give armor type 2 for the megasphere; dehacked only affects the MegaArmor". Routing it through `deh_blue_armor_class` would have diverged from vendor behavior. - Mirror the vendor comment about `deh_green_armor_class` not applying to the armor helmet (`SPR_BON2`). - In `P_TouchSpecialThing`, snapshot every `deh_*` `static mut` into a local at the top of the function instead of reading the global inside each match arm. Each unsafe static-mut read now happens once, in one place, instead of being scattered through the dispatch. Why: - Match upstream gameplay exactly; only the standalone MegaArmor pickup should react to DEHacked armor-class overrides. - Make the unsafety of static-mut reads visible at a single location and avoid hidden `unsafe_op_in_unsafe_fn`-style noise in the dispatch arms.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
P_TouchSpecialThinghandledSPR_ARM1differently from the C implementation by hardcoding armor class1. That bypassed the runtimedeh_green_armor_classvalue and ignored Dehacked overrides for green armor pickups.Behavior fix
SPR_ARM1pickup path inroom/src/doom/p_inter.rsfrom a hardcoded armor class todeh_green_armor_class.DEH-backed state
deh_green_armor_classglobal initialized fromDEH_DEFAULT_GREEN_ARMOR_CLASS.Code cleanup
FIXMEdocumenting the hardcoded value once the port mismatch is resolved.Regression coverage
Warning
Firewall rules blocked me from connecting to one or more addresses (expand for details)
I tried to connect to the following addresses, but was blocked by firewall rules:
dl.google.com/usr/lib/apt/methods/https /usr/lib/apt/methods/https /home/REDACTED/work/room/room/target/debug/deps/bytemuck_derive-16f098d6c9015d52.bembed-bitcode=no /home/REDACTED/work/room/room/target/debug/deps/bytemuck_derive-16f098d6c9015d52.b-C /home/REDACTED/work/room/room/target/debug/deps/bytemuck_derive-16f098d6c9015d52.bdebuginfo=2 ist /home/REDACTED/work/room/room/target/debug/deps/bytemuck_derive-16f098d6c9015d52.bcfg(docsrs,test) /home/REDACTED/work/room/room/target/debug/deps/bytemuck_derive-16f098d6c9015d52.b--check-cfg /home/REDACTED/work/room/room/target/debug/deps/rustcpubmlD/rmeta.o iserror_impl.43a1e06bdc12391-cgu.00.rcgu.o iserror_impl.43a1e06bdc12391-cgu.01.rcgu.o iserror_impl.43a1e06bdc12391-cgu.02.rcgu.o iserror_impl.43a1e06bdc12391-cgu.03.rcgu.o iserror_impl.43a1e06bdc12391-cgu.04.rcgu.o iserror_impl.43a1e06bdc12391-cgu.05.rcgu.o iserror_impl.43a1e06bdc12391-cgu.06.rcgu.o iserror_impl.43a1e06bdc12391-cgu.07.rcgu.o iserror_impl.43a1e06bdc12391-cgu.08.rcgu.o iserror_impl.43a1e06bdc12391-cgu.09.rcgu.o iserror_impl.43a1e06bdc12391-cgu.10.rcgu.o iserror_impl.43a1e06bdc12391-cgu.11.rcgu.o(dns block)If you need me to access, download, or install something from one of these locations, you can either: