C 内联程序集生成未处理的异常

C inline Assembly generating unhandled exception

所以我用 C 语言编写了这个函数

int transform ( char * p )
{
    if(*p!='-'){
        return 0;
    }

    p++;
    if(*p == 'a')
    {
        return 1;
    }
    else if(*p == 'b')
    {
        return 2;
    }
    else
    {
        return 0;
    }
}

然后我试着将它翻译成内联汇编 ia32,就像这样

    int trasform ( char * p )
    {
        int result; 
        _asm
        {
            mov eax, p
            mov ebx, 0
            mov bl, [eax]
            cmp bl, '-'   ;
                jne invalid
                mov bl, [4*eax]
            cmp bl, 'a'
                jne isB
                mov result, 1
                mov eax, result
            jmp out
    isB:
            cmp bl, 'b'
                jne invalid
                mov result, 2
                mov eax, result
            jmp out 
    invalid:
            mov result, 0  
            mov eax, result
    out: ; end

    }
    return result;
}

当我用 C 编写函数时,它在 Visual Studio 中工作得很好,但是当我将它更改为内联汇编并执行代码时,我得到一个错误

Unhandled exception at 0x774e15ee in proyect.exe : 0xC0000005: Access violation reading location 0x01745388.

这个问题一定是代码的问题还是visual studio的问题?

我调试了我的代码,发现错误在这一行

mov bl, [4*eax] 
mov bl, [4*eax]
 cmp bl, 'a'

想法是将EAX中的指针前移。不需要乘以它!

inc eax              ;ptr++
mov bl, [eax]
cmp bl, 'a'

如调试器所示,问题出在这条指令中:

mov bl, [4*eax]

看C代码,其意图是将字符串的第二个字节加载到bl中。指向第一个字节的指针是eax,所以指向第二个字节的指针是eax+1。也就是说,正确的命令是

mov bl, [eax+1]

或者,您可以使用两条指令来完成此操作:

inc eax
mov bl, [eax]

这样比较符合C代码:

p++;
if (*p == ...)

但同样如此。

您想读取“-”之后的字节,该字节位于 eax+1,而不是 4*eax