Skip to content

Redundant write barriers around byref-like structs #111575

@EgorBo

Description

@EgorBo

Reported in #111127 (comment) by @NinoFloris

public class Program
{
    object _obj = new();

    Test M0() => new Test() { Obj = _obj, Obj1 = _obj, Obj2 = _obj };

    void M1(ref Test ret) => ret = new Test() { Obj = _obj, Obj1 = _obj, Obj2 = _obj };

    void M2(out Test ret) => ret = new Test() { Obj = _obj, Obj1 = _obj, Obj2 = _obj };

    public ref struct Test
    {
        public object Obj;
        public object Obj1;
        public object Obj2;
    }
}

Currently all three M0, M1, M2 emit redundant write barriers, although, they're not needed due to "ByRefLike" modifier on Test struct (meaning it can live only on stack):

; Assembly listing for method Program:M0():Program+Test:this (FullOpts)
G_M000_IG01:
       push     rsi
       push     rbx
       mov      rbx, rdx
G_M000_IG02:
       mov      rsi, gword ptr [rcx+0x08]
       mov      rdx, rsi
       mov      rcx, rbx
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       lea      rcx, bword ptr [rbx+0x08]
       mov      rdx, rsi
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       lea      rcx, bword ptr [rbx+0x10]
       mov      rdx, rsi
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       mov      rax, rbx
G_M000_IG03:
       pop      rbx
       pop      rsi
       ret      
; Total bytes of code 50


; Assembly listing for method Program:M1(byref):this (FullOpts)
G_M000_IG01:
       push     rsi
       push     rbx
       mov      rbx, rdx
G_M000_IG02:
       mov      rsi, gword ptr [rcx+0x08]
       mov      rdx, rsi
       mov      rcx, rbx
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       lea      rcx, bword ptr [rbx+0x08]
       mov      rdx, rsi
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       lea      rcx, bword ptr [rbx+0x10]
       mov      rdx, rsi
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       nop      
G_M000_IG03:
       pop      rbx
       pop      rsi
       ret      
; Total bytes of code 48


; Assembly listing for method Program:M2(byref):this (FullOpts)
G_M000_IG01:
       push     rsi
       push     rbx
       mov      rbx, rdx
G_M000_IG02:
       mov      rsi, gword ptr [rcx+0x08]
       mov      rdx, rsi
       mov      rcx, rbx
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       lea      rcx, bword ptr [rbx+0x08]
       mov      rdx, rsi
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       lea      rcx, bword ptr [rbx+0x10]
       mov      rdx, rsi
       call     CORINFO_HELP_CHECKED_ASSIGN_REF
       nop      
G_M000_IG03:
       pop      rbx
       pop      rsi
       ret      
; Total bytes of code 48

Expected:

no CORINFO_HELP_CHECKED_ASSIGN_REF calls in the codegen.

Metadata

Metadata

Assignees

Labels

area-CodeGen-coreclrCLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMIin-prThere is an active PR which will close this issue when it is merged

Type

No type

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions