Files
whitemagic/openspec/changes/whitemagic-foundation/specs/function-hooking/spec.md
T
2026-07-21 22:30:10 +02:00

2.5 KiB

ADDED Requirements

Requirement: Reversible inline detours

WhiteMagic SHALL provide a DetourManager that creates named inline detours redirecting a target function to a managed hook, supporting Apply, Remove, and calling the original function. Detours operate in-process.

Scenario: apply redirects the target

  • WHEN a detour from a target function to a hook delegate is applied
  • THEN calling the target MUST invoke the hook delegate

Scenario: call original

  • WHEN the hook invokes CallOriginal(args)
  • THEN the original target behavior MUST execute with those arguments and its result returned

Scenario: remove restores original bytes

  • WHEN an applied detour is removed
  • THEN the target's original prologue bytes MUST be restored and calling the target MUST no longer invoke the hook

Scenario: named lookup

  • WHEN a detour is created with a name
  • THEN it MUST be retrievable from the manager by that name

Requirement: Instruction-boundary validation before splicing

Before overwriting a target prologue, the detour SHALL verify the overwrite covers whole instructions so that no instruction is split.

Scenario: aligned splice permitted

  • WHEN the bytes required for the jump cover a whole number of prologue instructions
  • THEN the detour MUST apply

Scenario: misaligned splice rejected

  • WHEN the required overwrite would end in the middle of an instruction and boundary information is available
  • THEN the detour MUST refuse to apply rather than corrupt the target

Requirement: Named reversible byte patches

WhiteMagic SHALL provide a PatchManager that creates named byte patches with Apply, Remove, and IsApplied, usable in both external and in-process modes.

Scenario: apply writes patch bytes

  • WHEN a patch is applied at an address
  • THEN memory at that address MUST equal the patch bytes

Scenario: remove restores original

  • WHEN an applied patch is removed
  • THEN memory at that address MUST equal the original bytes captured at creation

Scenario: is-applied reflects state

  • WHEN IsApplied is queried
  • THEN it MUST return true only when the current bytes equal the patch bytes

Requirement: Auto-restore on dispose

All live detours and patches SHALL be reverted when their owning MemoryBase is disposed.

Scenario: dispose reverts modifications

  • WHEN a MemoryBase with active detours and patches is disposed
  • THEN every modified region MUST be restored to its pre-modification bytes