Runtime: ์งˆ๋ฌธ: ์ธํ„ฐํŽ˜์ด์Šค ํ˜ธ์ถœ ๋ฐ ์ƒ์„ฑ๋œ ASM

์— ๋งŒ๋“  2019๋…„ 11์›” 28์ผ  ยท  3์ฝ”๋ฉ˜ํŠธ  ยท  ์ถœ์ฒ˜: dotnet/runtime

์•ˆ๋…• ์–˜๋“ค์•„!

์ด์™€ ๊ฐ™์€ ์ธํ„ฐํŽ˜์ด์Šค ๋ฉ”์†Œ๋“œ๋ฅผ ํ˜ธ์ถœํ•˜๋Š” ๋งค์šฐ ๊ฐ„๋‹จํ•œ ์•ฑ์ด ์žˆ์Šต๋‹ˆ๋‹ค.

namespace InterfaceCalls
{
    public interface IFoo
    {
        int  Bar();
    }

    class Program
    {
        public static int M1(IFoo foo)
        {
            return foo.Bar();
        }

        static void Main(string[] args)
        {
            M1(null);
        }
    }
}

๊ทธ๋Ÿฌ๋ฉด 2.2์— ๋Œ€ํ•ด ๋‹ค์Œ ASM์ด ์ƒ์„ฑ๋ฉ๋‹ˆ๋‹ค(3.0์—๋Š” add rsp,30h ๋Œ€์‹  lea rsp,[rbp]๊ฐ€ ์žˆ์Œ).

            return foo.Bar();
00007FFE7B521846  mov         rcx,rsi  
00007FFE7B521849  mov         r11,7FFE7B410028h  
00007FFE7B521853  cmp         dword ptr [rcx],ecx  
00007FFE7B521855  call        qword ptr [7FFE7B410028h]  
00007FFE7B52185B  nop  
00007FFE7B52185C  add         rsp,30h  
00007FFE7B521860  pop         rsi  
00007FFE7B521861  ret  

์ž ์žฌ์ ์œผ๋กœ ๋งค์šฐ ๋ฉ์ฒญํ•˜๊ณ  ์ดˆ๋ณด์ ์ธ ์งˆ๋ฌธ์— ๋Œ€ํ•ด ์ฃ„์†กํ•ฉ๋‹ˆ๋‹ค :) ํ•˜์ง€๋งŒ ๋ˆ„๊ตฐ๊ฐ€ ๋‚˜์—๊ฒŒ ํžŒํŠธ๋ฅผ ์ค„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?

1 ์—ฌ๊ธฐ์—์„œ cmp ๋ช…๋ น์ด ํ•„์š”ํ•œ ์ด์œ (cmp ์ดํ›„์—๋Š” ์กฐ๊ฑด๋ถ€ ์ ํ”„๊ฐ€ ์—†์Œ)
2 7FFE7B410028h๋Š” ๋ฌด์—‡์ด๋ฉฐ ์—ฌ๊ธฐ์—์„œ r11์„ ๋กœ๋“œํ•˜๋Š” ์ด์œ 
3 ์ธํ„ฐํŽ˜์ด์Šค ํ˜ธ์ถœ๋‹น cmp๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ๋„ˆ๋ฌด ๋น„์‹ธ์ง€ ์•Š์Šต๋‹ˆ๊นŒ(์ด ๊ฒฝ์šฐ cml๋กœ ์ธํ•ด ๋ถ„๊ธฐ ์˜ˆ์ธก์ด ๋ˆ„๋ฝ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?)

์ •๋ง ๊ณ ๋งˆ์›Œ!

area-CodeGen-coreclr

๊ฐ€์žฅ ์œ ์šฉํ•œ ๋Œ“๊ธ€

์—ฌ๊ธฐ์—์„œ cmp ๋ช…๋ น์ด ํ•„์š”ํ•œ ์ด์œ (cmp ์ดํ›„์—๋Š” ์กฐ๊ฑด๋ถ€ ์ ํ”„๊ฐ€ ์—†์Œ)

this ์ด null this ๋•Œ ํ˜ธ์ถœ ์ง€์ ์—์„œ NullReferenceException ๋ฅผ ํŠธ๋ฆฌ๊ฑฐํ•˜๋ ค๋ฉด.

7FFE7B410028h๋Š” ๋ฌด์—‡์ด๋ฉฐ ์—ฌ๊ธฐ์—์„œ r11์„ ๋กœ๋“œํ•˜๋Š” ์ด์œ 

์ธํ„ฐํŽ˜์ด์Šค ๊ตฌํ˜„ ๋ฉ”์„œ๋“œ๋ฅผ ํ™•์ธํ•˜๊ณ  ํ˜ธ์ถœํ•˜๋Š” ์Šคํ…์„ ๊ฐ€๋ฆฌํ‚ค๋Š” "๊ฐ„์ ‘ ์…€"์˜ ์ฃผ์†Œ์ž…๋‹ˆ๋‹ค. ๋ถˆํ–‰ํžˆ๋„ ์ธํ„ฐํŽ˜์ด์Šค ๋ฉ”์„œ๋“œ๋ฅผ ํ•ด๊ฒฐํ•˜๋Š” ๊ฒƒ์€ "์ธ๋ผ์ธ"์œผ๋กœ ์ˆ˜ํ–‰ํ•  ์ˆ˜ ์—†๋Š” ๋น„๊ต์  ๋ณต์žกํ•œ ์ž‘์—…์ž…๋‹ˆ๋‹ค.

์ฒ˜์Œ์—๋Š” https://github.com/dotnet/runtime/blob/4f9ae42d861fcb4be2fcd5d3d55d5f227d30e723/src/coreclr/src/vm/amd64/VirtualCallStubAMD64.asm#L28์„ ๊ฐ€๋ฆฌํ‚ต๋‹ˆ๋‹ค.

์ผ๋ถ€ ๋ฌธ์„œ๋Š” ์—ฌ๊ธฐ์—์„œ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค(์ตœ์‹  ์ •๋ณด์ธ์ง€๋Š” ํ™•์‹คํ•˜์ง€ ์•Š์Œ).
https://github.com/dotnet/runtime/blob/master/docs/design/coreclr/botr/virtual-stub-dispatch.md

๋น ๋ฅธ ๊ฐœ์š”๋ฅผ ๋ณด๋ ค๋ฉด https://github.com/dotnet/runtime/blob/master/docs/design/coreclr/botr/virtual-stub-dispatch.md#stubs ๋กœ ๋ฐ”๋กœ ๊ฑด๋„ˆ๋›ธ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ธํ„ฐํŽ˜์ด์Šค ํ˜ธ์ถœ๋‹น cmp๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ๋„ˆ๋ฌด ๋น„์‹ธ์ง€ ์•Š์Šต๋‹ˆ๊นŒ(์ด ๊ฒฝ์šฐ cml๋กœ ์ธํ•ด ๋ถ„๊ธฐ ์˜ˆ์ธก์ด ๋ˆ„๋ฝ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?)

์กฐ๊ฑด ๋ถ„๊ธฐ ๋ช…๋ น์ด ์•„๋‹Œ ๋น„๊ต ๋ช…๋ น์ด๋ฏ€๋กœ ๋ถ„๊ธฐ ์˜ˆ์ธก๊ณผ ๊ด€๋ จ์ด ์—†์Šต๋‹ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์‹ค์ œ ์ธํ„ฐํŽ˜์ด์Šค ํ˜ธ์ถœ ๋น„์šฉ์— ๋น„ํ•ด ๋งค์šฐ ์ €๋ ดํ•ฉ๋‹ˆ๋‹ค.

๋ชจ๋“  3 ๋Œ“๊ธ€

cmp ๋Š” ์ดˆ๊ธฐ null ๊ฒ€์‚ฌ์ž…๋‹ˆ๋‹ค.
์—ฌ๊ธฐ์—์„œ ์ธํ„ฐํŽ˜์ด์Šค ๋””์ŠคํŒจ์น˜์— ๋Œ€ํ•ด ์ฝ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. https://github.com/dotnet/coreclr/blob/master/Documentation/botr/virtual-stub-dispatch.md

์—ฌ๊ธฐ์—์„œ cmp ๋ช…๋ น์ด ํ•„์š”ํ•œ ์ด์œ (cmp ์ดํ›„์—๋Š” ์กฐ๊ฑด๋ถ€ ์ ํ”„๊ฐ€ ์—†์Œ)

this ์ด null this ๋•Œ ํ˜ธ์ถœ ์ง€์ ์—์„œ NullReferenceException ๋ฅผ ํŠธ๋ฆฌ๊ฑฐํ•˜๋ ค๋ฉด.

7FFE7B410028h๋Š” ๋ฌด์—‡์ด๋ฉฐ ์—ฌ๊ธฐ์—์„œ r11์„ ๋กœ๋“œํ•˜๋Š” ์ด์œ 

์ธํ„ฐํŽ˜์ด์Šค ๊ตฌํ˜„ ๋ฉ”์„œ๋“œ๋ฅผ ํ™•์ธํ•˜๊ณ  ํ˜ธ์ถœํ•˜๋Š” ์Šคํ…์„ ๊ฐ€๋ฆฌํ‚ค๋Š” "๊ฐ„์ ‘ ์…€"์˜ ์ฃผ์†Œ์ž…๋‹ˆ๋‹ค. ๋ถˆํ–‰ํžˆ๋„ ์ธํ„ฐํŽ˜์ด์Šค ๋ฉ”์„œ๋“œ๋ฅผ ํ•ด๊ฒฐํ•˜๋Š” ๊ฒƒ์€ "์ธ๋ผ์ธ"์œผ๋กœ ์ˆ˜ํ–‰ํ•  ์ˆ˜ ์—†๋Š” ๋น„๊ต์  ๋ณต์žกํ•œ ์ž‘์—…์ž…๋‹ˆ๋‹ค.

์ฒ˜์Œ์—๋Š” https://github.com/dotnet/runtime/blob/4f9ae42d861fcb4be2fcd5d3d55d5f227d30e723/src/coreclr/src/vm/amd64/VirtualCallStubAMD64.asm#L28์„ ๊ฐ€๋ฆฌํ‚ต๋‹ˆ๋‹ค.

์ผ๋ถ€ ๋ฌธ์„œ๋Š” ์—ฌ๊ธฐ์—์„œ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค(์ตœ์‹  ์ •๋ณด์ธ์ง€๋Š” ํ™•์‹คํ•˜์ง€ ์•Š์Œ).
https://github.com/dotnet/runtime/blob/master/docs/design/coreclr/botr/virtual-stub-dispatch.md

๋น ๋ฅธ ๊ฐœ์š”๋ฅผ ๋ณด๋ ค๋ฉด https://github.com/dotnet/runtime/blob/master/docs/design/coreclr/botr/virtual-stub-dispatch.md#stubs ๋กœ ๋ฐ”๋กœ ๊ฑด๋„ˆ๋›ธ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

์ธํ„ฐํŽ˜์ด์Šค ํ˜ธ์ถœ๋‹น cmp๋ฅผ ์‚ฌ์šฉํ•˜๋Š” ๊ฒƒ์ด ๋„ˆ๋ฌด ๋น„์‹ธ์ง€ ์•Š์Šต๋‹ˆ๊นŒ(์ด ๊ฒฝ์šฐ cml๋กœ ์ธํ•ด ๋ถ„๊ธฐ ์˜ˆ์ธก์ด ๋ˆ„๋ฝ๋  ์ˆ˜ ์žˆ์Šต๋‹ˆ๊นŒ?)

์กฐ๊ฑด ๋ถ„๊ธฐ ๋ช…๋ น์ด ์•„๋‹Œ ๋น„๊ต ๋ช…๋ น์ด๋ฏ€๋กœ ๋ถ„๊ธฐ ์˜ˆ์ธก๊ณผ ๊ด€๋ จ์ด ์—†์Šต๋‹ˆ๋‹ค. ๊ทธ๋ฆฌ๊ณ  ์‹ค์ œ ์ธํ„ฐํŽ˜์ด์Šค ํ˜ธ์ถœ ๋น„์šฉ์— ๋น„ํ•ด ๋งค์šฐ ์ €๋ ดํ•ฉ๋‹ˆ๋‹ค.

@mikedn @omariom ๊ฐ์‚ฌํ•ฉ๋‹ˆ๋‹ค

์ด ํŽ˜์ด์ง€๊ฐ€ ๋„์›€์ด ๋˜์—ˆ๋‚˜์š”?
0 / 5 - 0 ๋“ฑ๊ธ‰