Assembly 花一个假的mov eax,esi可以吗?

Assembly 花一个假的mov eax,esi可以吗?,assembly,Assembly,我正在用高级语言编写JIT编译器,有时有两种情况。在第一种情况下,接收对象位于eax,在另一种情况下,接收对象位于esi。因此,一些例程有两个版本,一个基于eax,另一个基于esi。除此之外,这两个版本在语义上是相同的。因此,我有两个选择: 有条件地生成一个或另一个例程,或 有条件地mov-eax、esi,并且仅生成基于eax的例程 如果没有任何副作用,选项2更适合高级代码,因为它简化了(本机)代码生成功能。但是,本机代码将执行附加的mov eax,esi,而不是使用esi作为基址寻址寄存器 问

我正在用高级语言编写JIT编译器,有时有两种情况。在第一种情况下,接收对象位于
eax
,在另一种情况下,接收对象位于
esi
。因此,一些例程有两个版本,一个基于
eax
,另一个基于
esi
。除此之外,这两个版本在语义上是相同的。因此,我有两个选择:

  • 有条件地生成一个或另一个例程,或
  • 有条件地
    mov-eax、esi
    ,并且仅生成基于
    eax
    的例程
  • 如果没有任何副作用,选项2更适合高级代码,因为它简化了(本机)代码生成功能。但是,本机代码将执行附加的
    mov eax,esi
    ,而不是使用
    esi
    作为基址寻址寄存器

    问题是:哪个选项更好

    我应该尝试节省几个CPU周期并避免额外的
    mov
    ,还是应该选择简化高级代码,因为性能上的差异可以忽略不计


    范例

    注意:
    imm8
    只是适当字节常量的占位符

    基于EAX的例程:

        test byte ptr [eax + imm8], imm8   ; EAX
        jz @1
        mov eax, [eax + imm8]              ; EAX
        jmp @2
    @1:
        mov al, [eax + imm8]               ; EAX
        and eax, 255
    @2:
        sal eax
        inc eax
    
        test byte ptr [esi + imm8], imm8   ; ESI
        jz @1
        mov eax, [esi + imm8]              ; ESI
        jmp @2
    @1:
        mov al, [esi + imm8]               ; ESI
        and eax, 255
    @2:
        sal eax
        inc eax
    
        mov eax, esi                        ; not present in option 1 
        test byte ptr [eax + imm8], imm8    ; EAX-based from now on
        jz @1
        mov eax, [eax + imm8]
        jmp @2
    @1:
        mov al, [eax + imm8]
        and eax, 255
    @2:
        sal eax
        inc eax
    
    基于ESI的例程(选项1):

        test byte ptr [eax + imm8], imm8   ; EAX
        jz @1
        mov eax, [eax + imm8]              ; EAX
        jmp @2
    @1:
        mov al, [eax + imm8]               ; EAX
        and eax, 255
    @2:
        sal eax
        inc eax
    
        test byte ptr [esi + imm8], imm8   ; ESI
        jz @1
        mov eax, [esi + imm8]              ; ESI
        jmp @2
    @1:
        mov al, [esi + imm8]               ; ESI
        and eax, 255
    @2:
        sal eax
        inc eax
    
        mov eax, esi                        ; not present in option 1 
        test byte ptr [eax + imm8], imm8    ; EAX-based from now on
        jz @1
        mov eax, [eax + imm8]
        jmp @2
    @1:
        mov al, [eax + imm8]
        and eax, 255
    @2:
        sal eax
        inc eax
    
    基于ESI的例程(选项2):

        test byte ptr [eax + imm8], imm8   ; EAX
        jz @1
        mov eax, [eax + imm8]              ; EAX
        jmp @2
    @1:
        mov al, [eax + imm8]               ; EAX
        and eax, 255
    @2:
        sal eax
        inc eax
    
        test byte ptr [esi + imm8], imm8   ; ESI
        jz @1
        mov eax, [esi + imm8]              ; ESI
        jmp @2
    @1:
        mov al, [esi + imm8]               ; ESI
        and eax, 255
    @2:
        sal eax
        inc eax
    
        mov eax, esi                        ; not present in option 1 
        test byte ptr [eax + imm8], imm8    ; EAX-based from now on
        jz @1
        mov eax, [eax + imm8]
        jmp @2
    @1:
        mov al, [eax + imm8]
        and eax, 255
    @2:
        sal eax
        inc eax
    

    您应该选择简化代码的选项。一旦你的产品完成,如果你发现额外的移动是一个重大的性能问题,你可以重新考虑这个决定。不同之处在于,您拥有可以帮助您做出决策的探查器数据

    +1对你来说,只是为了对付JTI。
    您将从中学到很多。

    很难找到一个剖析器准确反映多个函数上一条指令前导的成本。我认为这个答案没有帮助。