flat assembler
Message board for the users of flat assembler.

Index > Windows > Learning fasm from masm

Goto page Previous  1, 2, 3, 4, 5, 6  Next
Author
Thread Post new topic Reply to topic
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 14 Sep 2012, 23:16
Thanks i_inc.

There are two things I really want to learn right now, one being able to write macros and the second being able to write constants or string to a text file by using some sort of conditional assembly.

I am not sure if FASM have the ability to write stuff to a text file in the current project folder by using some conditional assembly, perhaps you can tell me.

Most importantly, I wish I knew of a good website that could explain away how to write macros, for the absolute beginner.

What I especially want to learn is how to return values from a macro and pass the returned value as parameter to a invoke procedure call.
Post 14 Sep 2012, 23:16
View user's profile Send private message Reply with quote
l_inc



Joined: 23 Oct 2009
Posts: 881
l_inc 15 Sep 2012, 02:43
nmake
Quote:
I am not sure if FASM have the ability to write stuff to a text file in the current project folder by using some conditional assembly, perhaps you can tell me.

Basically, the only output after the compilation is a single file (you can specify creation of a corresponding symbols file, but that's a different story). Therefore the only situation, when it's possible to write stuff to a text file, is when you compile the text file.

Quote:
I wish I knew of a good website that could explain away how to write macros, for the absolute beginner

Well. Here it is. Smile The manual from the fasm package actually provides all information without any assumptions of the reader's initial knowledge. You just need to read it veeeery attentively and many (three-four) times. Additionally it's always advisable to read this and especially this.

Quote:
What I especially want to learn is how to return values from a macro

Any macro parameter can be a return value. E.g.:
Code:
macro sum res,x,y { res = x + y }
sum result,1,2    

After this code is preprocessed and assembled, the numeric constant result will contain 3. If you want the return value to be placed into a symbol preceding the macro name, you may use another kind of macros (defined with the struc directive):
Code:
struc sum x,y { . = x + y }
result sum 1,2    

This is equivalent to the previous code snippet.

Quote:
and pass the returned value as parameter to a invoke procedure call

A macro is expanded only if it is the first (if defined with macro) or the second (if defined with struc) token on a line or if it will be placed on the first or second position during preprocessing. A single exception to this rule is when it follows a colon-defined label. Fasm does not support inline macros.

Therefore, if you want macros to be expanded on a line starting with the invoke macro, you have to redefine the invoke macro, so that it detects the macros, extracts them onto the corresponding position on a line (first or second) and uses their results appropriately.
Post 15 Sep 2012, 02:43
View user's profile Send private message Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 15 Sep 2012, 04:52
Thanks alot.

If I include a source file (lets call it a.asm) into my main source file (main.asm), and a.asm only contains one procedure. Will this procedure be compiled into the final executable if I don't make any reference to it?

And if a.asm make references to an API function and main.asm also make reference to the same API function, will the executable get two imports of the same function if both imports the same API function?
Post 15 Sep 2012, 04:52
View user's profile Send private message Reply with quote
JohnFound



Joined: 16 Jun 2003
Posts: 3499
Location: Bulgaria
JohnFound 15 Sep 2012, 08:24
No and No. Smile
Post 15 Sep 2012, 08:24
View user's profile Send private message Visit poster's website ICQ Number Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 15 Sep 2012, 14:09
A philosophical question, why is fasm created with times/repeat/while blocks, but no for/do? Question
Post 15 Sep 2012, 14:09
View user's profile Send private message Reply with quote
JohnFound



Joined: 16 Jun 2003
Posts: 3499
Location: Bulgaria
JohnFound 15 Sep 2012, 15:13
nmake wrote:
A philosophical question, why is fasm created with times/repeat/while blocks, but no for/do? Question


Well, Tomasz can say for sure, but for IMHO, FASM design is influenced by Pascal syntax, where "for" is not so flexible than in C/C++, so minimalistic approach require "while" cycles to be implemented rather than "for".

_________________
Tox ID: 48C0321ADDB2FE5F644BB5E3D58B0D58C35E5BCBC81D7CD333633FEDF1047914A534256478D9
Post 15 Sep 2012, 15:13
View user's profile Send private message Visit poster's website ICQ Number Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 15 Sep 2012, 17:04
Thanks.

If I import an API function in a.asm, I naturally would write the import segment and the imports in that source file.

But when I include a.asm in main.asm, will the import segment in a.asm be melted together with the import segment in main.asm? Or will it produce two separate import segments?

Also, is it normal to place include directives at the top of the main source file or is it common to place it at various places around the source file? Smile

How many segments can an executable contain btw, and how large can it be?
Post 15 Sep 2012, 17:04
View user's profile Send private message Reply with quote
JohnFound



Joined: 16 Jun 2003
Posts: 3499
Location: Bulgaria
JohnFound 15 Sep 2012, 17:19
In a.asm you should not put any import sections at all. You only need to create one import section in your main file. Generally speaking you only need to include some files from the "include/api/" directory and leave FASM macros to deal with the functions. Something like this:
Code:
section '.idata' import data readable writeable

  library kernel32,'KERNEL32.DLL',\
          user32,'USER32.DLL'

  include 'api\kernel32.inc'
  include 'api\user32.inc'  
    


About the include files - you place "include" statement where you want the file to be included. It depends on what this file contains and where you need it. For example, if the file contains macro definitions, you must include it before you use these macros.
Post 15 Sep 2012, 17:19
View user's profile Send private message Visit poster's website ICQ Number Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 15 Sep 2012, 22:13
Thanks.

What if my include file have one procedure and it also have data it is dependent on, can I create a .data segment in the include file and then include it in my main file, will the two segments melt together and form one segment? Smile

Let's say a.asm contains this:

Code:
section '.data' data readable writeable
        buf db 2000 dup 0

proc test
   mov eax, [buf]
   ret
endp
    

Can I include this file in my main now with this segment defined?

I also wonder what the true difference between the rept directive and the times directive. It seems like almost the same.

And I also wonder if it makes any difference if I put the .data segment at the top of the source code, I have a habit from masm of having the data segment at the top before the code segment?
Post 15 Sep 2012, 22:13
View user's profile Send private message Reply with quote
farrier



Joined: 26 Aug 2004
Posts: 274
Location: North Central Mississippi
farrier 16 Sep 2012, 01:34

_________________
Some Assembly Required
It's a good day to code!
U.S.Constitution; Bill of Rights; Amendment 1:
... the right of the people peaceably to assemble, ...
The code is dark, and full of errors!
Post 16 Sep 2012, 01:34
View user's profile Send private message Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 16 Sep 2012, 02:38
How can I put the offset of my window procedure into the WNDCLASSEX structure, the compiler gives me an error when I do that, but not when I do it with DialogBoxParam?

I have the WNDCLASSEX structure predefined in the data section.
Post 16 Sep 2012, 02:38
View user's profile Send private message Reply with quote
JohnFound



Joined: 16 Jun 2003
Posts: 3499
Location: Bulgaria
JohnFound 16 Sep 2012, 05:22
nmake, source where error appears, please.
Post 16 Sep 2012, 05:22
View user's profile Send private message Visit poster's website ICQ Number Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 16 Sep 2012, 05:54
JohnFound, the error went away. It occured because I put the type behind the parameter names in the procedure. I normally do that in Masm, but apparently it should not be done in Fasm?

I did this:

proc procname param1:DWORD, param2:DWORD

when I tried to refer get offset of procname, it failed. but succeeded when I did this:

proc procname param1, param2

Confused
Post 16 Sep 2012, 05:54
View user's profile Send private message Reply with quote
l_inc



Joined: 23 Oct 2009
Posts: 881
l_inc 16 Sep 2012, 14:55
nmake
Quote:
I did this:

proc procname param1:DWORD, param2:DWORD

when I tried to refer get offset of procname, it failed. but succeeded when I did this:

proc procname param1, param2

Impossible. You're mistaken somewhere else.
Post 16 Sep 2012, 14:55
View user's profile Send private message Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 16 Sep 2012, 23:12
I_inc: That is what I did, I have no idea what might have caused it, I did it back and forth to verify it, and it works when I remove parameter types and doesn't when I add them.

Could you teach me how to properly use procedures and parameters in fasm?
Post 16 Sep 2012, 23:12
View user's profile Send private message Reply with quote
l_inc



Joined: 23 Oct 2009
Posts: 881
l_inc 16 Sep 2012, 23:46
nmake
Quote:
Could you teach me how to properly use procedures and parameters in fasm?

There's nothing special about using procedures apart from what you've already shown. However it would be useful to see a minimal compilable example where you observe the described situation.
Post 16 Sep 2012, 23:46
View user's profile Send private message Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 17 Sep 2012, 00:25
JohnFound wrote:
nmake, source where error appears, please.

I solved it, but here is the code if you still want it. The problem happened when I tried to add the offset of WndProc into the WNDCLASSEX structure. It failed when I put parameter types behind the parameter names in WndProc, and succeeded when I removed it.

Beware, the window content will be empty because I removed background erasing, I will copy a dib section to it later when I fill in something useful, so you will only see the frame of the window with a corrupted content inside it.

Code:
display 'Template for non dialog window',13,10,13,10

WIDTH = 800
HEIGHT = 600

format PE GUI 4.0
entry start

include "win32a.inc"

section '.data' data readable writeable
        align 4
        hInstance rd 1
        wc WNDCLASSEX sizeof.WNDCLASSEX,\ ; size of structure
                      0,\ ; style
                      WndProc,\ ; address of window proc
                      0,\ ; cbClsExtra
                      0,\ ; cbWndExtra
                      400000h,\ ; hInstance
                      0,\ ; hIcon
                      0,\ ; hCursor (must be loaded)
                      0,\ ; hbrBackground
                      0,\ ; lpszMenuName
                      ClassName,\ ; lpszClassName
                      0
        msg MSG
        ClassName db "Window",0
        WindowName db "Fasm",0
        QuitCpt db "Quitting",0
        QuitTxt db "Quitting now...",0

section '.idata' import data readable writeable
        library kernel32,'KERNEL32.DLL',\
                user32,'USER32.DLL'
        include 'api\kernel32.inc'
        include 'api\user32.inc'

section '.text' code readable executable
  start:
        xor ebx,ebx
        mov esi,wc
        mov edi,WS_OVERLAPPEDWINDOW
        invoke GetModuleHandle,ebx
        mov [hInstance],eax

        invoke LoadCursor,ebx,IDC_ARROW
        mov [wc.hCursor],eax

        invoke RegisterClassEx,esi

        invoke GetSystemMetrics,SM_CXSCREEN
        push eax
        invoke GetSystemMetrics,SM_CYSCREEN
        mov ecx,HEIGHT
        sub eax,ecx
        shr eax,1
        sub eax,1 ; y
        pop ecx
        mov edx,WIDTH
        sub ecx,edx
        shr ecx,1
        sub ecx,1

        invoke CreateWindowEx,ebx,ClassName,WindowName,edi,ecx,eax,WIDTH,HEIGHT,ebx,ebx,[hInstance],ebx

        mov edi,eax ; hwnd
        mov esi, msg
        invoke ShowWindow,edi,SW_SHOWNORMAL
align 16
.msg:   invoke GetMessage,esi,ebx,ebx,ebx
        test eax,eax
        jz .die
        invoke TranslateMessage,esi
        invoke DispatchMessage,esi
        jmp .msg
.die:   invoke ExitProcess,ebx

proc WndProc hwnd,uMsg,wParam,lParam
     mov eax,[uMsg]
     cmp eax,WM_CLOSE
     je .close
     cmp eax,WM_DESTROY
     je .destroy
     cmp eax,WM_ERASEBKGND
     je .erase

     invoke DefWindowProc,[hwnd],[uMsg],[wParam],[lParam]
     ret

.erase:
     mov eax, 1
     ret

.destroy:
     invoke PostQuitMessage,NULL
     xor eax,eax
     ret

.close:
     invoke MessageBox,[hwnd],QuitTxt,QuitCpt,MB_OKCANCEL+MB_ICONWARNING+MB_DEFBUTTON2
     cmp eax,IDOK
     jne @F
     invoke DestroyWindow,[hwnd]
@@:  xor eax,eax
     ret
endp
    
Post 17 Sep 2012, 00:25
View user's profile Send private message Reply with quote
l_inc



Joined: 23 Oct 2009
Posts: 881
l_inc 17 Sep 2012, 00:40
nmake
It still perfectly compiles if you replace the line
Code:
proc WndProc hwnd,uMsg,wParam,lParam    

with the line
Code:
proc WndProc hwnd:DWORD,uMsg:DWORD,wParam:DWORD,lParam:DWORD    
.
You get an error only if you specify something other than a size operator (see table 1.1). If you want to be able to specify anything, I can provide a simple macro, that will default to DWORD, if something other than a size operator is specified.
Post 17 Sep 2012, 00:40
View user's profile Send private message Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 17 Sep 2012, 02:17
I see. Yes I did use the appropriate HWND, UINT and etc. But these are typedefs that really just point straight back to DWORD, so I wonder why it fails. A HWND is just a typedef of a DWORD.

Anyways, that explains it.
Post 17 Sep 2012, 02:17
View user's profile Send private message Reply with quote
nmake



Joined: 13 Sep 2012
Posts: 192
nmake 17 Sep 2012, 12:20
Semicolon comments out lines, but is there a way to comment out sections of code in fasm?
Post 17 Sep 2012, 12:20
View user's profile Send private message Reply with quote
Display posts from previous:
Post new topic Reply to topic

Jump to:  
Goto page Previous  1, 2, 3, 4, 5, 6  Next

< 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-2025, Tomasz Grysztar. Also on GitHub, YouTube.

Website powered by rwasa.