Sign in to follow this  
Followers 0
Beege

Assembly code

6 posts in this topic

#1 ·  Posted (edited)

Here's a practice script that Ive been playing with while trying to learn assembly. what it does is start a timer, then does 5 loops that each sleep 500ms and then gets the end time.

I can't figure out how to get the times out of the dllstruct. help would be great. thanks for looking.

#include <Memory.au3>
#Include <Array.au3>

Global $pQueryPerformanceFrequency = _Get_Function_Address('kernel32.dll', 'QueryPerformanceFrequency')
Global $pQueryPerformanceCounter = _Get_Function_Address('kernel32.dll', 'QueryPerformanceCounter')
Global $pSleep = _Get_Function_Address('kernel32.dll', 'Sleep')

Global $d_ST = DllStructCreate("int64")
Global $pStartTime = DllStructGetPtr($d_ST)

Global $d_ET = DllStructCreate("int64")
Global $pEndTime = DllStructGetPtr($d_ET)

Global $d_FT = DllStructCreate("int64")
Global $pFreq = DllStructGetPtr($d_FT)

Global $iMilliseconds = 500, $loops = 5

#Region Assembly
Global $aOpcode[23]
$aOpcode[0] = "0x"
$aOpcode[1] = '';"33DB"

;(2-7) DllCall("kernel32.dll", "int", "QueryPerformanceFrequency", "ptr", $pFreq)
$aOpcode[2] = "B8" & SwapEndian($pFreq);                     move eax, $pFreq
$aOpcode[3] = "50" ;                                        push eax
$aOpcode[4] = "B8" & SwapEndian($pQueryPerformanceFrequency) ;mov eax, $pQueryPerformanceFrequency
$aOpcode[5] = "FFD0" ;                                      call eax

;(6-9) $starttime = _TimerInt() ;  DllCall("kernel32.dll", "int", "$pQueryPerformanceCounter", "ptr", $pStartTime)
$aOpcode[6] = "B8" & SwapEndian($pStartTime);               move eax, $pStartTime
$aOpcode[7] = "50" ;                                        push eax
$aOpcode[8] = "B8" & SwapEndian($pQueryPerformanceCounter) ;mov eax, $pQueryPerformanceCounter
$aOpcode[9] = "FFD0" ;                                      call eax

;(10) $b = 0
$aOpcode[10] = "33DB" ;                                     xor ebx, ebx

;(11-14) Sleep($milliseconds)
$aOpcode[11] = "B8" & SwapEndian($iMilliseconds);           move eax, $milliseconds
$aOpcode[12] = "50" ;                                       push eax
$aOpcode[13] = "B8" & SwapEndian($pSleep) ;                 mov eax, $Sleep
$aOpcode[14] = "FFD0" ;                                     call eax

;(15) $b += 1
$aOpcode[15] = "43" ;                                       inc ebx

;(16-17) If $b <> $loops then jump back to index 11.
$aOpcode[16] = "81FB" & SwapEndian($loops) ;                cmp ebx, loops;
$aOpcode[17] = _jne($aOpcode, 17, 11);  '75' & Hex(-22, 2)  jne from index 17 to 11   (Jump if ebx is not = loops)

;;(18-21) DllCall("kernel32.dll", "int", "QueryPerformanceCounter", "ptr", $pEndTime)
$aOpcode[18] = "B8" & SwapEndian($pEndTime);                move eax, $pEndTime
$aOpcode[19] = "50" ;                                       push eax
$aOpcode[20] = "B8" & SwapEndian($pQueryPerformanceCounter);mov eax, $pQueryPerformanceCounter
$aOpcode[21] = "FFD0" ;                                     call eax

;return
$aOpcode[22] = "C3";                                        ret
#EndRegion


$sOpcode = _ArrayToString($aOpcode, '')
$execute = _Execute_Opcode($sOpcode)

$Freq = DllStructGetData($d_FT, 1)
$StartTime = DllStructGetData($d_ST, 1)
$EndTime = DllStructGetData($d_ET, 1)

$Total_Time = $EndTime - $StartTime
$Total_Time /= $Freq
$Total_Time *= 1000

MsgBox(0, 'Total Time', $Total_Time)

Func _Execute_Opcode($sOpcode)
    Local $CodeBuffer = DllStructCreate("byte[" & BinaryLen($sOpcode) & "]")
    DllStructSetData($CodeBuffer, 1, $sOpcode)
    $Ret = DllCall("user32.dll", "int", "CallWindowProc", "ptr", DllStructGetPtr($CodeBuffer), "int", 0, "int", 0, "int", 0, "int", 0)
    Return $Ret
EndFunc

Func _Get_Function_Address($sDLL, $sFunction)
    Local $Handle, $Address
    $Handle = _WinAPI_GetModuleHandle($sDLL)
    $Address = DllCall($sDLL, "ptr", "GetProcAddress", "ptr", $Handle, "str", $sFunction)
    Return $Address[0]
EndFunc   ;==>_Get_Function_Address

Func _jne($array, $iStart, $iEnd)
    Local $bytes
    $bytes = BinaryLen('0x' & _ArrayToString($array, '', $iEnd, $iStart)) + 2
    Return '75' & Hex(-$bytes, 2)

EndFunc   ;==>_jne

Func SwapEndian($iValue)
    Return Hex(Binary($iValue))
EndFunc   ;==>SwapEndian

edit: Somehow I posted the code twice

Edited by Beege

Share this post


Link to post
Share on other sites



I must be missing something very obvious :D

What is the problem except possible DEP issue?


♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

Im trying to figure out what windows dll call I would use instead dllstructgetdata() for this part of the code:

$Freq = DllStructGetData($d_FT, 1)
$StartTime = DllStructGetData($d_ST, 1)
$EndTime = DllStructGetData($d_ET, 1)

kinda like how you used RtlMoveMemory function instead of dllstructsetdata() in your assembly examples.

Share this post


Link to post
Share on other sites

Aha. So you wanna return $Total_Time directly out of _Execute_Opcode function?


♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

#5 ·  Posted (edited)

Exactly. By the way, Thank you especially for all the sweet assembly examples. I would never be where I am as far as assembly knowledge with out yours and monoceres examples.

Edited by Beege

Share this post


Link to post
Share on other sites

Exactly. By the way, Thank you especially for all the sweet assembly examples. I would never be where I am as far as assembly knowledge with out yours and monres examples.

monoceres

I did some modifications to your code. Every thing that I changed is between ";XXXXXX" lines. I didn't touch anything else.

There are few issues and all are caused by the fact that it's working with integers (dword).

If you want to process bigger numbers you will have to do additional modifications.

If you want floats you need to switch to them also (check Space.au3 maybe)

#include <Memory.au3>
#include <Array.au3>

;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
Global $pRemoteCode = _MemVirtualAlloc(0, 512, $MEM_COMMIT, $PAGE_EXECUTE_READWRITE)
;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX


Global $pQueryPerformanceFrequency = _Get_Function_Address('kernel32.dll', 'QueryPerformanceFrequency')
Global $pQueryPerformanceCounter = _Get_Function_Address('kernel32.dll', 'QueryPerformanceCounter')
Global $pSleep = _Get_Function_Address('kernel32.dll', 'Sleep')

Global $d_ST = DllStructCreate("int64")
Global $pStartTime = DllStructGetPtr($d_ST)

Global $d_ET = DllStructCreate("int64")
Global $pEndTime = DllStructGetPtr($d_ET)

Global $d_FT = DllStructCreate("int64")
Global $pFreq = DllStructGetPtr($d_FT)

;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
Global $iMilliseconds = 100, $loops = 5
;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

#region Assembly

;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
Global $aOpcode[24]
;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

$aOpcode[0] = "0x"
$aOpcode[1] = '';"33DB"

;(2-7) DllCall("kernel32.dll", "int", "QueryPerformanceFrequency", "ptr", $pFreq)
$aOpcode[2] = "B8" & SwapEndian($pFreq);                     move eax, $pFreq
$aOpcode[3] = "50" ;                                        push eax
$aOpcode[4] = "B8" & SwapEndian($pQueryPerformanceFrequency) ;mov eax, $pQueryPerformanceFrequency
$aOpcode[5] = "FFD0" ;                                      call eax

;(6-9) $starttime = _TimerInt() ;  DllCall("kernel32.dll", "int", "$pQueryPerformanceCounter", "ptr", $pStartTime)
$aOpcode[6] = "B8" & SwapEndian($pStartTime);               move eax, $pStartTime
$aOpcode[7] = "50" ;                                        push eax
$aOpcode[8] = "B8" & SwapEndian($pQueryPerformanceCounter) ;mov eax, $pQueryPerformanceCounter
$aOpcode[9] = "FFD0" ;                                      call eax

;(10) $b = 0
$aOpcode[10] = "33DB" ;                                     xor ebx, ebx

;(11-14) Sleep($milliseconds)
$aOpcode[11] = "B8" & SwapEndian($iMilliseconds);           move eax, $milliseconds
$aOpcode[12] = "50" ;                                       push eax
$aOpcode[13] = "B8" & SwapEndian($pSleep) ;                 mov eax, $Sleep
$aOpcode[14] = "FFD0" ;                                     call eax

;(15) $b += 1
$aOpcode[15] = "43" ;                                       inc ebx

;(16-17) If $b <> $loops then jump back to index 11.
$aOpcode[16] = "81FB" & SwapEndian($loops) ;                cmp ebx, loops;
$aOpcode[17] = _jne($aOpcode, 17, 11);  '75' & Hex(-22, 2)  jne from index 17 to 11   (Jump if ebx is not = loops)

;;(18-21) DllCall("kernel32.dll", "int", "QueryPerformanceCounter", "ptr", $pEndTime)
$aOpcode[18] = "B8" & SwapEndian($pEndTime);                move eax, $pEndTime
$aOpcode[19] = "50" ;                                       push eax
$aOpcode[20] = "B8" & SwapEndian($pQueryPerformanceCounter);mov eax, $pQueryPerformanceCounter
$aOpcode[21] = "FFD0" ;                                     call eax

;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
$aOpcode[22] = "A1" & SwapEndian($pEndTime) & _    ; mov eax, dword[$pEndTime]
        "2B05" & SwapEndian($pStartTime) & _       ; sub eax, dword[$pStartTime]
        "69C0" & SwapEndian(1000) & _              ; imul eax, 1000
        "99" & _                                   ; cdq
        "8B0D" & SwapEndian($pFreq) & _            ; mov ecx, dword[$pFreq]
        "F7F1"                                     ; div ecx

;return
$aOpcode[23] = "C3";                                        ret
;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

#endregion Assembly


$sOpcode = _ArrayToString($aOpcode, '')
$execute = _Execute_Opcode($sOpcode)

;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
ConsoleWrite("! " & $execute & @CRLF)
;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

;Exit

$Freq = DllStructGetData($d_FT, 1)
$StartTime = DllStructGetData($d_ST, 1)
$EndTime = DllStructGetData($d_ET, 1)

$Total_Time = $EndTime - $StartTime
$Total_Time *= 1000
$Total_Time /= $Freq

;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
;MsgBox(0, 'Total Time', $Total_Time)
ConsoleWrite("! " & $Total_Time & @CRLF)
;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX


Func _Execute_Opcode($sOpcode)
    ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
    Local $CodeBuffer = DllStructCreate("byte[" & BinaryLen($sOpcode) & "]", $pRemoteCode)
    DllStructSetData($CodeBuffer, 1, $sOpcode)

    $Ret = DllCall("user32.dll", "int", "CallWindowProcW", _
            "ptr", DllStructGetPtr($CodeBuffer), _
            "int", 0, _
            "int", 0, _
            "int", 0, _
            "int", 0)
    Return $Ret[0]
    ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
EndFunc   ;==>_Execute_Opcode

Func _Get_Function_Address($sDLL, $sFunction)
    Local $Handle, $Address
    $Handle = _WinAPI_GetModuleHandle($sDLL)
    $Address = DllCall($sDLL, "ptr", "GetProcAddress", "ptr", $Handle, "str", $sFunction)
    Return $Address[0]
EndFunc   ;==>_Get_Function_Address

Func _jne($array, $iStart, $iEnd)
    Local $bytes
    $bytes = BinaryLen('0x' & _ArrayToString($array, '', $iEnd, $iStart)) + 2
    Return '75' & Hex(-$bytes, 2)

EndFunc   ;==>_jne

Func SwapEndian($iValue)
    ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
    Return Hex(BinaryMid($iValue, 1, 4))
    ;XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX
EndFunc   ;==>SwapEndian

♡♡♡

.

eMyvnE

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0