Repository: dotnet/runtime
File: src/coreclr/nativeaot/Runtime/amd64/GcProbe.asm (Assembly)

Code before:
        call        RhpGcPoll2
        POP_COOP_PINVOKE_FRAME
        ret
NESTED_END RhpGcPollRare, _TEXT



ifdef FEATURE_GC_STRESS

;;
;; GC Stress Hijack targets
;;
LEAF_ENTRY RhpGcStressHijack, _TEXT
        FixupHijackedCallstack
        mov         r8d, DEFAULT_FRAME_SAVE_FLAGS + PTFF_SAVE_RAX + PTFF_SAVE_RCX
        jmp         RhpGcStressProbe
LEAF_END RhpGcStressHijack, _TEXT

;;
;; Worker for our GC stress probes.  Do not call directly!!
;; Instead, go through RhpGcStressHijack{Scalar|Object|Byref}.
;; This worker performs the GC Stress work and returns to the original return address.
;;
;; Register state on entry:
;;  RDX: thread pointer
;;  RCX: register bitmask
;;
;; Register state on exit:
;;  Scratch registers, except for RAX/RCX, have been trashed
;;  All other registers restored as they were when the hijack was first reached.
;;
NESTED_ENTRY RhpGcStressProbe, _TEXT
        PUSH_PROBE_FRAME rdx, rax, r8
        END_PROLOGUE

        call        RhpStressGc

        POP_PROBE_FRAME
        ret
NESTED_END RhpGcStressProbe, _TEXT

;; PAL_LIMITED_CONTEXT, 6 xmm regs to save, 2 scratch regs to save, plus 20h bytes for scratch space
RhpHijackForGcStress_FrameSize equ SIZEOF__PAL_LIMITED_CONTEXT + 6*10h + 2*8h + 20h

; -----------------------------------------------------------------------------------------------------------
; RhpHijackForGcStress
;
; Called at the beginning of the epilog when a method is bound with /gcstress
;
; N.B. -- Leaf frames may not have aligned the stack or reserved any scratch space on the stack.  Also, in
;         order to have a resonable stacktrace in the debugger, we must use the .pushframe unwind directive.

Review comment (suggestion):
The comment stating "RCX: register bitmask" is outdated. The register bitmask is now passed in R8, not RCX, as seen in the code on line 150 where r8d is set to the flags and line 168 where r8 is passed to PUSH_PROBE_FRAME. This change was necessary to preserve RCX for async continuation return values. The comment should be updated to say "R8: register bitmask".
```suggestion
;;  R8: register bitmask
```

Code after:
        call        RhpGcPoll2
        POP_COOP_PINVOKE_FRAME
        ret
NESTED_END RhpGcPollRare, _TEXT



ifdef FEATURE_GC_STRESS

;;
;; GC Stress Hijack targets
;;
LEAF_ENTRY RhpGcStressHijack, _TEXT
        FixupHijackedCallstack
        mov         r8d, DEFAULT_FRAME_SAVE_FLAGS + PTFF_SAVE_RAX + PTFF_SAVE_RCX
        jmp         RhpGcStressProbe
LEAF_END RhpGcStressHijack, _TEXT

;;
;; Worker for our GC stress probes.  Do not call directly!!
;; Instead, go through RhpGcStressHijack{Scalar|Object|Byref}.
;; This worker performs the GC Stress work and returns to the original return address.
;;
;; Register state on entry:
;;  RDX: thread pointer
;;  R8: register bitmask
;;
;; Register state on exit:
;;  Scratch registers, except for RAX/RCX, have been trashed
;;  All other registers restored as they were when the hijack was first reached.
;;
NESTED_ENTRY RhpGcStressProbe, _TEXT
        PUSH_PROBE_FRAME rdx, rax, r8
        END_PROLOGUE

        call        RhpStressGc

        POP_PROBE_FRAME
        ret
NESTED_END RhpGcStressProbe, _TEXT

;; PAL_LIMITED_CONTEXT, 6 xmm regs to save, 2 scratch regs to save, plus 20h bytes for scratch space
RhpHijackForGcStress_FrameSize equ SIZEOF__PAL_LIMITED_CONTEXT + 6*10h + 2*8h + 20h

; -----------------------------------------------------------------------------------------------------------
; RhpHijackForGcStress
;
; Called at the beginning of the epilog when a method is bound with /gcstress
;
; N.B. -- Leaf frames may not have aligned the stack or reserved any scratch space on the stack.  Also, in
;         order to have a resonable stacktrace in the debugger, we must use the .pushframe unwind directive.