Subversion Repositories Kolibri OS

Rev

Rev 593 | Rev 2455 | Go to most recent revision | Blame | Compare with Previous | Last modification | View Log | Download | RSS feed

  1.  
  2. $Revision: 750 $
  3.  
  4.  
  5. ; Macroinstructions for defining and calling procedures
  6.  
  7. macro stdcall proc,[arg]                ; directly call STDCALL procedure
  8.  { common
  9.     if ~ arg eq
  10.    reverse
  11.     pushd arg
  12.    common
  13.     end if
  14.     call proc }
  15.  
  16. macro invoke proc,[arg]                 ; indirectly call STDCALL procedure
  17.  { common
  18.     if ~ arg eq
  19.    reverse
  20.      pushd arg
  21.    common
  22.     end if
  23.     call [proc] }
  24.  
  25. macro ccall proc,[arg]                  ; directly call CDECL procedure
  26.  { common
  27.     size@ccall = 0
  28.     if ~ arg eq
  29.    reverse
  30.     pushd arg
  31.     size@ccall = size@ccall+4
  32.    common
  33.     end if
  34.     call proc
  35.     if size@ccall
  36.     add esp,size@ccall
  37.     end if }
  38.  
  39. macro cinvoke proc,[arg]                ; indirectly call CDECL procedure
  40.  { common
  41.     size@ccall = 0
  42.     if ~ arg eq
  43.    reverse
  44.     pushd arg
  45.     size@ccall = size@ccall+4
  46.    common
  47.     end if
  48.     call [proc]
  49.     if size@ccall
  50.     add esp,size@ccall
  51.     end if }
  52.  
  53. macro proc [args]                       ; define procedure
  54.  { common
  55.     match name params, args>
  56.     \{ define@proc name,<params \} }
  57.  
  58. prologue@proc equ prologuedef
  59.  
  60. macro prologuedef procname,flag,parmbytes,localbytes,reglist
  61.  { if parmbytes | localbytes
  62.     push ebp
  63.     mov ebp,esp
  64.     if localbytes
  65.      sub esp,localbytes
  66.     end if
  67.    end if
  68.    irps reg, reglist \{ push reg \} }
  69.  
  70. epilogue@proc equ epiloguedef
  71.  
  72. macro epiloguedef procname,flag,parmbytes,localbytes,reglist
  73.  { irps reg, reglist \{ reverse pop reg \}
  74.    if parmbytes | localbytes
  75.     leave
  76.    end if
  77.    if (flag and 10000b) | (parmbytes=0)
  78.     retn
  79.    else
  80.     retn parmbytes
  81.    end if }
  82.  
  83. macro define@proc name,statement
  84.  { local params,flag,regs,parmbytes,localbytes,current
  85.    if used name
  86.    name:
  87.    match =stdcall args, statement \{ params equ args
  88.                                      flag = 11b \}
  89.    match =stdcall, statement \{ params equ
  90.                                 flag = 11b \}
  91.    match =c args, statement \{ params equ args
  92.                                flag = 10001b \}
  93.    match =c, statement \{ params equ
  94.                           flag = 10001b \}
  95.    match =params, params \{ params equ statement
  96.                             flag = 0 \}
  97.    virtual at ebp+8
  98.    match =uses reglist=,args, params \{ regs equ reglist
  99.                                         params equ args \}
  100.    match =regs =uses reglist, regs params \{ regs equ reglist
  101.                                              params equ \}
  102.    match =regs, regs \{ regs equ \}
  103.    match =,args, params \{ defargs@proc args \}
  104.    match =args@proc args, args@proc params \{ defargs@proc args \}
  105.    parmbytes = $ - (ebp+8)
  106.    end virtual
  107.    name # % = parmbytes/4
  108.    all@vars equ
  109.    current = 0
  110.    match prologue:reglist, prologue@proc:<regs> \{ prologue name,flag,parmbytes,localbytes,reglist \}
  111.    macro locals
  112.    \{ virtual at ebp-localbytes+current
  113.       macro label . \\{ deflocal@proc .,:, \\}
  114.       struc db [val] \\{ \common deflocal@proc .,db,val \\}
  115.       struc dw [val] \\{ \common deflocal@proc .,dw,val \\}
  116.       struc dp [val] \\{ \common deflocal@proc .,dp,val \\}
  117.       struc dd [val] \\{ \common deflocal@proc .,dd,val \\}
  118.       struc dt [val] \\{ \common deflocal@proc .,dt,val \\}
  119.       struc dq [val] \\{ \common deflocal@proc .,dq,val \\}
  120.       struc rb cnt \\{ deflocal@proc .,rb cnt, \\}
  121.       struc rw cnt \\{ deflocal@proc .,rw cnt, \\}
  122.       struc rp cnt \\{ deflocal@proc .,rp cnt, \\}
  123.       struc rd cnt \\{ deflocal@proc .,rd cnt, \\}
  124.       struc rt cnt \\{ deflocal@proc .,rt cnt, \\}
  125.       struc rq cnt \\{ deflocal@proc .,rq cnt, \\} \}
  126.    macro endl
  127.    \{ purge label
  128.       restruc db,dw,dp,dd,dt,dq
  129.       restruc rb,rw,rp,rd,rt,rq
  130.       restruc byte,word,dword,pword,tword,qword
  131.       current = $-(ebp-localbytes)
  132.       end virtual \}
  133.    macro ret operand
  134.    \{ match any, operand \\{ retn operand \\}
  135.       match , operand \\{ match epilogue:reglist, epilogue@proc:<regs>
  136.                           \\\{ epilogue name,flag,parmbytes,localbytes,reglist \\\} \\} \}
  137.    macro finish@proc \{ localbytes = (((current-1) shr 2)+1) shl 2
  138.                         end if \} }
  139.  
  140. macro defargs@proc [arg]
  141.  { common
  142.     if ~ arg eq
  143.    forward
  144.      local ..arg,current@arg
  145.      match argname:type, arg
  146.       \{ current@arg equ argname
  147.          label ..arg type
  148.          argname equ ..arg
  149.          if dqword eq type
  150.            dd ?,?,?,?
  151.          else if tbyte eq type
  152.            dd ?,?,?
  153.          else if qword eq type | pword eq type
  154.            dd ?,?
  155.          else
  156.            dd ?
  157.          end if \}
  158.      match =current@arg,current@arg
  159.       \{ current@arg equ arg
  160.          arg equ ..arg
  161.          ..arg dd ? \}
  162.    common
  163.      args@proc equ current@arg
  164.    forward
  165.      restore current@arg
  166.    common
  167.     end if }
  168.  
  169. macro deflocal@proc name,def,[val]
  170.  { common
  171.     match vars, all@vars \{ all@vars equ all@vars, \}
  172.     all@vars equ all@vars name
  173.    forward
  174.     local ..var,..tmp
  175.     ..var def val
  176.     match =?, val \{ ..tmp equ \}
  177.     match any =dup (=?), val \{ ..tmp equ \}
  178.     match tmp : value, ..tmp : val
  179.      \{ tmp: end virtual
  180.         initlocal@proc ..var,def value
  181.         virtual at tmp\}
  182.    common
  183.     match first rest, ..var, \{ name equ first \} }
  184.  
  185. macro initlocal@proc name,def
  186.  { virtual at name
  187.     def
  188.     size@initlocal = $ - name
  189.    end virtual
  190.    position@initlocal = 0
  191.    while size@initlocal > position@initlocal
  192.     virtual at name
  193.      def
  194.      if size@initlocal - position@initlocal < 2
  195.       current@initlocal = 1
  196.       load byte@initlocal byte from name+position@initlocal
  197.      else if size@initlocal - position@initlocal < 4
  198.       current@initlocal = 2
  199.       load word@initlocal word from name+position@initlocal
  200.      else
  201.       current@initlocal = 4
  202.       load dword@initlocal dword from name+position@initlocal
  203.      end if
  204.     end virtual
  205.     if current@initlocal = 1
  206.      mov byte [name+position@initlocal],byte@initlocal
  207.     else if current@initlocal = 2
  208.      mov word [name+position@initlocal],word@initlocal
  209.     else
  210.      mov dword [name+position@initlocal],dword@initlocal
  211.     end if
  212.     position@initlocal = position@initlocal + current@initlocal
  213.    end while }
  214.  
  215. macro endp
  216.  { purge ret,locals,endl
  217.    finish@proc
  218.    purge finish@proc
  219.    restore regs@proc
  220.    match all,args@proc \{ restore all \}
  221.    restore args@proc
  222.    match all,all@vars \{ restore all \} }
  223.  
  224. macro local [var]
  225.  { common
  226.     locals
  227.    forward done@local equ
  228.     match varname[count]:vartype, var
  229.     \{ match =BYTE, vartype \\{ varname rb count
  230.                                 restore done@local \\}
  231.        match =WORD, vartype \\{ varname rw count
  232.                                 restore done@local \\}
  233.        match =DWORD, vartype \\{ varname rd count
  234.                                  restore done@local \\}
  235.        match =PWORD, vartype \\{ varname rp count
  236.                                  restore done@local \\}
  237.        match =QWORD, vartype \\{ varname rq count
  238.                                  restore done@local \\}
  239.        match =TBYTE, vartype \\{ varname rt count
  240.                                  restore done@local \\}
  241.        match =DQWORD, vartype \\{ label varname dqword
  242.                                   rq count+count
  243.                                   restore done@local \\}
  244.        match , done@local \\{ virtual
  245.                                varname vartype
  246.                               end virtual
  247.                               rb count*sizeof.\#vartype
  248.                               restore done@local \\} \}
  249.     match :varname:vartype, done@local:var
  250.     \{ match =BYTE, vartype \\{ varname db ?
  251.                                 restore done@local \\}
  252.        match =WORD, vartype \\{ varname dw ?
  253.                                 restore done@local \\}
  254.        match =DWORD, vartype \\{ varname dd ?
  255.                                  restore done@local \\}
  256.        match =PWORD, vartype \\{ varname dp ?
  257.                                  restore done@local \\}
  258.        match =QWORD, vartype \\{ varname dq ?
  259.                                  restore done@local \\}
  260.        match =TBYTE, vartype \\{ varname dt ?
  261.                                  restore done@local \\}
  262.        match =DQWORD, vartype \\{ label varname dqword
  263.                                   dq ?,?
  264.                                   restore done@local \\}
  265.        match , done@local \\{ varname vartype
  266.                               restore done@local \\} \}
  267.     match ,done@local
  268.     \{ var
  269.        restore done@local \}
  270.    common
  271.     endl }
  272.