Subversion Repositories Kolibri OS

Rev

Rev 6613 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
7107 akron1 1
(*
2
    Copyright 2016, 2017 Anton Krotov
6613 leency 3
 
4
    This program is free software: you can redistribute it and/or modify
5
    it under the terms of the GNU Lesser General Public License as published by
6
    the Free Software Foundation, either version 3 of the License, or
7
    (at your option) any later version.
8
 
9
    This program is distributed in the hope that it will be useful,
10
    but WITHOUT ANY WARRANTY; without even the implied warranty of
11
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
    GNU Lesser General Public License for more details.
13
 
14
    You should have received a copy of the GNU Lesser General Public License
15
    along with this program.  If not, see .
16
*)
17
 
18
MODULE RTL;
19
 
20
IMPORT sys := SYSTEM, API;
21
 
22
TYPE
23
 
24
  IntArray = ARRAY 2048 OF INTEGER;
25
  STRING = ARRAY 2048 OF CHAR;
26
  PROC = PROCEDURE;
27
 
28
VAR
29
 
30
  SelfName, rtab: INTEGER; CloseProc: PROC;
7107 akron1 31
  init: BOOLEAN;
32
  main_thread_id: INTEGER;
6613 leency 33
 
34
PROCEDURE [stdcall] _halt*(n: INTEGER);
35
BEGIN
36
  API.ExitProcess(n)
37
END _halt;
38
 
39
PROCEDURE [stdcall] _newrec*(size, t: INTEGER; VAR ptr: INTEGER);
40
BEGIN
41
  ptr := API._NEW(size);
42
  IF ptr # 0 THEN
43
    sys.PUT(ptr, t);
44
    INC(ptr, 4)
45
  END
46
END _newrec;
47
 
48
PROCEDURE [stdcall] _disprec*(VAR ptr: INTEGER);
49
BEGIN
50
  IF ptr # 0 THEN
51
    ptr := API._DISPOSE(ptr - 4)
52
  END
53
END _disprec;
54
 
55
PROCEDURE [stdcall] _rset*(y, x: INTEGER);
56
BEGIN
57
  sys.CODE("8B45088B4D0C3BC87F0A83F91F760B83F81F760633C0C9C2080083F9007D0233C983F81F7E05B81F000000BA000000802BC8F7D9D3FA83E81F8BC8F7D9D3EA8BC2C9C20800")
58
END _rset;
59
 
60
PROCEDURE [stdcall] _inset*(y, x: INTEGER);
61
BEGIN
62
  sys.CODE("8B45088B4D0C83F91F7709D3E883E001C9C20800C933C0C20800")
63
END _inset;
64
 
65
PROCEDURE [stdcall] _checktype*(table, t, r: INTEGER);
66
BEGIN
67
  table := rtab;
68
  sys.CODE("8B450C8B4D1085C975076A0158C9C20C008B51FC8B4D083BD0740D85D27409C1E20203D18B12EBEF33C93BC20F94C18BC1C9C20C00")
69
END _checktype;
70
 
71
PROCEDURE [stdcall] _savearr*(size, source, dest: INTEGER);
72
BEGIN
73
  sys.CODE("9CFC8BD78BC68B7D108B750C8B4D08F3A48BFA8BF09D")
74
END _savearr;
75
 
76
PROCEDURE [stdcall] _saverec*(dyn, stat, size, source, dest: INTEGER): BOOLEAN;
77
VAR res: BOOLEAN;
78
BEGIN
79
  res := dyn = stat;
80
  IF res THEN
81
    _savearr(size, source, dest)
82
  END
83
  RETURN res
84
END _saverec;
85
 
86
PROCEDURE [stdcall] _arrayidx*(Dim: INTEGER; VAR Arr: IntArray; bsize, idx, c: INTEGER);
87
VAR i, m: INTEGER;
88
BEGIN
89
  m := bsize * idx;
90
  FOR i := 4 TO Dim + 2 DO
91
    m := m * Arr[i]
92
  END;
93
  IF (Arr[3] > idx) & (idx >= 0) THEN
94
    Arr[3] := c + m
95
  ELSE
96
    Arr[3] := 0
97
  END
98
END _arrayidx;
99
 
100
PROCEDURE [stdcall] _arrayidx1*(VAR Arr: IntArray; bsize, idx, c: INTEGER);
101
BEGIN
102
  IF (Arr[3] > idx) & (idx >= 0) THEN
103
    Arr[3] := bsize * idx + c
104
  ELSE
105
    Arr[3] := 0
106
  END
107
END _arrayidx1;
108
 
109
PROCEDURE [stdcall] _arrayrot*(m, n: INTEGER; VAR Arr: IntArray);
110
VAR i, j, t: INTEGER;
111
BEGIN
112
  FOR i := 1 TO n DO
113
    t := Arr[0];
114
    FOR j := 0 TO m + n - 1 DO
115
      Arr[j] := Arr[j + 1]
116
    END;
117
    Arr[m + n] := t
118
  END
119
END _arrayrot;
120
 
121
PROCEDURE [stdcall] _length*(s: ARRAY OF CHAR): INTEGER;
122
BEGIN
123
  sys.CODE("8B4508");     //  mov     eax, [ebp + 08h]
124
  sys.CODE("8B4D0C");     //  mov     ecx, [ebp + 0Ch]
125
  sys.CODE("48");         //  dec     eax
7107 akron1 126
                          //  L1:
6613 leency 127
  sys.CODE("40");         //  inc     eax
128
  sys.CODE("803800");     //  cmp     byte ptr [eax], 0
129
  sys.CODE("7403");       //  jz      L2
130
  sys.CODE("E2F8");       //  loop    L1
131
  sys.CODE("40");         //  inc     eax
7107 akron1 132
                          //  L2:
6613 leency 133
  sys.CODE("2B4508");     //  sub     eax, [ebp + 08h]
134
  sys.CODE("C9");         //  leave
135
  sys.CODE("C20800");     //  ret     08h
136
  RETURN 0
137
END _length;
138
 
139
PROCEDURE [stdcall] _strcopy*(b, blen, a, alen: INTEGER);
140
BEGIN
7107 akron1 141
  _savearr(MIN(alen, blen), a, b);
6613 leency 142
  IF blen > alen THEN
143
    sys.PUT(b + alen, 0X)
144
  END
145
END _strcopy;
146
 
147
PROCEDURE [stdcall] _strcmp*(op: INTEGER; b, a: ARRAY OF CHAR): BOOLEAN;
148
VAR i: INTEGER; Res: BOOLEAN;
149
BEGIN
7107 akron1 150
  i := API.strncmp(sys.ADR(a), sys.ADR(b), MIN(LEN(a), LEN(b)));
6613 leency 151
  IF i = 0 THEN
152
    i := _length(a) - _length(b)
153
  END;
154
  CASE op OF
155
  |0: Res := i = 0
156
  |1: Res := i # 0
157
  |2: Res := i < 0
158
  |3: Res := i > 0
159
  |4: Res := i <= 0
160
  |5: Res := i >= 0
161
  ELSE
162
  END
163
  RETURN Res
164
END _strcmp;
165
 
166
PROCEDURE [stdcall] _lstrcmp*(op: INTEGER; b: CHAR; a: ARRAY OF CHAR): BOOLEAN;
167
VAR s: ARRAY 2 OF CHAR;
168
BEGIN
169
  s[0] := b;
170
  s[1] := 0X;
171
  RETURN _strcmp(op, s, a)
172
END _lstrcmp;
173
 
174
PROCEDURE [stdcall] _rstrcmp*(op: INTEGER; b: ARRAY OF CHAR; a: CHAR): BOOLEAN;
175
VAR s: ARRAY 2 OF CHAR;
176
BEGIN
177
  s[0] := a;
178
  s[1] := 0X;
179
  RETURN _strcmp(op, b, s)
180
END _rstrcmp;
181
 
182
PROCEDURE Int(x: INTEGER; VAR str: STRING);
183
VAR i, a, b: INTEGER; c: CHAR;
184
BEGIN
185
  i := 0;
186
  a := 0;
187
  REPEAT
188
    str[i] := CHR(x MOD 10 + ORD("0"));
189
    x := x DIV 10;
190
    INC(i)
191
  UNTIL x = 0;
192
  b := i - 1;
193
  WHILE a < b DO
194
    c := str[a];
195
    str[a] := str[b];
196
    str[b] := c;
197
    INC(a);
198
    DEC(b)
199
  END;
200
  str[i] := 0X
201
END Int;
202
 
203
PROCEDURE [stdcall] _assrt*(code, m: INTEGER; modname: STRING; line: INTEGER);
204
VAR msg, int: STRING; pos, n: INTEGER;
205
 
206
  PROCEDURE StrAppend(s: STRING);
207
  VAR i, n: INTEGER;
208
  BEGIN
209
    n := LEN(s);
210
    i := 0;
211
    WHILE (i < n) & (s[i] # 0X) DO
212
      msg[pos] := s[i];
213
      INC(pos);
214
      INC(i)
215
    END
216
  END StrAppend;
217
 
218
BEGIN
219
  pos := 0;
220
  n := line MOD 16;
221
  line := line DIV 16;
222
  CASE n OF
223
  |1: StrAppend("assertion failure")
224
  |2: StrAppend("variable of a procedure type has NIL as value")
225
  |3: StrAppend("typeguard error")
226
  |4: StrAppend("inadmissible dynamic type")
227
  |5: StrAppend("index check error")
228
  |6: StrAppend("NIL pointer dereference")
229
  |7: StrAppend("invalid value in case statement")
230
  |8: StrAppend("division by zero")
231
  ELSE
232
  END;
233
  StrAppend(0DX);
234
  StrAppend(0AX);
235
  StrAppend("module ");
236
  StrAppend(modname);
237
  StrAppend(0DX);
238
  StrAppend(0AX);
239
  StrAppend("line ");
240
  Int(line, int);
241
  StrAppend(int);
242
  IF m = 2 THEN
243
    StrAppend(0DX);
244
    StrAppend(0AX);
245
    StrAppend("code ");
246
    Int(code, int);
247
    StrAppend(int)
248
  END;
7107 akron1 249
  IF API.GetCurrentThreadId() = main_thread_id THEN
250
    API.ExitProcess(0)
251
  ELSE
252
    API.ExitThread(0)
253
  END
6613 leency 254
END _assrt;
255
 
256
PROCEDURE [stdcall] _close*;
257
BEGIN
258
  IF CloseProc # NIL THEN
259
    CloseProc
260
  END
261
END _close;
262
 
263
PROCEDURE [stdcall] _init*(self, rec, gsize, gadr, esp: INTEGER);
264
BEGIN
7107 akron1 265
  IF ~init THEN
266
    API.zeromem(gsize, gadr);
267
    init := TRUE;
268
    API.init(esp);
269
    main_thread_id := API.GetCurrentThreadId();
270
    SelfName := self;
271
    rtab := rec;
272
    CloseProc := NIL
273
  END
6613 leency 274
END _init;
275
 
276
PROCEDURE SetClose*(proc: PROC);
277
BEGIN
278
  CloseProc := proc
279
END SetClose;
280
 
281
END RTL.