2013-10-14 63 views
1

例子:0xAABBCCDD会变成0xDDCCBBAA反向字节顺序登记

我的程序崩溃,由于访问冲突异常就在第一XOR操作。

好像有一个更好的天真的解决方案,使用移动或旋转,但不管怎么说,这里是代码:

;; ######################################################################### 

     .486 
     .model flat, stdcall 
     option casemap :none ; case sensitive 

;; ######################################################################### 

     include \masm32\include\masm32.inc 
     include \masm32\include\kernel32.inc 

     includelib \masm32\lib\kernel32.lib 
    includelib \masm32\lib\masm32.lib 


.code 
;; The following program will flip the sequence of the bytes in the eax 
;; example : 0xAABBCCDD will turn into 0xDDCCBBAA 
start: 
MOV eax, 0AABBCCDDh 
XOR BYTE PTR [eax], al ;; Swap first byte and last byte 
XOR al, BYTE PTR [eax] 
XOR BYTE PTR [eax], al 
XOR BYTE PTR [eax+1], ah ;; Swap 2nd byte of eax and 3rd byte 
XOR ah, BYTE PTR [eax+1] 
XOR BYTE PTR [eax+1], ah 
end_prog: 
    ;;Exit the program, eax is the exit code 
    push eax 
    call ExitProcess 
END start 

什么我错在这里做什么?有没有更好的解决方案?

回答

9

为什么不干脆:

mov eax, 0AABBCCDDh 
bswap eax 

我不知道你正在尝试在您的程序做,但可以说什么CPU实际上是尝试做(但不能,这就是为什么崩溃) :

这一个:

XOR BYTE PTR [eax], al 

试图在计算的值的XOR运算的寄存器AL(字节大小),并在地址0AABBCCDDh(EAX寄存器的内容的存储器中的字节的值)。只要在这个地址上没有任何OS分配的内存,程序就会与GPF一起崩溃。

不使用BSWAP正确的字节交换如下(感谢X.J):

xchg ah, al 
    ror eax, 16 
    xchg ah, al. 
+0

因为我从来不知道有这样的操作码:)无论如何,你能看到为什么程序崩溃?或者如果有另一种解决方案而不使用bswap操作码? – idish

+0

@idish - 答案是用某种解释编辑的。 – johnfound

+0

我还是不明白什么是错的。我试图在0xAA和0xDD之间进行XOR操作。 (第一个字节和最后一个字节) – idish

3

怎么回合...

mov eax, 0AABBCCDDh 
    xchg al, ah ; 0AABBDDCCh 
    rol eax, 16 ; 0DDCCAABBh 
    xchg al, ah ; 0DDCCBBAAh 

那会不会做什么是一个寄存器通缉?我看到X.J已经发布了(向左旋转,向右旋转 - 相同的结果)要快速击败你们! :)

+0

哇,这是一个很棒的解决方案,谢谢!我会+1你,因为我已经接受约翰的答案XD – idish

+0

这是一个非常酷的解决方案,但请记住它可能会更慢。使用部分寄存器通常非常昂贵,因为大多数x86 CPU不保存不同的寄存器,并且必须在每次部分写入时进行昂贵的合并。 – Leeor