【问题标题】:C++/ASM - "Operand size conflict", "Improper operand type"C++/ASM - “操作数大小冲突”、“操作数类型不正确”
【发布时间】:2016-04-24 14:04:26
【问题描述】:

我正在尝试在 ASM 中编写一个简单的 for 循环。我需要访问两个数组,它们是在 C++ 中的代码 sn-p 之外编写的(即 OrigChars 和 EncrChars)

    char temporary_char;                    

__asm {             
      xor ebx, ebx              
      jmp checkend              

      loopfor: inc ebx                          

      checkend: cmp ebx, len              
      jge endfor1               

      mov bx, word ptr[ebx + OrigChars]
      mov temporary_char, bx //error - "operand size conflict"

      push eax
      push ecx

      movzx  ecx, temporary_char    
      lea    eax, EKey          

      push eax                  
      push ecx

      call encrypt1             
      add esp, 8            

      mov temporary_char, al    

      pop ecx
      pop eax

      mov EncrChars[ebx], temporary_char  //error - "improper operand type"

      jmp loopfor           
}

上面已经注释了有错误的行。

简而言之,为什么这些对我不起作用:

  • mov temporary_char, bx // temp_char = OChars [i];
  • mov EncrChars[ebx],temporary_char //EncrChars[ebx] =temporary_char;

【问题讨论】:

  • 您确定mov bx, word ptr[ebx + OrigChars] 不起作用吗?它看起来像是问题 insns 的要点列表中唯一正确的一个。 (顺便说一句,请参阅 x86 tag wiki 以获取许多有用的链接。

标签: c++ assembly


【解决方案1】:
mov bx, word ptr[ebx + OrigChars]
mov temporary_char, bx //error - "operand size conflict"

由于 temporary_charchar 类型,您只需将 BX 替换为 BL。
最好还是使用 AL,因为您使用的是 EBX作为寻址索引!

mov al, byte ptr [OrigChars + ebx]
mov temporary_char, al

mov EncrChars[ebx], temporary_char  //error - "improper operand type"

在同一条指令中不能有 2 个内存引用。使用间歇性寄存器:

mov al, temporary_char
mov byte ptr [EncrChars + ebx], al

【讨论】:

  • 谢谢,解决了这两个问题,并充分解释了原因。
  • @ozank:如果您想在加载字节时将 reg 的其余部分归零,请使用 movzx ebx, byte ptr [mem] 或类似名称。还有一个符号扩展的movsx。符号或零扩展加载不会花费任何额外费用(除了几个字节的代码大小),并且可以避免后续指令导致部分寄存器减速。 (或者在那个 insn 上,在 Intel P6 或 SnB 系列以外的 CPU 上,其中部分 reg 写入对整个 reg 有错误的依赖性。)
【解决方案2】:

char 类型通常为 8 位大小。 bx 寄存器是 16 位的。这是你的不匹配。

【讨论】:

  • 好的,我该如何解决?对不起,我是 ASM 的新手,我需要截断寄存器吗?
  • 相反。在第一个错误中,您的限制是目标(char 类型),它小于源(16 位寄存器)。你应该为你的temporary_char 使用更大的类型。
  • 我把temporary_char的类型改成了字符串,但我还是在底部得到了“不正确的操作数类型”。
  • string 是一种完全不同的类型,与您正在使用的整数类型不兼容。您应该使用整数类型,例如int
  • 如果你只想要一个字符,而不是移动额外的东西,请参考寄存器bl(这是ebx寄存器的最低有效8位,就像bxebx 的最低有效 16 位。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-08-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-10-21
相关资源
最近更新 更多