Skip to content

".?" operator with foreach doesn't creates nullptr check assembly. also no compile-time exception #6410

@ArtBlnd

Description

@ArtBlnd

(first please understand about my english skills. Im really bad at english)

this is example.

class Program
{

        class Foo
        {
            public Bar bar = null;
        }

        class Bar
        {
            public List<int> list = new List<int>(2);
        }

        static void Main(string[] args)
        {
            Foo foo = new Foo();

            foreach (int j in foo.bar?.list)
            {
                System.Console.WriteLine(j);
            }
        }
}

this should throws compile-time error because there is no things to handle is foo.bar?. that is nullptr
also. even assembly JIT codegen doesn't even creates nullptr check assembly.

See dump here.

25:             Foo foo = new Foo();
00007FF87C7C4941 48 B9 38 55 80 7C F8 7F 00 00 mov         rcx,7FF87C805538h  
00007FF87C7C494B E8 F0 02 65 5F       call        00007FF8DBE14C40  
00007FF87C7C4950 48 89 45 68          mov         qword ptr [rbp+68h],rax  
00007FF87C7C4954 48 8B 4D 68          mov         rcx,qword ptr [rbp+68h]  
00007FF87C7C4958 E8 F3 C6 FF FF       call        00007FF87C7C1050  
00007FF87C7C495D 48 8B 55 68          mov         rdx,qword ptr [rbp+68h]  
00007FF87C7C4961 48 89 95 90 00 00 00 mov         qword ptr [rbp+90h],rdx  


    27:             foreach (int j in foo.bar?.list)
00007FF87C7C4969 48 8B 95 90 00 00 00 mov         rdx,qword ptr [rbp+90h]  << here is where that exception throws in run-time
00007FF87C7C4970 48 8B 52 08          mov         rdx,qword ptr [rdx+8]  
00007FF87C7C4974 48 89 55 60          mov         qword ptr [rbp+60h],rdx  
00007FF87C7C4978 48 8B 55 60          mov         rdx,qword ptr [rbp+60h]  
00007FF87C7C497C 48 89 55 58          mov         qword ptr [rbp+58h],rdx  
00007FF87C7C4980 48 8B 55 60          mov         rdx,qword ptr [rbp+60h]  
00007FF87C7C4984 48 85 D2             test        rdx,rdx  
00007FF87C7C4987 75 09                jne         00007FF87C7C4992  
00007FF87C7C4989 90                   nop  
00007FF87C7C498A 33 D2                xor         edx,edx  
00007FF87C7C498C 48 89 55 50          mov         qword ptr [rbp+50h],rdx  
00007FF87C7C4990 EB 0C                jmp         00007FF87C7C499E  
00007FF87C7C4992 48 8B 55 58          mov         rdx,qword ptr [rbp+58h]  
00007FF87C7C4996 48 8B 52 08          mov         rdx,qword ptr [rdx+8]  
00007FF87C7C499A 48 89 55 50          mov         qword ptr [rbp+50h],rdx  
00007FF87C7C499E 48 8D 55 38          lea         rdx,[rbp+38h]  
00007FF87C7C49A2 48 8B 4D 50          mov         rcx,qword ptr [rbp+50h]  
00007FF87C7C49A6 39 09                cmp         dword ptr [rcx],ecx  
00007FF87C7C49A8 E8 A3 C4 E8 5E       call        00007FF8DB650E50  
00007FF87C7C49AD C4 E1 7A 6F 45 38    vmovdqu     xmm0,xmmword ptr [rbp+38h]  
00007FF87C7C49B3 C4 E1 7A 7F 45 78    vmovdqu     xmmword ptr [rbp+78h],xmm0  
00007FF87C7C49B9 48 8B 4D 48          mov         rcx,qword ptr [rbp+48h]  
00007FF87C7C49BD 48 89 8D 88 00 00 00 mov         qword ptr [rbp+88h],rcx  
00007FF87C7C49C4 90                   nop  
00007FF87C7C49C5 EB 1D                jmp         00007FF87C7C49E4  
00007FF87C7C49C7 48 8D 4D 78          lea         rcx,[rbp+78h]  
00007FF87C7C49CB E8 D0 D1 E8 5E       call        00007FF8DB651BA0  
00007FF87C7C49D0 89 45 30             mov         dword ptr [rbp+30h],eax  
00007FF87C7C49D3 8B 4D 30             mov         ecx,dword ptr [rbp+30h]  
00007FF87C7C49D6 89 4D 74             mov         dword ptr [rbp+74h],ecx 

00007FF87C7C4969 48 8B 95 90 00 00 00 mov rdx,qword ptr [rbp+90h] << doesn't even check nullptr before. it should be like.

lea rdx, qword ptr[rbp+90h]
test rdx, rdx
jne ~ nullptr handler ~
mov rdx, [rdx]

Metadata

Metadata

Assignees

No one assigned

    Labels

    area-CodeGen-coreclrCLR JIT compiler in src/coreclr/src/jit and related components such as SuperPMI

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions