Frage

Hi people I am new keen learner to assembly language x86, i am trying to produce a CDECL Call Convention from a set of encryption instructions. I believe I am going somewhere wrong down the line implementing the convention. Below is the original set of instructions and function given as the problem. Also included is my attempt (Please excuse me if its totally wrong very new to assembly language). I am using visual studio 2013 in C++ development settings.

The WARNING given on several lines is -- Warning C4409: illegal instruction size (used a '@' symbol before the instruction to mark the line where is applies)

Also I am getting 2 more warnings -- Warning C4731:'encrypt_chars' : 'frame pointer register 'ebp' modified by inline assembly code (used a '$' symbol before the line where it applies)

void encrypt_chars (int length, char EKey)
{   char temp_char;                         // char temporary store

for (int i = 0; i < length; i++)            // encrypt characters one at a time
{   temp_char = OChars [i];         

__asm {                          

        //------------------------ORIGINAL CODE-------------------------------------------//
        //--------------------------------------------------------------------------------//
        //push   eax                    // save register values on stack to be safe
        //push   ecx                    //
        //movzx  ecx,temp_char          // 
        //lea    eax,EKey               // 
        //call   encrypt4               // encrypt the character
        //mov    temp_char,al           // 
        //pop    ecx                    // restore original register values from stack
        //pop    eax                    //
        //--------------------------------------------------------------------------------//


        //---------------------------------CDECL VERSION----------------------------------//
        push eax                        //save register values on stack
        push ecx
        @push EKey                      //save orginal values of parameters
        @push temp_char

        call encrypt4                   //call function
        add esp, 8                      //clean parameters of stack

        mov temp_char, al               //move the temporay character into a 8bit register
        @pop temp_char                  //recover register values
        @pop EKey
        pop ecx
        pop eax
        //--------------------------------------------------------------------------------//

    }
    EChars [i] = temp_char;         // Store encrypted char in the encrypted chars array
}
return;

and here is the sub-routine:

 encrypt4:     
    //-------------------------ORGINAL CODE----------------------------------------------//
    //push edi
    //push ecx
    //not byte ptr[eax]
    //add byte ptr[eax], 0x04
    //movzx edi, byte ptr[eax]
    //pop eax
    //xor eax, edi
    //pop edi
    //rol al, 1
    //rol al, 1
    //add al, 0x04
    //ret
    //-----------------------------------------------------------------------------------//



    //-------------------------CDECL VERSION---------------------------------------------//
    push ebp                        //save old base pointer value
    $mov ebp, esp                   //set new base pointer value
    push edi                        //destination index register used for string, memory array copying, setting and for far pointer addressing with ES (push EDI onto stack)
    push ecx                        //counter register, used as a loop counter (push 'Char' onto stack)
    mov eax, [ebp +8]               //move value of parameter 1 into eax
    mov ecx, [ebp +12]              //move valye of parameter 2 into ecx
    not byte ptr[eax]               //ones complement negation byte pointer used with the 'EKey' single byte location address
    add byte ptr[eax], 0x04         //byte pointer used to add 4 in hexidecimal to the 'EKey' single byte location address
    movzx edi, byte ptr[eax]        //moves the value of 'EKey' address to EDI using zeros instead of a sign bit
    pop eax                         //pop value of 'character to be encrypted' from stack
    xor eax, edi                    //XOR 'character to be encrypted' with EDI value, this give the 'encrypted value of the source character'(stage 1)
    pop ecx                         //recover register value
    pop edi                         //pop orginal address of EDI from stack
    rol al, 1                       //rotates the 'encrypted value of the source character' register(stage 2) left by 1 bit, leaves a carry for my test string 'manutd$'
    rol al, 1                       //rotates the 'encrypted value of the source character' register(stage 3) left by 1 bit, leaves a carry for my test string 'manutd$'
    add al, 0x04                    //adds 4 in hexidecimal to 'encrypted value of the source character'(final stage)
    mov esp, ebp                    //deallocate values
    $pop ebp                    //restore callers base pointer value
    ret                             //return from procedure
    //-----------------------------------------------------------------------------------//

Any would be appreciated. Thanks

War es hilfreich?

Lösung

push and pop cannot work on bytes. The minimum size is 16 bits.

Andere Tipps

To fix the second warning you should use __declspec(naked) on functions which are pure assembly.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top