我正在查看一些装配,我看到了
行CMP ECX, ECX
这对我没有意义,因为它总是不正确A == A? (反身财产)
不确定这是否有帮助,但在此上下文中使用它:
CPU Disasm
Address Hex dump Command Comments
00414A24 |. 39C9 CMP ECX,ECX
00414A26 |. F3:A6 REPE CMPS BYTE PTR DS:[ESI],BYTE PTR ES:[EDI]
00414A28 |. 0F92C0 SETB AL
00414A2B |. 0F97C2 SETA DL
00414A2E |. 28C2 SUB DL,AL
00414A30 |. 0FBEC2 MOVSX EAX,DL
答案 0 :(得分:2)
如果ECX寄存器为零,则根本不执行repe cmpsb
。
这意味着以下setb
和seta
指令会产生垃圾!
因此程序员选择确保标志具有已定义的状态。
在这种情况下,cmp ecx,ecx
导致CarryFlag = 0和ZeroFlag = 1。 setb
会使AL为零,而seta
会使DL为零。
@ user35443 repe cmpsb
不会事先减少ECX。重复确实检查ECX是否为零,否则将递减。
@Hans Passant repe cmpsb
不需要您初始化Z标志,也不需要除方向标志之外的任何其他标志。
答案 1 :(得分:1)
正如@ user3144770所说...... CMP ECX, ECX
清除CF
和ZF
(以及其他),因为如果计数从零开始,则REPE CMPS ...
什么都不做 - 包括不影响标志。
英特尔程序员参考对REP / REPE / etc说:
WHILE CountReg ≠ 0
DO
Service pending interrupts (if any);
Execute associated string instruction;
CountReg ← (CountReg – 1);
IF CountReg = 0
THEN exit WHILE loop; FI;
IF (Repeat prefix is REPZ or REPE) and (ZF = 0)
or (Repeat prefix is REPNZ or REPNE) and (ZF = 1)
THEN exit WHILE loop; FI;
OD;
为避免疑问:
在ECX
中选择CMP ECX, ECX
没有任何意义...... CMP EDX, EDX
也会做同样的事情,并且避免任何关于计算令人担忧的建议!< / p>
为ZF
填充REPE
标记需要 ...所以如果ECX != 0
不需要准备。
可以在REPE
之前将标志设置为您喜欢的任何内容...无论它们设置为什么,如果ECX == 0
将其保留,并由最后CMPS
替换。不这样做。