Rev 9577 | Details | Compare with Previous | Last modification | View Log | RSS feed
Rev | Author | Line No. | Line |
---|---|---|---|
7983 | leency | 1 | (* |
7597 | akron1 | 2 | BSD 2-Clause License |
6613 | leency | 3 | |
9577 | akron1 | 4 | Copyright (c) 2018-2019, 2022 Anton Krotov |
7597 | akron1 | 5 | All rights reserved. |
6613 | leency | 6 | *) |
7 | |||
8 | MODULE KOSAPI; |
||
9 | |||
7597 | akron1 | 10 | IMPORT SYSTEM; |
6613 | leency | 11 | |
12 | |||
7597 | akron1 | 13 | TYPE |
6613 | leency | 14 | |
7597 | akron1 | 15 | STRING = ARRAY 1024 OF CHAR; |
16 | |||
17 | |||
18 | VAR |
||
19 | |||
20 | DLL_INIT: PROCEDURE [stdcall] (entry: INTEGER); |
||
21 | |||
22 | |||
23 | PROCEDURE [stdcall-] sysfunc1* (arg1: INTEGER): INTEGER; |
||
6613 | leency | 24 | BEGIN |
7597 | akron1 | 25 | SYSTEM.CODE( |
26 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
27 | 0CDH, 040H, (* int 64 *) |
||
28 | 0C9H, (* leave *) |
||
29 | 0C2H, 004H, 000H (* ret 4 *) |
||
30 | ) |
||
31 | RETURN 0 |
||
6613 | leency | 32 | END sysfunc1; |
33 | |||
7597 | akron1 | 34 | |
35 | PROCEDURE [stdcall-] sysfunc2* (arg1, arg2: INTEGER): INTEGER; |
||
6613 | leency | 36 | BEGIN |
7597 | akron1 | 37 | SYSTEM.CODE( |
38 | 053H, (* push ebx *) |
||
39 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
40 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
41 | 0CDH, 040H, (* int 64 *) |
||
42 | 05BH, (* pop ebx *) |
||
43 | 0C9H, (* leave *) |
||
44 | 0C2H, 008H, 000H (* ret 8 *) |
||
45 | ) |
||
46 | RETURN 0 |
||
6613 | leency | 47 | END sysfunc2; |
48 | |||
7597 | akron1 | 49 | |
50 | PROCEDURE [stdcall-] sysfunc3* (arg1, arg2, arg3: INTEGER): INTEGER; |
||
6613 | leency | 51 | BEGIN |
7597 | akron1 | 52 | SYSTEM.CODE( |
53 | 053H, (* push ebx *) |
||
54 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
55 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
56 | 08BH, 04DH, 010H, (* mov ecx, dword [ebp + 16] *) |
||
57 | 0CDH, 040H, (* int 64 *) |
||
58 | 05BH, (* pop ebx *) |
||
59 | 0C9H, (* leave *) |
||
60 | 0C2H, 00CH, 000H (* ret 12 *) |
||
61 | ) |
||
62 | RETURN 0 |
||
6613 | leency | 63 | END sysfunc3; |
64 | |||
7597 | akron1 | 65 | |
66 | PROCEDURE [stdcall-] sysfunc4* (arg1, arg2, arg3, arg4: INTEGER): INTEGER; |
||
6613 | leency | 67 | BEGIN |
7597 | akron1 | 68 | SYSTEM.CODE( |
69 | 053H, (* push ebx *) |
||
70 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
71 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
72 | 08BH, 04DH, 010H, (* mov ecx, dword [ebp + 16] *) |
||
73 | 08BH, 055H, 014H, (* mov edx, dword [ebp + 20] *) |
||
74 | 0CDH, 040H, (* int 64 *) |
||
75 | 05BH, (* pop ebx *) |
||
76 | 0C9H, (* leave *) |
||
77 | 0C2H, 010H, 000H (* ret 16 *) |
||
78 | ) |
||
79 | RETURN 0 |
||
6613 | leency | 80 | END sysfunc4; |
81 | |||
7597 | akron1 | 82 | |
83 | PROCEDURE [stdcall-] sysfunc5* (arg1, arg2, arg3, arg4, arg5: INTEGER): INTEGER; |
||
6613 | leency | 84 | BEGIN |
7597 | akron1 | 85 | SYSTEM.CODE( |
86 | 053H, (* push ebx *) |
||
87 | 056H, (* push esi *) |
||
88 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
89 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
90 | 08BH, 04DH, 010H, (* mov ecx, dword [ebp + 16] *) |
||
91 | 08BH, 055H, 014H, (* mov edx, dword [ebp + 20] *) |
||
92 | 08BH, 075H, 018H, (* mov esi, dword [ebp + 24] *) |
||
93 | 0CDH, 040H, (* int 64 *) |
||
94 | 05EH, (* pop esi *) |
||
95 | 05BH, (* pop ebx *) |
||
96 | 0C9H, (* leave *) |
||
97 | 0C2H, 014H, 000H (* ret 20 *) |
||
98 | ) |
||
99 | RETURN 0 |
||
6613 | leency | 100 | END sysfunc5; |
101 | |||
7597 | akron1 | 102 | |
103 | PROCEDURE [stdcall-] sysfunc6* (arg1, arg2, arg3, arg4, arg5, arg6: INTEGER): INTEGER; |
||
6613 | leency | 104 | BEGIN |
7597 | akron1 | 105 | SYSTEM.CODE( |
106 | 053H, (* push ebx *) |
||
107 | 056H, (* push esi *) |
||
108 | 057H, (* push edi *) |
||
109 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
110 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
111 | 08BH, 04DH, 010H, (* mov ecx, dword [ebp + 16] *) |
||
112 | 08BH, 055H, 014H, (* mov edx, dword [ebp + 20] *) |
||
113 | 08BH, 075H, 018H, (* mov esi, dword [ebp + 24] *) |
||
114 | 08BH, 07DH, 01CH, (* mov edi, dword [ebp + 28] *) |
||
115 | 0CDH, 040H, (* int 64 *) |
||
116 | 05FH, (* pop edi *) |
||
117 | 05EH, (* pop esi *) |
||
118 | 05BH, (* pop ebx *) |
||
119 | 0C9H, (* leave *) |
||
120 | 0C2H, 018H, 000H (* ret 24 *) |
||
121 | ) |
||
122 | RETURN 0 |
||
6613 | leency | 123 | END sysfunc6; |
124 | |||
7597 | akron1 | 125 | |
126 | PROCEDURE [stdcall-] sysfunc7* (arg1, arg2, arg3, arg4, arg5, arg6, arg7: INTEGER): INTEGER; |
||
6613 | leency | 127 | BEGIN |
7597 | akron1 | 128 | SYSTEM.CODE( |
129 | 053H, (* push ebx *) |
||
130 | 056H, (* push esi *) |
||
131 | 057H, (* push edi *) |
||
132 | 055H, (* push ebp *) |
||
133 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
134 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
135 | 08BH, 04DH, 010H, (* mov ecx, dword [ebp + 16] *) |
||
136 | 08BH, 055H, 014H, (* mov edx, dword [ebp + 20] *) |
||
137 | 08BH, 075H, 018H, (* mov esi, dword [ebp + 24] *) |
||
138 | 08BH, 07DH, 01CH, (* mov edi, dword [ebp + 28] *) |
||
139 | 08BH, 06DH, 020H, (* mov ebp, dword [ebp + 32] *) |
||
140 | 0CDH, 040H, (* int 64 *) |
||
141 | 05DH, (* pop ebp *) |
||
142 | 05FH, (* pop edi *) |
||
143 | 05EH, (* pop esi *) |
||
144 | 05BH, (* pop ebx *) |
||
145 | 0C9H, (* leave *) |
||
146 | 0C2H, 01CH, 000H (* ret 28 *) |
||
147 | ) |
||
148 | RETURN 0 |
||
6613 | leency | 149 | END sysfunc7; |
150 | |||
7597 | akron1 | 151 | |
152 | PROCEDURE [stdcall-] sysfunc22* (arg1, arg2: INTEGER; VAR res2: INTEGER): INTEGER; |
||
6613 | leency | 153 | BEGIN |
7597 | akron1 | 154 | SYSTEM.CODE( |
155 | 053H, (* push ebx *) |
||
156 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
157 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
158 | 0CDH, 040H, (* int 64 *) |
||
159 | 08BH, 04DH, 010H, (* mov ecx, dword [ebp + 16] *) |
||
160 | 089H, 019H, (* mov dword [ecx], ebx *) |
||
161 | 05BH, (* pop ebx *) |
||
162 | 0C9H, (* leave *) |
||
163 | 0C2H, 00CH, 000H (* ret 12 *) |
||
164 | ) |
||
165 | RETURN 0 |
||
6613 | leency | 166 | END sysfunc22; |
167 | |||
7597 | akron1 | 168 | |
169 | PROCEDURE mem_commit (adr, size: INTEGER); |
||
170 | VAR |
||
171 | tmp: INTEGER; |
||
6647 | akron1 | 172 | BEGIN |
7597 | akron1 | 173 | FOR tmp := adr TO adr + size - 1 BY 4096 DO |
174 | SYSTEM.PUT(tmp, 0) |
||
175 | END |
||
6647 | akron1 | 176 | END mem_commit; |
177 | |||
7597 | akron1 | 178 | |
179 | PROCEDURE [stdcall] malloc* (size: INTEGER): INTEGER; |
||
180 | VAR |
||
181 | ptr: INTEGER; |
||
6613 | leency | 182 | BEGIN |
7597 | akron1 | 183 | SYSTEM.CODE(060H); (* pusha *) |
184 | IF sysfunc2(18, 16) > ASR(size, 10) THEN |
||
185 | ptr := sysfunc3(68, 12, size); |
||
186 | IF ptr # 0 THEN |
||
187 | mem_commit(ptr, size) |
||
188 | END |
||
189 | ELSE |
||
190 | ptr := 0 |
||
191 | END; |
||
192 | SYSTEM.CODE(061H) (* popa *) |
||
193 | RETURN ptr |
||
6613 | leency | 194 | END malloc; |
195 | |||
7597 | akron1 | 196 | |
197 | PROCEDURE [stdcall] free* (ptr: INTEGER): INTEGER; |
||
6613 | leency | 198 | BEGIN |
7597 | akron1 | 199 | SYSTEM.CODE(060H); (* pusha *) |
200 | IF ptr # 0 THEN |
||
201 | ptr := sysfunc3(68, 13, ptr) |
||
202 | END; |
||
203 | SYSTEM.CODE(061H) (* popa *) |
||
204 | RETURN 0 |
||
6613 | leency | 205 | END free; |
206 | |||
7597 | akron1 | 207 | |
208 | PROCEDURE [stdcall] realloc* (ptr, size: INTEGER): INTEGER; |
||
6613 | leency | 209 | BEGIN |
7597 | akron1 | 210 | SYSTEM.CODE(060H); (* pusha *) |
211 | ptr := sysfunc4(68, 20, size, ptr); |
||
212 | SYSTEM.CODE(061H) (* popa *) |
||
213 | RETURN ptr |
||
6613 | leency | 214 | END realloc; |
215 | |||
7597 | akron1 | 216 | |
217 | PROCEDURE AppAdr (): INTEGER; |
||
7209 | akron1 | 218 | VAR |
219 | buf: ARRAY 1024 OF CHAR; |
||
220 | a: INTEGER; |
||
221 | BEGIN |
||
7597 | akron1 | 222 | a := sysfunc3(9, SYSTEM.ADR(buf), -1); |
223 | SYSTEM.GET(SYSTEM.ADR(buf) + 22, a) |
||
7209 | akron1 | 224 | RETURN a |
225 | END AppAdr; |
||
226 | |||
7597 | akron1 | 227 | |
228 | PROCEDURE GetCommandLine* (): INTEGER; |
||
229 | VAR |
||
230 | param: INTEGER; |
||
6613 | leency | 231 | BEGIN |
7597 | akron1 | 232 | SYSTEM.GET(28 + AppAdr(), param) |
233 | RETURN param |
||
6613 | leency | 234 | END GetCommandLine; |
235 | |||
7597 | akron1 | 236 | |
237 | PROCEDURE GetName* (): INTEGER; |
||
238 | VAR |
||
239 | name: INTEGER; |
||
6613 | leency | 240 | BEGIN |
7597 | akron1 | 241 | SYSTEM.GET(32 + AppAdr(), name) |
242 | RETURN name |
||
6613 | leency | 243 | END GetName; |
244 | |||
7597 | akron1 | 245 | |
246 | PROCEDURE [stdcall] dll_init2 (arg1, arg2, arg3, arg4, arg5: INTEGER); |
||
6613 | leency | 247 | BEGIN |
7597 | akron1 | 248 | SYSTEM.CODE( |
249 | 060H, (* pusha *) |
||
250 | 08BH, 045H, 008H, (* mov eax, dword [ebp + 8] *) |
||
251 | 08BH, 05DH, 00CH, (* mov ebx, dword [ebp + 12] *) |
||
252 | 08BH, 04DH, 010H, (* mov ecx, dword [ebp + 16] *) |
||
253 | 08BH, 055H, 014H, (* mov edx, dword [ebp + 20] *) |
||
254 | 08BH, 075H, 018H, (* mov esi, dword [ebp + 24] *) |
||
255 | 0FFH, 0D6H, (* call esi *) |
||
256 | 061H, (* popa *) |
||
257 | 0C9H, (* leave *) |
||
258 | 0C2H, 014H, 000H (* ret 20 *) |
||
259 | ) |
||
6613 | leency | 260 | END dll_init2; |
261 | |||
262 | |||
7597 | akron1 | 263 | PROCEDURE GetProcAdr* (name: ARRAY OF CHAR; lib: INTEGER): INTEGER; |
264 | VAR |
||
265 | cur, procname, adr: INTEGER; |
||
6613 | leency | 266 | |
7597 | akron1 | 267 | PROCEDURE streq (str1, str2: INTEGER): BOOLEAN; |
268 | VAR |
||
269 | c1, c2: CHAR; |
||
270 | BEGIN |
||
271 | REPEAT |
||
272 | SYSTEM.GET(str1, c1); |
||
273 | SYSTEM.GET(str2, c2); |
||
274 | INC(str1); |
||
275 | INC(str2) |
||
276 | UNTIL (c1 # c2) OR (c1 = 0X) |
||
277 | |||
278 | RETURN c1 = c2 |
||
279 | END streq; |
||
280 | |||
6613 | leency | 281 | BEGIN |
7597 | akron1 | 282 | adr := 0; |
283 | IF (lib # 0) & (name # "") THEN |
||
284 | cur := lib; |
||
285 | REPEAT |
||
286 | SYSTEM.GET(cur, procname); |
||
287 | INC(cur, 8) |
||
288 | UNTIL (procname = 0) OR streq(procname, SYSTEM.ADR(name[0])); |
||
289 | IF procname # 0 THEN |
||
290 | SYSTEM.GET(cur - 4, adr) |
||
291 | END |
||
6613 | leency | 292 | END |
7597 | akron1 | 293 | |
294 | RETURN adr |
||
6613 | leency | 295 | END GetProcAdr; |
296 | |||
7597 | akron1 | 297 | |
298 | PROCEDURE init (dll: INTEGER); |
||
299 | VAR |
||
300 | lib_init: INTEGER; |
||
6613 | leency | 301 | BEGIN |
7597 | akron1 | 302 | lib_init := GetProcAdr("lib_init", dll); |
303 | IF lib_init # 0 THEN |
||
304 | DLL_INIT(lib_init) |
||
305 | END; |
||
306 | lib_init := GetProcAdr("START", dll); |
||
307 | IF lib_init # 0 THEN |
||
308 | DLL_INIT(lib_init) |
||
309 | END |
||
6613 | leency | 310 | END init; |
311 | |||
312 | |||
9646 | akron1 | 313 | PROCEDURE OutChar* (c: CHAR); |
314 | BEGIN |
||
315 | sysfunc3(63, 1, ORD(c)) |
||
316 | END OutChar; |
||
317 | |||
318 | |||
319 | PROCEDURE OutLn*; |
||
320 | BEGIN |
||
321 | OutChar(0DX); |
||
322 | OutChar(0AX) |
||
323 | END OutLn; |
||
324 | |||
325 | |||
326 | PROCEDURE OutString (s: ARRAY OF CHAR); |
||
327 | VAR |
||
328 | i: INTEGER; |
||
329 | BEGIN |
||
330 | i := 0; |
||
331 | WHILE (i < LEN(s)) & (s[i] # 0X) DO |
||
332 | OutChar(s[i]); |
||
333 | INC(i) |
||
334 | END |
||
335 | END OutString; |
||
336 | |||
337 | |||
338 | PROCEDURE imp_error (lib, proc: STRING); |
||
339 | BEGIN |
||
340 | OutString("import error: "); |
||
341 | IF proc = "" THEN |
||
342 | OutString("can't load '") |
||
343 | ELSE |
||
344 | OutString("not found '"); OutString(proc); OutString("' in '") |
||
345 | END; |
||
346 | OutString(lib); |
||
347 | OutString("'" + 0DX + 0AX) |
||
348 | END imp_error; |
||
349 | |||
350 | |||
7597 | akron1 | 351 | PROCEDURE GetStr (adr, i: INTEGER; VAR str: STRING); |
352 | VAR |
||
353 | c: CHAR; |
||
354 | BEGIN |
||
6613 | leency | 355 | REPEAT |
7597 | akron1 | 356 | SYSTEM.GET(adr, c); INC(adr); |
357 | str[i] := c; INC(i) |
||
6613 | leency | 358 | UNTIL c = 0X |
7597 | akron1 | 359 | END GetStr; |
6613 | leency | 360 | |
7597 | akron1 | 361 | |
9646 | akron1 | 362 | PROCEDURE [stdcall-] dll_Load* (import_table: INTEGER): INTEGER; |
9577 | akron1 | 363 | CONST |
364 | path = "/sys/lib/"; |
||
7597 | akron1 | 365 | VAR |
9646 | akron1 | 366 | imp, lib, exp, proc, pathLen: INTEGER; |
7597 | akron1 | 367 | procname, libname: STRING; |
6613 | leency | 368 | BEGIN |
7597 | akron1 | 369 | SYSTEM.CODE(060H); (* pusha *) |
9577 | akron1 | 370 | libname := path; |
371 | pathLen := LENGTH(libname); |
||
9646 | akron1 | 372 | |
373 | SYSTEM.GET(import_table, imp); |
||
374 | WHILE imp # 0 DO |
||
375 | SYSTEM.GET(import_table + 4, lib); |
||
376 | GetStr(lib, pathLen, libname); |
||
377 | exp := sysfunc3(68, 19, SYSTEM.ADR(libname[0])); |
||
378 | IF exp = 0 THEN |
||
379 | imp_error(libname, "") |
||
7597 | akron1 | 380 | ELSE |
381 | REPEAT |
||
382 | SYSTEM.GET(imp, proc); |
||
383 | IF proc # 0 THEN |
||
384 | GetStr(proc, 0, procname); |
||
385 | proc := GetProcAdr(procname, exp); |
||
386 | IF proc # 0 THEN |
||
9646 | akron1 | 387 | SYSTEM.PUT(imp, proc) |
7597 | akron1 | 388 | ELSE |
9646 | akron1 | 389 | proc := 1; |
390 | imp_error(libname, procname) |
||
391 | END; |
||
392 | INC(imp, 4) |
||
7597 | akron1 | 393 | END |
394 | UNTIL proc = 0; |
||
9646 | akron1 | 395 | init(exp) |
396 | END; |
||
397 | INC(import_table, 8); |
||
398 | SYSTEM.GET(import_table, imp); |
||
6613 | leency | 399 | END; |
9646 | akron1 | 400 | |
7597 | akron1 | 401 | SYSTEM.CODE(061H) (* popa *) |
9646 | akron1 | 402 | RETURN 0 |
6613 | leency | 403 | END dll_Load; |
404 | |||
7597 | akron1 | 405 | |
406 | PROCEDURE [stdcall] dll_Init (entry: INTEGER); |
||
6613 | leency | 407 | BEGIN |
7597 | akron1 | 408 | SYSTEM.CODE(060H); (* pusha *) |
409 | IF entry # 0 THEN |
||
410 | dll_init2(SYSTEM.ADR(malloc), SYSTEM.ADR(free), SYSTEM.ADR(realloc), SYSTEM.ADR(dll_Load), entry) |
||
411 | END; |
||
412 | SYSTEM.CODE(061H); (* popa *) |
||
6613 | leency | 413 | END dll_Init; |
414 | |||
7597 | akron1 | 415 | |
416 | PROCEDURE LoadLib* (name: ARRAY OF CHAR): INTEGER; |
||
417 | VAR |
||
418 | Lib: INTEGER; |
||
6613 | leency | 419 | BEGIN |
7597 | akron1 | 420 | DLL_INIT := dll_Init; |
421 | Lib := sysfunc3(68, 19, SYSTEM.ADR(name[0])); |
||
422 | IF Lib # 0 THEN |
||
423 | init(Lib) |
||
424 | END |
||
425 | RETURN Lib |
||
6613 | leency | 426 | END LoadLib; |
427 | |||
7597 | akron1 | 428 | |
9646 | akron1 | 429 | PROCEDURE _init* (import_table: INTEGER); |
7597 | akron1 | 430 | BEGIN |
431 | DLL_INIT := dll_Init; |
||
9646 | akron1 | 432 | dll_Load(import_table) |
7597 | akron1 | 433 | END _init; |
434 | |||
435 | |||
7983 | leency | 436 | END KOSAPI.> |