0

I dont know if I am doing this properly, but I want to make a simple PROC in x86 MASM for my MD5 implementation. And for instruction ROL it seems that I cannot use this type of coding.

HCALC proc NEAR Avar: DWORD, Xvar: DWORD, Yvar: DWORD, Zvar: DWORD, Mvar: DWORD, S: DWORD, Hvar: DWORD
pushad
mov eax, Avar 
mov ebx, Xvar 
mov ecx, Yvar 
mov edx, Zvar 

xor ebx, ecx 
xor ebx, edx 

add eax, ebx ; a + H(x,y,z)
add eax, Mvar ; a + H(x,y,z) + M[k]
add eax, Hvar ; a + H(x,y,z) + M[k] + h
rol eax, S ; (a + F(x,y,z) + M[k] + h) <<< s)

add eax, ebx ; x + ((a + F(x,y,z) + M[k] + h) <<< s), wynik całości w EAX
mov Avar, eax 
popad 
ret 
HCALC endp

It gives an error error A2070: invalid instruction operands

PwQt
  • 11
  • 2
  • 1
    You don't need `pushad` / `popad`. `ebx` is the only call-preserved register you use, so it's *much* faster to only push/pop ebx. Also, why don't you just return the result in `eax`, instead of storing it through a pointer that's passed as a function arg (on the stack, yuck). The 32bit `__vectorcall` calling convention passes the first two args in registers, which saves instructions. – Peter Cordes Feb 23 '16 at 03:33
  • I think function-call overhead is going to be killer for this. You're only doing a tiny amount of work in each function call. If this is mostly just because you can't get a compiler to emit a rotate instruction without other fluff, see http://stackoverflow.com/questions/776508/best-practices-for-circular-shift-rotate-operations-in-c. Also, see the x86 tag wiki for links to the insn set reference. Any time an assembler tells you it doesn't like the args for an instruction, check the manual and see what they're allowed to be! – Peter Cordes Feb 23 '16 at 03:36

2 Answers2

4

The ROL instruction requires either an immediate 8 bit operand or the CL register as the shift count. Using

mov ecx, S
rol eax, cl

should work just fine.

owacoder
  • 4,815
  • 20
  • 47
2

You've got 2 problems in this program:

  • The rol instruction can't use a memory counter. You should move it to the CL register:

    mov ecx, S
    rol eax, cl ; (a + F(x,y,z) + M[k] + h) <<< s)
    
  • By the time you do the final addition, EBX no longer holds the X variable but rather H(X,Y,Z)

    mov ebx, X
    add eax, ebx ; x + ((a + F(x,y,z) + M[k] + h) <<< s)
    
Sep Roland
  • 33,889
  • 7
  • 43
  • 76