flat assembler
Message board for the users of flat assembler.

Index > Windows > My first PE program that could (but don't)

Author
Thread Post new topic Reply to topic
Esaam



Joined: 19 May 2009
Posts: 2
Esaam
First, I humbly apoligize as it's my first day doing assembly. I'm pretty sure my question is stupid but don't stone me to death. I was fiddling with org 100h then I wanted to go use PE

Code:
;-----------------
; test
;-----------------
format PE
entry start

section '.text' code readable executable
start:
        ; operations
        mov     ax, word [_message]
        mov     bx, word [_compare]
        cmp     ax,bx
        je      same    
        mov     dx, _no
        jmp     finish

same:
        mov     dx, _yes
        jmp     finish

; display
finish:
        mov     ah,9
        int     21h
        mov     ax, 4c00h
        int     21h

; db

section '.data' data readable
  _message db 'aa'
  _compare db 'aa'
  _yes  db 'same', 24h
  _no   db 'not the same', 24h    


But when I try to compile it I get :

Code:
C:\fasm>fasm test.asm test.exe
flat assembler  version 1.67.38  (1463903 kilobytes memory)
test.asm [14]:
        mov     dx, _no
error: value out of range.    


I don't quite understand as it works if I'm using the org 100h
Thank you for your time AND your patience. Embarassed
Post 19 May 2009, 23:00
View user's profile Send private message Reply with quote
bitshifter



Joined: 04 Dec 2007
Posts: 764
Location: Massachusetts, USA
bitshifter
You are trying to use a word pointer, it needs dword pointer
Use 32 bit instructions for Win32 PE
Needs much other work to be ready.
Start looking at fasm examples.

Its youre lucky day (i had nothing better to do)
Code:
format PE GUI 4.0
entry start 

section '.text' code readable executable 
    start:
        mov     ax,word[_message]
        mov     bx,word[_compare]
        mov     edi,_yes
        cmp     ax,bx 
        je      finish
        mov     edi,_no
    finish:
        push    0x00040040 ; MB_OK | MB_TOPMOST | MB_ICONINFORMATION
        push    _caption
        push    edi
        push    0
        call    [MessageBoxA]
        push    0
        call    [ExitProcess]

section '.data' data readable ;writeable
  _caption db 'result',0
  _message db 'aa'
  _compare db 'aa' 
  _yes  db 'same',0
  _no   db 'not the same',0

section '.idata' import data readable

  dd 0,0,0,rva kernel_name,rva kernel_table
  dd 0,0,0,rva user_name,rva user_table
  dd 0,0,0,0,0

  kernel_table:
    ExitProcess dd rva _ExitProcess
    dd 0
  user_table:
    MessageBoxA dd rva _MessageBoxA
    dd 0

  kernel_name db 'kernel32.dll',0
  user_name db 'user32.dll',0

  _ExitProcess dw 0
    db 'ExitProcess',0
  _MessageBoxA dw 0
    db 'MessageBoxA',0

section '.reloc' fixups data readable discardable
    

_________________
Coding a 3D game engine with fasm is like trying to eat an elephant,
you just have to keep focused and take it one 'byte' at a time.
Post 19 May 2009, 23:10
View user's profile Send private message Reply with quote
Esaam



Joined: 19 May 2009
Posts: 2
Esaam
Thank you very much as all the example I could find where using cinvokes and I would rather not use them for now.

However, I wanted to use console output. Which again is called through cinvoke in the examples I found.
Post 19 May 2009, 23:54
View user's profile Send private message Reply with quote
Borsuc



Joined: 29 Dec 2005
Posts: 2466
Location: Bucharest, Romania
Borsuc
All you have to do is manually "push" the function's arguments then, from right to left (i.e push the right-most first). Then call [WriteFile] or whatever with the console handle.
Post 20 May 2009, 00:57
View user's profile Send private message Reply with quote
bitshifter



Joined: 04 Dec 2007
Posts: 764
Location: Massachusetts, USA
bitshifter
How to get a console up and running in Windoze...
http://board.flatassembler.net/topic.php?t=10049

And like Borsuc said, something using invoke macro...
Code:
invoke MyTask,[value1],[value2]    


Can use no macro to do same thing...
Code:
push [value2]
push [value1]
call MyTask    


Or even for imported funcs...
Code:
push [value2]
push [value1]
call [ImpTask]    

_________________
Coding a 3D game engine with fasm is like trying to eat an elephant,
you just have to keep focused and take it one 'byte' at a time.
Post 20 May 2009, 06:36
View user's profile Send private message Reply with quote
DOS386



Joined: 08 Dec 2006
Posts: 1901
DOS386
You may NEVER use int 21h in a Win32 PE (might work in a DOS PE if someone insists, though). Your org 100h is NOT a Win32 executable, even if it "seems to work". You can use 16-bit instructions in a Win32 PE, but 32-bit is more efficient.
Post 21 May 2009, 13:48
View user's profile Send private message Reply with quote
Japheth



Joined: 26 Oct 2004
Posts: 151
Japheth
DOS386 wrote:
You may NEVER use int 21h in a Win32 PE.


This is "usually" true only. Here's a FASM sample how to use INT 21h in a Win32 PE:

Code:

format PE

;--- running DOS in Win32

szHello db "Hello world!",13,10,'$'

  entry realstart

start:
        mov edx,szHello
        mov ah,09h
        int 21h
        mov ax,4c00h
        int 21h
       
myexc:
;proc c pReport:dword, pFrame:dword, pContext:dword

        pushad
        mov ebp,esp

pReport   equ [ebp+9*4]
pFrame    equ [ebp+10*4]
pContext  equ [ebp+11*4]

STD_OUTPUT_HANDLE equ -11

rEdx   equ 0A8h
rEax        equ 0B0h
rEip        equ 0B8h
rEfl        equ 0C0h

        mov ebx, pReport
        mov edi, pContext
        mov edx, [edi+rEip]
        cmp word [edx], 021CDh
        jnz noint21
        mov al,[edi+rEax+1]
        cmp al,09
        jnz isnt09
        push STD_OUTPUT_HANDLE
        call [GetStdHandle]
        mov ebx, eax
        mov esi,[edi+rEdx]
nextitem:
        cmp byte [esi], '$'
        jz stringout_done
        push 0
        mov edx, esp
        push 0
        push edx
        push 1
        push esi
        push ebx
        call [WriteConsole]
        pop edx
        inc esi
        jmp nextitem
stringout_done:
        and byte [edi+rEfl],0FEh
        jmp int21done
isnt09:
        cmp al,4ch
        jnz int21done
        movzx eax,byte [edi+rEax]
        push eax
        call [ExitProcess]
int21done:
        add dword [edi+rEip], 2
        mov eax,0 ;0=continue execution
        jmp doneexc
noint21:
        mov eax,1
doneexc:
        mov [esp+28],eax
        popad
        ret

realstart:

        xor edx,edx
        push myexc
        push dword [fs:0]
        mov [fs:edx],esp
        call start
        push eax
        call [ExitProcess]

section '.idata' import data readable writeable

  dd 0,0,0,RVA kernel_name,RVA kernel_table
  dd 0,0,0,0,0

  kernel_table:
    ExitProcess dd RVA _ExitProcess
    GetStdHandle dd RVA _GetStdHandle
    WriteConsole dd RVA _WriteConsole
    dd 0

  kernel_name db 'KERNEL32.DLL',0

  _ExitProcess dw 0
    db 'ExitProcess',0
  _GetStdHandle dw 0
    db 'GetStdHandle',0
  _WriteConsole dw 0
    db 'WriteConsoleA',0
    


The original sample was in Masm and posted in the Masm32 forum some months ago.
Post 22 May 2009, 16:27
View user's profile Send private message Visit poster's website Reply with quote
DOS386



Joined: 08 Dec 2006
Posts: 1901
DOS386
Japheth wrote:
DOS386 wrote:
You may NEVER use int 21h in a Win32 PE.
This is "usually" true only. Here's a FASM sample how to use INT 21h in a Win32 PE


Yeah ... this is great Smile I've been searching for such an example and it even seems to work (on XP, later will test on ME also) Smile

Still, this is a very exotic hack, for beginners the rule persists: use PE examples and avoid int 21h (and INT instruction at all), org 100h and accessing segment registers Wink
Post 23 May 2009, 09:07
View user's profile Send private message Reply with quote
LiuGuoHua(Chinese)



Joined: 26 Sep 2003
Posts: 25
LiuGuoHua(Chinese)
To Japheth:
A very good trick to emulate DOS interruption! But I don't thinks it's a good example for beginner, maybe they will get a wrong conclusion that it is possible to call "int 21" on win32.
Post 03 Dec 2009, 14:36
View user's profile Send private message Reply with quote
DOS386



Joined: 08 Dec 2006
Posts: 1901
DOS386
> But I don't thinks it's a good example for beginner

Indeed, it's cool but not for a beginner. Also, one shouldn't ASS'ume that you can "use" segment registers in Win32 code (except, of course, for exceptions).

> ;--- running DOS in Win32

It doesn't work in ME Sad
Post 06 Dec 2009, 22:55
View user's profile Send private message Reply with quote
Display posts from previous:
Post new topic Reply to topic

Jump to:  


< Last Thread | Next Thread >
Forum Rules:
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You can download files in this forum


Copyright © 1999-2020, Tomasz Grysztar.

Powered by rwasa.