flat assembler
Message board for the users of flat assembler.

Index > Macroinstructions > HL Function, Return, Locals, Aliases

Author
Thread Post new topic Reply to topic
m3ntal



Joined: 08 Dec 2013
Posts: 296
m3ntal 17 Feb 2014, 05:43
To anyone who's writing a function/proc/edure, here's my function for reference. I've used it to create literally 1,000s of functions (See Sprite-Fight). Advantages: No prefix, HL return, no ret before endp, endf can return a value, easy locals, automatic [] for parameters and locals, usable in conjunction with get/try style constructs, will not be inserted in the executable unless it has been used, names aligned in lists/prototypes (unlike in C, name appears somewhere after the type), designed to be universal and portable to other CPUs (ie, no X86 specific optimizations).

Function:
Code:
; create "function/proc/edure"...

macro function name, [p] {
common

; only insert this inside of the executable
; if it was accessed somewhere

if used !#name ; real function !name
!#name:

; macro to call with no prefix.
; example: f a, b, c

macro name p \{
 pushr p
 call !\#name
\}

!#name#$type='f'
?begin equ !#name
?parameters equ p
..n.parameters=0
..n.locals=0
..locals.size=0
?alias equ

; create parameter names and offsets

if ~ p eq           ; if parameters
  virtual at ebp+8
  forward
  local ..p
  ..p dd ?          ; (ebp+Cool+i*4
  p equ [..p]
  ..n.parameters=\  ; i++
  ..n.parameters+1
  common
  end virtual
  push ebp          ; create stack frame
  mov ebp, esp
end if
; ...
}

; end function

macro endf v {
  if ~v eq
    mov eax, v
  end if
  .!:                        ; end
  return
  .$=$-?begin                ; total size
  if ..n.parameters<>0       ; if parameters
    match p, ?parameters
     \{ restore p, ?begin \}
   end if
  if ..n.locals<>0           ; if locals
    match l, local.names
     \{ restore l \}
    match a, ?alias \
     \{ restore a \}
  end if
 
  ; end "if used name" at very beginning
  ; of function
 
  end if
}

macro ?list.attach list, item {
  match any, list \{ list equ list, item \}
  match , list \{ list equ item \}
}    
Syntax:
Code:
function name, a, b, c
  ; ...
endf    
Return:
Code:
; HL return statement. no ret/urn before endf.
; it inserts one automatically

macro return v {
 if ~v eq               ; value?
   mov eax, v
 end if
 if ..n.parameters<>0   ; if parameters
   mov esp, ebp
   pop ebp
   ret ..n.parameters*4 ; ret n
 else if ..n.locals<>0  ; if locals
   mov esp, ebp
   pop ebp
   ret
 else
   ret
 end if
}    
Locals:
Code:
; locals ... - create local 32BIT variables.
; example: locals x, y, n, c

macro locals [p] {
  common local.names equ p
  forward ..n.locals=..n.locals+1
  common ..locals.size=..n.locals*4
  virtual at ebp-..locals.size
  forward
  local ..l
  ..l dd ?
  p equ [..l]
  common
  end virtual
  if ..n.parameters=0    ; create stack frame?
    push ebp
    mov ebp, esp
  end if
  sub esp, ..locals.size ; allocate locals
}

; create locals of specified sizes or 32BIT.
; example:

; locale x, y, username(32), filename(256),\
; image(IMAGE.$), my.font(FONT.$), etc

macro locale [p] {
  common
    ..locals.size=0
  forward                  ; get names and sizes
    define ?s 0
    match name(size), p \{ ; size specified
      ?list.attach local.names, name
      verify.size size
      ..locals.size=..locals.size+size
      define ?s 1
    \}
    match =0 name, ?s p \{ ; default 32BIT
      ?list.attach local.names, name
      ..locals.size=..locals.size+4
      define ?s 1
    \}
   ..n.locals=..n.locals+1
  common
    virtual at ebp-..locals.size ; get offsets
  forward
    local ..l
    define ?s 0
    match name(size), p \{
      ..l dd (size/4) dup(?)
      name equ [..l]
      define ?s 1
   \}
   match =0 name, ?s p \{  ; default 32BIT
     ..l dd ?
     name equ [..l]
     define ?s 1
   \}
  common
    end virtual
    if ..n.parameters=0    ; create stack frame?
      push ebp
      mov ebp, esp
    end if
    sub esp, ..locals.size ; allocate locals
}    
Aliases (See Magic-ARM Compiler)
Code:
; aliases for register names inside functions.
; endf will restore names. example:

; alias x=r0, y=r1, w=r2, h=r3, c=v1

macro alias [x] {
  forward
  match name==r, x \{
    ?list.attach ?alias, name
    name equ r
  \}
}    
Edit: pushr:
Code:
macro pushr [p] { reverse pushd p }    
Please compare this to the poor limited "proc" in Fresh-Lib which is not even as good as the one included with FASM.
Post 17 Feb 2014, 05:43
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-2024, Tomasz Grysztar. Also on GitHub, YouTube.

Website powered by rwasa.