Subversion Repositories Kolibri OS

Rev

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

Rev Author Line No. Line
7597 akron1 1
(*
2
    BSD 2-Clause License
6613 leency 3
 
7597 akron1 4
    Copyright (c) 2018, 2019, Anton Krotov
5
    All rights reserved.
6613 leency 6
*)
7
 
8
MODULE Compiler;
9
 
7597 akron1 10
IMPORT ST := STATEMENTS, PARS, UTILS, PATHS, C := CONSOLE, ERRORS, STRINGS, mConst := CONSTANTS, WRITER;
6613 leency 11
 
12
 
7597 akron1 13
PROCEDURE Target (s: ARRAY OF CHAR): INTEGER;
14
VAR
15
    res: INTEGER;
6613 leency 16
 
7597 akron1 17
BEGIN
18
    IF s = mConst.Target_sConsole THEN
19
        res := mConst.Target_iConsole
20
    ELSIF s = mConst.Target_sGUI THEN
21
        res := mConst.Target_iGUI
22
    ELSIF s = mConst.Target_sDLL THEN
23
        res := mConst.Target_iDLL
24
    ELSIF s = mConst.Target_sKolibri THEN
25
        res := mConst.Target_iKolibri
26
    ELSIF s = mConst.Target_sObject THEN
27
        res := mConst.Target_iObject
28
    ELSIF s = mConst.Target_sConsole64 THEN
29
        res := mConst.Target_iConsole64
30
    ELSIF s = mConst.Target_sGUI64 THEN
31
        res := mConst.Target_iGUI64
32
    ELSIF s = mConst.Target_sDLL64 THEN
33
        res := mConst.Target_iDLL64
34
    ELSIF s = mConst.Target_sELF32 THEN
35
        res := mConst.Target_iELF32
36
    ELSIF s = mConst.Target_sELF64 THEN
37
        res := mConst.Target_iELF64
38
    ELSE
39
        res := 0
40
    END
6613 leency 41
 
7597 akron1 42
    RETURN res
43
END Target;
6613 leency 44
 
45
 
7597 akron1 46
PROCEDURE keys (VAR StackSize, BaseAddress, Version: INTEGER; VAR pic: BOOLEAN; VAR checking: SET);
6613 leency 47
VAR
7597 akron1 48
    param: PARS.PATH;
49
    i, j:  INTEGER;
50
    end:   BOOLEAN;
51
    value: INTEGER;
52
    minor,
53
    major: INTEGER;
6613 leency 54
 
55
BEGIN
7597 akron1 56
    end := FALSE;
57
    i := 4;
58
    REPEAT
59
        UTILS.GetArg(i, param);
6613 leency 60
 
7597 akron1 61
        IF param = "-stk" THEN
62
            INC(i);
63
            UTILS.GetArg(i, param);
64
            IF STRINGS.StrToInt(param, value) & (1 <= value) & (value <= 32) THEN
65
                StackSize := value
66
            END;
67
            IF param[0] = "-" THEN
68
                DEC(i)
69
            END
6613 leency 70
 
7597 akron1 71
        ELSIF param = "-base" THEN
72
            INC(i);
73
            UTILS.GetArg(i, param);
74
            IF STRINGS.StrToInt(param, value) THEN
75
                BaseAddress := ((value DIV 64) * 64) * 1024
76
            END;
77
            IF param[0] = "-" THEN
78
                DEC(i)
79
            END
6613 leency 80
 
7597 akron1 81
        ELSIF param = "-nochk" THEN
82
            INC(i);
83
            UTILS.GetArg(i, param);
6613 leency 84
 
7597 akron1 85
            IF param[0] = "-" THEN
86
                DEC(i)
87
            ELSE
88
                j := 0;
89
                WHILE param[j] # 0X DO
6613 leency 90
 
7597 akron1 91
                    IF    param[j] = "p" THEN
92
                        EXCL(checking, ST.chkPTR)
93
                    ELSIF param[j] = "t" THEN
94
                        EXCL(checking, ST.chkGUARD)
95
                    ELSIF param[j] = "i" THEN
96
                        EXCL(checking, ST.chkIDX)
97
                    ELSIF param[j] = "b" THEN
98
                        EXCL(checking, ST.chkBYTE)
99
                    ELSIF param[j] = "c" THEN
100
                        EXCL(checking, ST.chkCHR)
101
                    ELSIF param[j] = "w" THEN
102
                        EXCL(checking, ST.chkWCHR)
103
                    ELSIF param[j] = "r" THEN
104
                        EXCL(checking, ST.chkCHR);
105
                        EXCL(checking, ST.chkWCHR);
106
                        EXCL(checking, ST.chkBYTE)
107
                    ELSIF param[j] = "a" THEN
108
                        checking := {}
109
                    END;
6613 leency 110
 
7597 akron1 111
                    INC(j)
112
                END
113
            END
6613 leency 114
 
7597 akron1 115
        ELSIF param = "-ver" THEN
116
            INC(i);
117
            UTILS.GetArg(i, param);
118
            IF STRINGS.StrToVer(param, major, minor) THEN
119
                Version := major * 65536 + minor
120
            END;
121
            IF param[0] = "-" THEN
122
                DEC(i)
123
            END
6613 leency 124
 
7597 akron1 125
        ELSIF param = "-pic" THEN
126
            pic := TRUE
6613 leency 127
 
7597 akron1 128
        ELSIF param = "" THEN
129
            end := TRUE
6613 leency 130
 
7107 akron1 131
        ELSE
7597 akron1 132
            ERRORS.error3("bad parameter: ", param, "")
7107 akron1 133
        END;
6613 leency 134
 
7597 akron1 135
        INC(i)
136
    UNTIL end
6613 leency 137
 
7597 akron1 138
END keys;
6613 leency 139
 
140
 
7597 akron1 141
PROCEDURE main;
142
VAR
143
    path:       PARS.PATH;
144
    inname:     PARS.PATH;
145
    ext:        PARS.PATH;
146
    app_path:   PARS.PATH;
147
    lib_path:   PARS.PATH;
148
    modname:    PARS.PATH;
149
    outname:    PARS.PATH;
150
    param:      PARS.PATH;
151
    temp:       PARS.PATH;
6613 leency 152
 
7597 akron1 153
    target:     INTEGER;
6613 leency 154
 
7597 akron1 155
    time:       INTEGER;
6613 leency 156
 
7597 akron1 157
    StackSize,
158
    Version,
159
    BaseAdr:    INTEGER;
160
    pic:        BOOLEAN;
161
    checking:   SET;
6613 leency 162
 
7597 akron1 163
    bits64: BOOLEAN;
6613 leency 164
 
165
BEGIN
7597 akron1 166
    StackSize := 2;
167
    Version := 65536;
168
    pic := FALSE;
169
    checking := ST.chkALL;
6613 leency 170
 
7597 akron1 171
    PATHS.GetCurrentDirectory(app_path);
172
    lib_path := app_path;
6613 leency 173
 
7597 akron1 174
    UTILS.GetArg(1, inname);
6613 leency 175
 
7597 akron1 176
    IF inname = "" THEN
177
        C.String("Akron Oberon-07/16 Compiler v"); C.Int(mConst.vMajor); C.String("."); C.Int2(mConst.vMinor);
178
            C.String(" ("); C.Int(UTILS.bit_depth); C.StringLn("-bit)"); C.Ln;
179
        C.StringLn("Usage: Compiler 
[optional settings]"); C.Ln;
180
        IF UTILS.bit_depth = 64 THEN
181
            C.StringLn('target = console | gui | dll | console64 | gui64 | dll64 | kos | obj | elfexe | elfexe64'); C.Ln;
182
        ELSIF UTILS.bit_depth = 32 THEN
183
            C.StringLn('target = console | gui | dll | kos | obj | elfexe'); C.Ln;
7107 akron1 184
        END;
7597 akron1 185
        C.StringLn("optional settings:"); C.Ln;
186
        C.StringLn("  -stk             set size of stack in megabytes"); C.Ln;
187
        C.StringLn("  -base 
set base address of image in kilobytes"); C.Ln;
188
        C.StringLn('  -ver      set version of program'); C.Ln;
189
        C.StringLn('  -nochk <"ptibcwra">    disable runtime checking (pointers, types, indexes,');
190
        C.StringLn('                         BYTE, CHR, WCHR)'); C.Ln;
191
        UTILS.Exit(0)
6613 leency 192
    END;
193
 
7597 akron1 194
    PATHS.split(inname, path, modname, ext);
6613 leency 195
 
7597 akron1 196
    IF ext # mConst.FILE_EXT THEN
197
        ERRORS.error3('inputfile name extension must be "', mConst.FILE_EXT, '"')
6613 leency 198
    END;
7597 akron1 199
    IF PATHS.isRelative(path) THEN
200
        PATHS.RelPath(app_path, path, temp);
201
        path := temp
6613 leency 202
    END;
203
 
7597 akron1 204
    UTILS.GetArg(2, outname);
205
    IF outname = "" THEN
206
        ERRORS.error1("not enough parameters")
6613 leency 207
    END;
7597 akron1 208
    IF PATHS.isRelative(outname) THEN
209
        PATHS.RelPath(app_path, outname, temp);
210
        outname := temp
6613 leency 211
    END;
7597 akron1 212
 
213
    UTILS.GetArg(3, param);
214
    IF param = "" THEN
215
        ERRORS.error1("not enough parameters")
6613 leency 216
    END;
217
 
7597 akron1 218
    target := Target(param);
6613 leency 219
 
7597 akron1 220
    IF target = 0 THEN
221
        ERRORS.error1("bad parameter ")
6613 leency 222
    END;
223
 
7597 akron1 224
    bits64 := target IN {mConst.Target_iConsole64, mConst.Target_iGUI64, mConst.Target_iDLL64, mConst.Target_iELF64};
6613 leency 225
 
7597 akron1 226
    IF bits64 THEN
227
        IF UTILS.bit_depth = 32 THEN
228
            ERRORS.error1("bad parameter ")
229
        END;
230
        PARS.init(64, target)
231
    ELSE
232
        PARS.init(32, target)
6613 leency 233
    END;
234
 
7597 akron1 235
    PARS.program.dll := target IN {mConst.Target_iDLL, mConst.Target_iObject, mConst.Target_iDLL64};
236
    PARS.program.obj := target = mConst.Target_iObject;
6613 leency 237
 
7597 akron1 238
    STRINGS.append(lib_path, "lib");
239
    STRINGS.append(lib_path, UTILS.slash);
6613 leency 240
 
7597 akron1 241
    IF target IN {mConst.Target_iConsole, mConst.Target_iGUI, mConst.Target_iDLL} THEN
242
        IF target = mConst.Target_iDLL THEN
243
            BaseAdr := 10000000H
7107 akron1 244
        ELSE
7597 akron1 245
            BaseAdr := 400000H
7107 akron1 246
        END;
7597 akron1 247
        STRINGS.append(lib_path, "Windows32")
6613 leency 248
 
7597 akron1 249
    ELSIF target IN {mConst.Target_iKolibri, mConst.Target_iObject} THEN
250
        STRINGS.append(lib_path, "KolibriOS")
6613 leency 251
 
7597 akron1 252
    ELSIF target = mConst.Target_iELF32 THEN
253
        STRINGS.append(lib_path, "Linux32")
6613 leency 254
 
7597 akron1 255
    ELSIF target = mConst.Target_iELF64 THEN
256
        STRINGS.append(lib_path, "Linux64")
6613 leency 257
 
7597 akron1 258
    ELSIF target IN {mConst.Target_iConsole64, mConst.Target_iGUI64, mConst.Target_iDLL64} THEN
259
        STRINGS.append(lib_path, "Windows64")
6613 leency 260
 
261
    END;
262
 
7597 akron1 263
    STRINGS.append(lib_path, UTILS.slash);
6613 leency 264
 
7597 akron1 265
    keys(StackSize, BaseAdr, Version, pic, checking);
6613 leency 266
 
7597 akron1 267
    ST.compile(path, lib_path, modname, outname, target, Version, StackSize, BaseAdr, pic, checking);
6613 leency 268
 
7597 akron1 269
    time := UTILS.GetTickCount() - UTILS.time;
6613 leency 270
 
7597 akron1 271
    C.Int(time DIV 100); C.String("."); C.Int2(time MOD 100); C.String(" sec, ");
272
    C.Int(WRITER.counter); C.StringLn(" bytes");
6613 leency 273
 
7597 akron1 274
    UTILS.Exit(0)
275
END main;
276
 
277
 
6613 leency 278
BEGIN
7597 akron1 279
    main
6613 leency 280
END Compiler.