2 ; Macroinstructions for defining and calling procedures
4 macro stdcall proc,[arg] ; directly call STDCALL procedure
13 macro invoke proc,[arg] ; indirectly call STDCALL procedure
22 macro ccall proc,[arg] ; directly call CDECL procedure
28 size@ccall = size@ccall+4
36 macro cinvoke proc,[arg] ; indirectly call CDECL procedure
42 size@ccall = size@ccall+4
50 macro proc [args] ; define procedure
52 match name params, args>
53 \{ define@proc name,<params \} }
55 prologue@proc equ prologuedef
57 macro prologuedef procname,flag,parmbytes,localbytes,reglist
58 { if parmbytes | localbytes
65 irps reg, reglist \{ push reg \} }
67 epilogue@proc equ epiloguedef
69 macro epiloguedef procname,flag,parmbytes,localbytes,reglist
70 { irps reg, reglist \{ reverse pop reg \}
71 if parmbytes | localbytes
74 if (flag and 10000b) | (parmbytes=0)
80 macro define@proc name,statement
81 { local params,flag,regs,parmbytes,localbytes,current
84 match =stdcall args, statement \{ params equ args
86 match =stdcall, statement \{ params equ
88 match =c args, statement \{ params equ args
90 match =c, statement \{ params equ
92 match =params, params \{ params equ statement
95 match =uses reglist=,args, params \{ regs equ reglist
97 match =regs =uses reglist, regs params \{ regs equ reglist
99 match =regs, regs \{ regs equ \}
100 match =,args, params \{ defargs@proc args \}
101 match =args@proc args, args@proc params \{ defargs@proc args \}
102 parmbytes = $ - (ebp+8)
104 name # % = parmbytes/4
107 match prologue:reglist, prologue@proc:<regs> \{ prologue name,flag,parmbytes,localbytes,reglist \}
109 \{ virtual at ebp-localbytes+current
110 macro label . \\{ deflocal@proc .,:, \\}
111 struc db [val] \\{ \common deflocal@proc .,db,val \\}
112 struc dw [val] \\{ \common deflocal@proc .,dw,val \\}
113 struc dp [val] \\{ \common deflocal@proc .,dp,val \\}
114 struc dd [val] \\{ \common deflocal@proc .,dd,val \\}
115 struc dt [val] \\{ \common deflocal@proc .,dt,val \\}
116 struc dq [val] \\{ \common deflocal@proc .,dq,val \\}
117 struc rb cnt \\{ deflocal@proc .,rb cnt, \\}
118 struc rw cnt \\{ deflocal@proc .,rw cnt, \\}
119 struc rp cnt \\{ deflocal@proc .,rp cnt, \\}
120 struc rd cnt \\{ deflocal@proc .,rd cnt, \\}
121 struc rt cnt \\{ deflocal@proc .,rt cnt, \\}
122 struc rq cnt \\{ deflocal@proc .,rq cnt, \\} \}
125 restruc db,dw,dp,dd,dt,dq
126 restruc rb,rw,rp,rd,rt,rq
127 restruc byte,word,dword,pword,tword,qword
128 current = $-(ebp-localbytes)
131 \{ match any, operand \\{ retn operand \\}
132 match , operand \\{ match epilogue:reglist, epilogue@proc:<regs>
133 \\\{ epilogue name,flag,parmbytes,localbytes,reglist \\\} \\} \}
134 macro finish@proc \{ localbytes = (((current-1) shr 2)+1) shl 2
137 macro defargs@proc [arg]
141 local ..arg,current@arg
142 match argname:type, arg
143 \{ current@arg equ argname
148 else if tbyte eq type
150 else if qword eq type | pword eq type
155 match =current@arg,current@arg
156 \{ current@arg equ arg
160 args@proc equ current@arg
166 macro deflocal@proc name,def,[val]
168 match vars, all@vars \{ all@vars equ all@vars, \}
169 all@vars equ all@vars name
173 match =?, val \{ ..tmp equ \}
174 match any =dup (=?), val \{ ..tmp equ \}
175 match tmp : value, ..tmp : val
177 initlocal@proc ..var,def value
180 match first rest, ..var, \{ name equ first \} }
182 macro initlocal@proc name,def
185 size@initlocal = $ - name
187 position@initlocal = 0
188 while size@initlocal > position@initlocal
191 if size@initlocal - position@initlocal < 2
192 current@initlocal = 1
193 load byte@initlocal byte from name+position@initlocal
194 else if size@initlocal - position@initlocal < 4
195 current@initlocal = 2
196 load word@initlocal word from name+position@initlocal
198 current@initlocal = 4
199 load dword@initlocal dword from name+position@initlocal
202 if current@initlocal = 1
203 mov byte [name+position@initlocal],byte@initlocal
204 else if current@initlocal = 2
205 mov word [name+position@initlocal],word@initlocal
207 mov dword [name+position@initlocal],dword@initlocal
209 position@initlocal = position@initlocal + current@initlocal
213 { purge ret,locals,endl
217 match all,args@proc \{ restore all \}
219 match all,all@vars \{ restore all \} }
224 forward done@local equ
225 match varname[count]:vartype, var
226 \{ match =BYTE, vartype \\{ varname rb count
227 restore done@local \\}
228 match =WORD, vartype \\{ varname rw count
229 restore done@local \\}
230 match =DWORD, vartype \\{ varname rd count
231 restore done@local \\}
232 match =PWORD, vartype \\{ varname rp count
233 restore done@local \\}
234 match =QWORD, vartype \\{ varname rq count
235 restore done@local \\}
236 match =TBYTE, vartype \\{ varname rt count
237 restore done@local \\}
238 match =DQWORD, vartype \\{ label varname dqword
240 restore done@local \\}
241 match , done@local \\{ virtual
244 rb count*sizeof.\#vartype
245 restore done@local \\} \}
246 match :varname:vartype, done@local:var
247 \{ match =BYTE, vartype \\{ varname db ?
248 restore done@local \\}
249 match =WORD, vartype \\{ varname dw ?
250 restore done@local \\}
251 match =DWORD, vartype \\{ varname dd ?
252 restore done@local \\}
253 match =PWORD, vartype \\{ varname dp ?
254 restore done@local \\}
255 match =QWORD, vartype \\{ varname dq ?
256 restore done@local \\}
257 match =TBYTE, vartype \\{ varname dt ?
258 restore done@local \\}
259 match =DQWORD, vartype \\{ label varname dqword
261 restore done@local \\}
262 match , done@local \\{ varname vartype
263 restore done@local \\} \}
266 restore done@local \}