Visual studio 在VisualStudio中通过内联汇编程序从字符串中读取字符

Visual studio 在VisualStudio中通过内联汇编程序从字符串中读取字符,visual-studio,assembly,x86,Visual Studio,Assembly,X86,我对VisualStudio内联汇编程序有问题,它似乎没有加载正确的值。我声明一个C字符串,如下所示: const char* str = "1235"; 然后我在asm中访问字符串,如下所示: movzx ebx, byte ptr str[esi] 问题在于,它没有将49加载到ebx(表示“1”的ascii代码)中,而是加载0。我确信esi是正确的索引,因为它进行了大量的调试。我加载字符串时出错了吗?请尝试: movzx ebx, byte ptr str[esi] 尝试:

我对VisualStudio内联汇编程序有问题,它似乎没有加载正确的值。我声明一个C字符串,如下所示:

const char* str = "1235";  
然后我在asm中访问字符串,如下所示:

movzx ebx, byte ptr str[esi]
问题在于,它没有将49加载到ebx(表示“1”的ascii代码)中,而是加载0。我确信esi是正确的索引,因为它进行了大量的调试。我加载字符串时出错了吗?

请尝试:

movzx     ebx, byte ptr str[esi]
尝试:

指令

movzx ebx, byte ptr str[esi]
表示读取
str
开始后的
esi
字节。它是与

ebx = *(unsigned char*)(&str) + esi);
在您的例子中,
str
是指针变量,因此
str[0]
是指针的低位8位,
str[1]
是位8-15,
str[2]
是位16-23,
str[3]
是位24-31。任何大于3的值都是缓冲区溢出,因为您正在读取的内存不是
str
的一部分

您实际想要做的是将
str
变量加载到寄存器中,然后从该寄存器进行索引寻址

mov ebx, str
movzx ebx, byte ptr [ebx+esi]
图片:

         +----+
    1003 | 12 |
         +----+
    1002 | 34 |
         +----+
    1001 | 56 |
         +----+
str 1000 | 78 |
         +----+

             +----+
    1234567D | 00 |
             +----+
    1234567C | 45 |
             +----+
    1234567B | 44 |
             +----+
    1234567A | 43 |
             +----+
    12345679 | 42 |
             +----+
    12345678 | 41 |
             +----+
您正在尝试读取字节
str+esi
,它读取部分变量
str
。如果
esi
大于3,则表示您的读数超过了
str
的末尾

你真正想做的是阅读
str
指向的东西。这意味着您需要将
str
加载到寄存器中(我选择了
ebx
),然后将
esi
添加到结果中,然后访问那里的字节。

指令

movzx ebx, byte ptr str[esi]
表示读取
str
开始后的
esi
字节。它是与

ebx = *(unsigned char*)(&str) + esi);
在您的例子中,
str
是指针变量,因此
str[0]
是指针的低位8位,
str[1]
是位8-15,
str[2]
是位16-23,
str[3]
是位24-31。任何大于3的值都是缓冲区溢出,因为您正在读取的内存不是
str
的一部分

您实际想要做的是将
str
变量加载到寄存器中,然后从该寄存器进行索引寻址

mov ebx, str
movzx ebx, byte ptr [ebx+esi]
图片:

         +----+
    1003 | 12 |
         +----+
    1002 | 34 |
         +----+
    1001 | 56 |
         +----+
str 1000 | 78 |
         +----+

             +----+
    1234567D | 00 |
             +----+
    1234567C | 45 |
             +----+
    1234567B | 44 |
             +----+
    1234567A | 43 |
             +----+
    12345679 | 42 |
             +----+
    12345678 | 41 |
             +----+
您正在尝试读取字节
str+esi
,它读取部分变量
str
。如果
esi
大于3,则表示您的读数超过了
str
的末尾



你真正想做的是阅读
str
指向的东西。这意味着您需要将
str
加载到寄存器中(我选择了
ebx
),然后将
esi
添加到结果中,然后访问那里的字节。

当您执行
mov ebx,str[esi]
时,esi中的值是多少?@JerryCoffin esi被用作循环中的计数器,在这种情况下,它是0@PgrAm-如果您在asm代码中使用寄存器,是否会更改周围循环的代码?我打赌是的@BoPersson它不是C意义上的循环。它只是asm块末尾的条件跳转表达式。更改所述寄存器无效。您没有索引字符串指针。您正在为变量编制索引。x86没有双间接寻址模式。查看编译器生成的程序集以了解发生了什么。执行
mov ebx,str[esi]
,esi中的值是多少?@JerryCoffin esi被用作循环中的计数器,在本例中是0@PgrAm-如果您在asm代码中使用寄存器,是否会更改周围循环的代码?我打赌是的@BoPersson它不是C意义上的循环。它只是asm块末尾的条件跳转表达式。更改所述寄存器无效。您没有索引字符串指针。您正在为变量编制索引。x86没有双间接寻址模式。查看编译器生成的程序集以了解发生了什么。问题是
str
不是数组,因此您无法使用此寻址模式访问其内容。问题是
str
不是数组,因此您无法使用此寻址模式访问其内容。是的,我这样做了,它成功了!我做了这个“mov-edi,str”,然后是“movzx-ebx,byte-ptr[edi+esi]”我希望你能理解发生了什么,而不是盲目地复制答案。事实上,昨晚我自己解决了这个问题。既然你给了我正确的答案,我想我应该接受。是的,我做到了,而且成功了!我做了这个“mov-edi,str”,然后是“movzx-ebx,byte-ptr[edi+esi]”我希望你能理解发生了什么,而不是盲目地复制答案。事实上,昨晚我自己解决了这个问题。既然你给了我正确的答案,我想我应该接受。