Subversion Repositories Kolibri OS

Rev

Rev 7983 | Go to most recent revision | Show entire file | Regard whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 7983 Rev 8097
Line 32... Line 32...
32
    END;
32
    END;
Line 33... Line 33...
33
 
33
 
Line 34... Line 34...
34
    EXPR* = RECORD
34
    EXPR* = RECORD
35
 
35
 
36
        obj*:         INTEGER;
36
        obj*:         INTEGER;
37
        type*:        PROG.TYPE_;
37
        _type*:       PROG._TYPE;
38
        value*:       ARITH.VALUE;
38
        value*:       ARITH.VALUE;
39
        stproc*:      INTEGER;
39
        stproc*:      INTEGER;
Line 40... Line 40...
40
        readOnly*:    BOOLEAN;
40
        readOnly*:    BOOLEAN;
Line 41... Line 41...
41
        ident*:       PROG.IDENT
41
        ident*:       PROG.IDENT
42
 
42
 
43
    END;
43
    END;
Line 44... Line 44...
44
 
44
 
Line 45... Line 45...
45
    STATPROC  = PROCEDURE (parser: PARSER);
45
    STATPROC  = PROCEDURE (parser: PARSER);
46
    EXPRPROC  = PROCEDURE (parser: PARSER; VAR e: EXPR);
46
    EXPRPROC  = PROCEDURE (parser: PARSER; VAR e: EXPR);
Line 72... Line 72...
72
    END;
72
    END;
Line 73... Line 73...
73
 
73
 
Line 74... Line -...
74
 
-
 
75
VAR
-
 
76
 
74
 
Line 77... Line 75...
77
    program*: PROG.PROGRAM;
75
VAR
Line 131... Line 129...
131
    errno: INTEGER;
129
    errno: INTEGER;
Line 132... Line 130...
132
 
130
 
133
BEGIN
131
BEGIN
134
    SCAN.Next(parser.scanner, parser.lex);
132
    SCAN.Next(parser.scanner, parser.lex);
135
    errno := parser.lex.error;
133
    errno := parser.lex.error;
136
    IF (errno = 0) & (TARGETS.CPU = TARGETS.cpuMSP430) THEN
134
    IF errno = 0 THEN
137
        IF parser.lex.sym = SCAN.lxFLOAT THEN
135
        IF (TARGETS.RealSize = 0) & (parser.lex.sym = SCAN.lxFLOAT) THEN
138
            errno := -SCAN.lxERROR13
136
            errno := -SCAN.lxERROR13
139
        ELSIF (parser.lex.sym = SCAN.lxCHAR) & (parser.lex.value.typ = ARITH.tWCHAR) THEN
137
        ELSIF (TARGETS.BitDepth = 16) & (parser.lex.sym = SCAN.lxCHAR) & (parser.lex.value.typ = ARITH.tWCHAR) THEN
140
            errno := -SCAN.lxERROR10
138
            errno := -SCAN.lxERROR10
141
        END
139
        END
Line 142... Line 140...
142
    END;
140
    END;
Line 182... Line 180...
182
        |SCAN.lxLROUND:  err := 64
180
        |SCAN.lxLROUND:  err := 64
183
        |SCAN.lxEQ:      err := 32
181
        |SCAN.lxEQ:      err := 32
184
        |SCAN.lxSEMI:    err := 24
182
        |SCAN.lxSEMI:    err := 24
185
        |SCAN.lxRETURN:  err := 38
183
        |SCAN.lxRETURN:  err := 38
186
        |SCAN.lxMODULE:  err := 21
184
        |SCAN.lxMODULE:  err := 21
187
        |SCAN.lxSTRING:  err := 66
-
 
188
        END;
185
        END;
Line 189... Line 186...
189
 
186
 
190
        check1(FALSE, parser, err)
187
        check1(FALSE, parser, err)
191
    END
188
    END
Line 225... Line 222...
225
 
222
 
Line 226... Line 223...
226
        Next(parser);
223
        Next(parser);
227
 
224
 
228
        IF (parser.sym = SCAN.lxCOMMA) OR (parser.sym = SCAN.lxSEMI) THEN
225
        IF (parser.sym = SCAN.lxCOMMA) OR (parser.sym = SCAN.lxSEMI) THEN
Line 229... Line 226...
229
            alias := FALSE;
226
            alias := FALSE;
230
            unit := PROG.getUnit(program, name);
227
            unit := PROG.getUnit(name);
231
 
228
 
232
            IF unit # NIL THEN
229
            IF unit # NIL THEN
Line 248... Line 245...
248
 
245
 
249
                parser2.parse(parser2);
246
                parser2.parse(parser2);
250
                unit := parser2.unit;
247
                unit := parser2.unit;
251
                destroy(parser2)
248
                destroy(parser2)
252
            END;
249
            END;
253
            IF unit = program.sysunit THEN
250
            IF unit = PROG.program.sysunit THEN
254
                parser.unit.sysimport := TRUE
251
                parser.unit.sysimport := TRUE
255
            END;
252
            END;
Line 256... Line 253...
256
            ident.unit := unit
253
            ident.unit := unit
Line 348... Line 345...
348
    check(e.obj = eCONST, pos, 62);
345
    check(e.obj = eCONST, pos, 62);
349
    v := e.value
346
    v := e.value
350
END ConstExpression;
347
END ConstExpression;
Line 351... Line 348...
351
 
348
 
352
 
349
 
353
PROCEDURE FieldList (parser: PARSER; rec: PROG.TYPE_);
350
PROCEDURE FieldList (parser: PARSER; rec: PROG._TYPE);
354
VAR
351
VAR
355
    name:   SCAN.IDENT;
352
    name:   SCAN.IDENT;
Line 385... Line 382...
385
    END
382
    END
Line 386... Line 383...
386
 
383
 
Line 387... Line 384...
387
END FieldList;
384
END FieldList;
388
 
385
 
389
 
386
 
Line 390... Line 387...
390
PROCEDURE FormalParameters (parser: PARSER; type: PROG.TYPE_);
387
PROCEDURE FormalParameters (parser: PARSER; _type: PROG._TYPE);
391
VAR
388
VAR
392
    ident: PROG.IDENT;
389
    ident: PROG.IDENT;
393
 
390
 
394
 
391
 
395
    PROCEDURE FPSection (parser: PARSER; type: PROG.TYPE_);
392
    PROCEDURE FPSection (parser: PARSER; _type: PROG._TYPE);
396
    VAR
393
    VAR
Line 397... Line 394...
397
        ident:   PROG.IDENT;
394
        ident:   PROG.IDENT;
398
        exit:    BOOLEAN;
395
        exit:    BOOLEAN;
399
        vPar:    BOOLEAN;
396
        vPar:    BOOLEAN;
400
        dim:     INTEGER;
397
        dim:     INTEGER;
Line 408... Line 405...
408
 
405
 
409
        checklex(parser, SCAN.lxIDENT);
406
        checklex(parser, SCAN.lxIDENT);
Line 410... Line 407...
410
        exit := FALSE;
407
        exit := FALSE;
411
 
408
 
412
        WHILE (parser.sym = SCAN.lxIDENT) & ~exit DO
409
        WHILE (parser.sym = SCAN.lxIDENT) & ~exit DO
413
            check1(PROG.addParam(type, parser.lex.ident, vPar), parser, 30);
410
            check1(PROG.addParam(_type, parser.lex.ident, vPar), parser, 30);
414
            Next(parser);
411
            Next(parser);
415
            IF parser.sym = SCAN.lxCOMMA THEN
412
            IF parser.sym = SCAN.lxCOMMA THEN
416
                ExpectSym(parser, SCAN.lxIDENT)
413
                ExpectSym(parser, SCAN.lxIDENT)
Line 425... Line 422...
425
                END;
422
                END;
426
                checklex(parser, SCAN.lxIDENT);
423
                checklex(parser, SCAN.lxIDENT);
427
                ident := QIdent(parser, FALSE);
424
                ident := QIdent(parser, FALSE);
428
                check1(ident.typ = PROG.idTYPE, parser, 68);
425
                check1(ident.typ = PROG.idTYPE, parser, 68);
Line 429... Line 426...
429
 
426
 
430
                t0 := ident.type;
427
                t0 := ident._type;
Line 431... Line 428...
431
                t1 := t0;
428
                t1 := t0;
432
 
429
 
433
                WHILE dim > 0 DO
430
                WHILE dim > 0 DO
434
                    t1 := PROG.enterType(program, PROG.tARRAY, -1, 0, parser.unit);
431
                    t1 := PROG.enterType(PROG.tARRAY, -1, 0, parser.unit);
435
                    t1.base := t0;
432
                    t1.base := t0;
436
                    t0 := t1;
433
                    t0 := t1;
Line 437... Line 434...
437
                    DEC(dim)
434
                    DEC(dim)
438
                END;
435
                END;
439
 
436
 
440
                PROG.setParams(type, t1);
437
                PROG.setParams(_type, t1);
441
                Next(parser);
438
                Next(parser);
442
                exit := TRUE
439
                exit := TRUE
Line 452... Line 449...
452
    IF parser.sym = SCAN.lxLROUND THEN
449
    IF parser.sym = SCAN.lxLROUND THEN
Line 453... Line 450...
453
 
450
 
Line 454... Line 451...
454
        Next(parser);
451
        Next(parser);
455
 
452
 
456
        IF (parser.sym = SCAN.lxVAR) OR (parser.sym = SCAN.lxIDENT) THEN
453
        IF (parser.sym = SCAN.lxVAR) OR (parser.sym = SCAN.lxIDENT) THEN
457
            FPSection(parser, type);
454
            FPSection(parser, _type);
458
            WHILE parser.sym = SCAN.lxSEMI DO
455
            WHILE parser.sym = SCAN.lxSEMI DO
459
                Next(parser);
456
                Next(parser);
460
                FPSection(parser, type)
457
                FPSection(parser, _type)
Line 461... Line 458...
461
            END
458
            END
462
        END;
459
        END;
Line 463... Line 460...
463
 
460
 
464
        checklex(parser, SCAN.lxRROUND);
461
        checklex(parser, SCAN.lxRROUND);
465
        Next(parser);
462
        Next(parser);
466
 
463
 
467
        IF parser.sym = SCAN.lxCOLON THEN
464
        IF parser.sym = SCAN.lxCOLON THEN
468
            ExpectSym(parser, SCAN.lxIDENT);
465
            ExpectSym(parser, SCAN.lxIDENT);
469
            ident := QIdent(parser, FALSE);
466
            ident := QIdent(parser, FALSE);
470
            check1(ident.typ = PROG.idTYPE, parser, 68);
467
            check1(ident.typ = PROG.idTYPE, parser, 68);
471
            check1(~(ident.type.typ IN {PROG.tRECORD, PROG.tARRAY}), parser, 69);
468
            check1(~(ident._type.typ IN {PROG.tRECORD, PROG.tARRAY}), parser, 69);
472
            check1( ~(ODD(type.call) & (ident.type.typ = PROG.tREAL)), parser, 113);
469
            check1( ~(ODD(_type.call) & (ident._type.typ = PROG.tREAL)), parser, 113);
473
            type.base := ident.type;
470
            _type.base := ident._type;
Line 474... Line 471...
474
            Next(parser)
471
            Next(parser)
475
        ELSE
472
        ELSE
Line 501... Line 498...
501
        sf := PROG.sf_windows
498
        sf := PROG.sf_windows
502
    ELSIF parser.lex.s = "linux" THEN
499
    ELSIF parser.lex.s = "linux" THEN
503
        sf := PROG.sf_linux
500
        sf := PROG.sf_linux
504
    ELSIF parser.lex.s = "code" THEN
501
    ELSIF parser.lex.s = "code" THEN
505
        sf := PROG.sf_code
502
        sf := PROG.sf_code
-
 
503
    ELSIF parser.lex.s = "oberon" THEN
-
 
504
        sf := PROG.sf_oberon
506
    ELSIF parser.lex.s = "noalign" THEN
505
    ELSIF parser.lex.s = "noalign" THEN
507
        sf := PROG.sf_noalign
506
        sf := PROG.sf_noalign
508
    ELSE
507
    ELSE
509
        check1(FALSE, parser, 124)
508
        check1(FALSE, parser, 124)
510
    END;
509
    END;
Line 511... Line 510...
511
 
510
 
Line 512... Line 511...
512
    check1(sf IN program.sysflags, parser, 125);
511
    check1(sf IN PROG.program.sysflags, parser, 125);
513
 
512
 
514
    IF proc THEN
513
    IF proc THEN
515
        check1(sf IN PROG.proc_flags, parser, 123)
514
        check1(sf IN PROG.proc_flags, parser, 123)
Line 530... Line 529...
530
        res := PROG.win64
529
        res := PROG.win64
531
    |PROG.sf_systemv:
530
    |PROG.sf_systemv:
532
        res := PROG.systemv
531
        res := PROG.systemv
533
    |PROG.sf_code:
532
    |PROG.sf_code:
534
        res := PROG.code
533
        res := PROG.code
-
 
534
    |PROG.sf_oberon:
-
 
535
        IF TARGETS.OS IN {TARGETS.osWIN32, TARGETS.osLINUX32, TARGETS.osKOS} THEN
-
 
536
            res := PROG.default32
-
 
537
        ELSIF TARGETS.OS IN {TARGETS.osWIN64, TARGETS.osLINUX64} THEN
-
 
538
            res := PROG.default64
-
 
539
        END
535
    |PROG.sf_windows:
540
    |PROG.sf_windows:
536
        IF TARGETS.OS = TARGETS.osWIN32 THEN
541
        IF TARGETS.OS = TARGETS.osWIN32 THEN
537
            res := PROG.stdcall
542
            res := PROG.stdcall
538
        ELSIF TARGETS.OS = TARGETS.osWIN64 THEN
543
        ELSIF TARGETS.OS = TARGETS.osWIN64 THEN
539
            res := PROG.win64
544
            res := PROG.win64
Line 550... Line 555...
550
 
555
 
551
    RETURN res
556
    RETURN res
Line 552... Line 557...
552
END sysflag;
557
END sysflag;
553
 
558
 
554
 
559
 
555
PROCEDURE procflag (parser: PARSER; VAR import: IL.IMPORT_PROC; isProc: BOOLEAN): INTEGER;
560
PROCEDURE procflag (parser: PARSER; VAR _import: IL.IMPORT_PROC; isProc: BOOLEAN): INTEGER;
556
VAR
561
VAR
Line -... Line 562...
-
 
562
    call: INTEGER;
-
 
563
    dll, proc: SCAN.LEXSTR;
-
 
564
    pos: POSITION;
-
 
565
 
-
 
566
 
-
 
567
    PROCEDURE getStr (parser: PARSER; VAR name: SCAN.LEXSTR);
557
    call: INTEGER;
568
    VAR
-
 
569
        pos: POSITION;
-
 
570
        str: ARITH.VALUE;
-
 
571
 
-
 
572
    BEGIN
-
 
573
        getpos(parser, pos);
-
 
574
        ConstExpression(parser, str);
-
 
575
        IF str.typ = ARITH.tSTRING THEN
-
 
576
            name := str.string(SCAN.IDENT).s
-
 
577
        ELSIF str.typ = ARITH.tCHAR THEN
-
 
578
            ARITH.charToStr(str, name)
Line -... Line 579...
-
 
579
        ELSE
-
 
580
            check(FALSE, pos, 117)
558
    dll, proc: SCAN.LEXSTR;
581
        END
Line 559... Line 582...
559
    pos: POSITION;
582
    END getStr;
560
 
583
 
561
BEGIN
584
 
562
 
585
BEGIN
Line 570... Line 593...
570
        Next(parser);
593
        Next(parser);
571
        IF parser.sym = SCAN.lxMINUS THEN
594
        IF parser.sym = SCAN.lxMINUS THEN
572
            Next(parser);
595
            Next(parser);
573
            INC(call)
596
            INC(call)
574
        END;
597
        END;
575
        IF ~isProc THEN
-
 
576
            checklex(parser, SCAN.lxRSQUARE)
-
 
577
        END;
598
 
578
        IF parser.sym = SCAN.lxCOMMA THEN
599
        IF isProc & (parser.sym = SCAN.lxCOMMA) THEN
579
            ExpectSym(parser, SCAN.lxSTRING);
600
            Next(parser);
580
            dll := parser.lex.s;
601
            getStr(parser, dll);
581
            STRINGS.UpCase(dll);
602
            STRINGS.UpCase(dll);
582
            ExpectSym(parser, SCAN.lxCOMMA);
603
            checklex(parser, SCAN.lxCOMMA);
583
            ExpectSym(parser, SCAN.lxSTRING);
-
 
584
            proc := parser.lex.s;
-
 
585
            Next(parser);
604
            Next(parser);
-
 
605
            getStr(parser, proc);
586
            import := IL.AddImp(dll, proc)
606
            _import := IL.AddImp(dll, proc)
587
        END;
607
        END;
-
 
608
 
588
        checklex(parser, SCAN.lxRSQUARE);
609
        checklex(parser, SCAN.lxRSQUARE);
589
        Next(parser)
610
        Next(parser)
590
    ELSE
611
    ELSE
591
        CASE TARGETS.BitDepth OF
612
        CASE TARGETS.BitDepth OF
592
        |16: call := PROG.default16
613
        |16: call := PROG.default16
593
        |32: IF TARGETS.target = TARGETS.STM32CM3 THEN
614
        |32: IF TARGETS.CPU = TARGETS.cpuX86 THEN
594
                 call := PROG.ccall
-
 
595
             ELSE
-
 
596
                 call := PROG.default32
615
                 call := PROG.default32
-
 
616
             ELSE
-
 
617
                 call := PROG.ccall
597
             END
618
             END
598
        |64: call := PROG.default64
619
        |64: call := PROG.default64
599
        END
620
        END
600
    END;
621
    END;
Line 601... Line 622...
601
 
622
 
602
    IF import # NIL THEN
623
    IF _import # NIL THEN
603
        check(TARGETS.Import, pos, 70)
624
        check(TARGETS.Import, pos, 70)
Line 604... Line 625...
604
    END
625
    END
605
 
626
 
Line 606... Line 627...
606
    RETURN call
627
    RETURN call
607
END procflag;
628
END procflag;
608
 
629
 
609
 
630
 
610
PROCEDURE type (parser: PARSER; VAR t: PROG.TYPE_; flags: SET);
631
PROCEDURE _type (parser: PARSER; VAR t: PROG._TYPE; flags: SET);
Line 617... Line 638...
617
    arrLen:     ARITH.VALUE;
638
    arrLen:     ARITH.VALUE;
618
    typeSize:   ARITH.VALUE;
639
    typeSize:   ARITH.VALUE;
619
    ident:      PROG.IDENT;
640
    ident:      PROG.IDENT;
620
    unit:       PROG.UNIT;
641
    unit:       PROG.UNIT;
621
    pos, pos2:  POSITION;
642
    pos, pos2:  POSITION;
622
    fieldType:  PROG.TYPE_;
643
    fieldType:  PROG._TYPE;
623
    baseIdent:  SCAN.IDENT;
644
    baseIdent:  SCAN.IDENT;
624
    a, b:       INTEGER;
645
    a, b:       INTEGER;
625
    RecFlag:    INTEGER;
646
    RecFlag:    INTEGER;
626
    import:     IL.IMPORT_PROC;
647
    _import:     IL.IMPORT_PROC;
Line 627... Line 648...
627
 
648
 
628
BEGIN
649
BEGIN
629
    unit := parser.unit;
650
    unit := parser.unit;
Line 630... Line 651...
630
    t := NIL;
651
    t := NIL;
631
 
652
 
Line 632... Line 653...
632
    IF parser.sym = SCAN.lxIDENT THEN
653
    IF parser.sym = SCAN.lxIDENT THEN
633
        ident := QIdent(parser, forward IN flags);
654
        ident := QIdent(parser, forward IN flags);
634
 
655
 
635
        IF ident # NIL THEN
656
        IF ident # NIL THEN
636
            check1(ident.typ = PROG.idTYPE, parser, 49);
657
            check1(ident.typ = PROG.idTYPE, parser, 49);
637
            t := ident.type;
658
            t := ident._type;
638
            check1(t # NIL, parser, 50);
659
            check1(t # NIL, parser, 50);
639
            IF closed IN flags THEN
660
            IF closed IN flags THEN
Line 654... Line 675...
654
 
675
 
655
        check(arrLen.typ = ARITH.tINTEGER, pos, 43);
676
        check(arrLen.typ = ARITH.tINTEGER, pos, 43);
656
        check(ARITH.check(arrLen),         pos, 39);
677
        check(ARITH.check(arrLen),         pos, 39);
Line 657... Line 678...
657
        check(ARITH.getInt(arrLen) > 0,    pos, 51);
678
        check(ARITH.getInt(arrLen) > 0,    pos, 51);
Line 658... Line 679...
658
 
679
 
659
        t := PROG.enterType(program, PROG.tARRAY, -1, ARITH.getInt(arrLen), unit);
680
        t := PROG.enterType(PROG.tARRAY, -1, ARITH.getInt(arrLen), unit);
660
 
681
 
661
        IF parser.sym = SCAN.lxCOMMA THEN
682
        IF parser.sym = SCAN.lxCOMMA THEN
662
            type(parser, t.base, {comma, closed})
683
            _type(parser, t.base, {comma, closed})
663
        ELSIF parser.sym = SCAN.lxOF THEN
684
        ELSIF parser.sym = SCAN.lxOF THEN
664
            Next(parser);
685
            Next(parser);
665
            type(parser, t.base, {closed})
686
            _type(parser, t.base, {closed})
Line 666... Line 687...
666
        ELSE
687
        ELSE
Line 679... Line 700...
679
 
700
 
680
    ELSIF parser.sym = SCAN.lxRECORD THEN
701
    ELSIF parser.sym = SCAN.lxRECORD THEN
681
        getpos(parser, pos2);
702
        getpos(parser, pos2);
Line 682... Line 703...
682
        Next(parser);
703
        Next(parser);
683
 
704
 
Line 684... Line 705...
684
        t := PROG.enterType(program, PROG.tRECORD, 0, 0, unit);
705
        t := PROG.enterType(PROG.tRECORD, 0, 0, unit);
685
        t.align := 1;
706
        t.align := 1;
686
 
707
 
Line 696... Line 717...
696
        IF parser.sym = SCAN.lxLROUND THEN
717
        IF parser.sym = SCAN.lxLROUND THEN
697
            check1(~t.noalign, parser, 111);
718
            check1(~t.noalign, parser, 111);
698
            ExpectSym(parser, SCAN.lxIDENT);
719
            ExpectSym(parser, SCAN.lxIDENT);
699
            getpos(parser, pos);
720
            getpos(parser, pos);
Line 700... Line 721...
700
 
721
 
Line 701... Line 722...
701
            type(parser, t.base, {closed});
722
            _type(parser, t.base, {closed});
Line 702... Line 723...
702
 
723
 
703
            check(t.base.typ IN {PROG.tRECORD, PROG.tPOINTER}, pos, 52);
724
            check(t.base.typ IN {PROG.tRECORD, PROG.tPOINTER}, pos, 52);
Line 715... Line 736...
715
            t.size := t.base.size;
736
            t.size := t.base.size;
716
            IF t.base.align > t.align THEN
737
            IF t.base.align > t.align THEN
717
                t.align := t.base.align
738
                t.align := t.base.align
718
            END
739
            END
719
        ELSE
740
        ELSE
720
            t.base := program.stTypes.tANYREC
741
            t.base := PROG.program.stTypes.tANYREC
721
        END;
742
        END;
Line 722... Line 743...
722
 
743
 
723
        WHILE parser.sym = SCAN.lxIDENT DO
744
        WHILE parser.sym = SCAN.lxIDENT DO
Line 724... Line 745...
724
            FieldList(parser, t);
745
            FieldList(parser, t);
725
 
746
 
Line 726... Line 747...
726
            ASSERT(parser.sym = SCAN.lxCOLON);
747
            ASSERT(parser.sym = SCAN.lxCOLON);
727
            Next(parser);
748
            Next(parser);
Line 728... Line 749...
728
 
749
 
729
            type(parser, fieldType, {closed});
750
            _type(parser, fieldType, {closed});
730
            check(PROG.setFields(t, fieldType), pos2, 104);
751
            check(PROG.setFields(t, fieldType), pos2, 104);
Line 754... Line 775...
754
 
775
 
755
    ELSIF parser.sym = SCAN.lxPOINTER THEN
776
    ELSIF parser.sym = SCAN.lxPOINTER THEN
756
        ExpectSym(parser, SCAN.lxTO);
777
        ExpectSym(parser, SCAN.lxTO);
Line 757... Line 778...
757
        Next(parser);
778
        Next(parser);
758
 
779
 
Line 759... Line 780...
759
        t := PROG.enterType(program, PROG.tPOINTER, TARGETS.AdrSize, 0, unit);
780
        t := PROG.enterType(PROG.tPOINTER, TARGETS.AdrSize, 0, unit);
Line 760... Line 781...
760
        t.align := TARGETS.AdrSize;
781
        t.align := TARGETS.AdrSize;
761
 
782
 
762
        getpos(parser, pos);
783
        getpos(parser, pos);
Line 763... Line 784...
763
 
784
 
Line 764... Line 785...
764
        IF parser.sym = SCAN.lxIDENT THEN
785
        IF parser.sym = SCAN.lxIDENT THEN
765
            baseIdent := parser.lex.ident
786
            baseIdent := parser.lex.ident
766
        END;
787
        END;
767
 
788
 
768
        type(parser, t.base, {forward});
789
        _type(parser, t.base, {forward});
Line 769... Line 790...
769
 
790
 
770
        IF t.base # NIL THEN
791
        IF t.base # NIL THEN
771
            check(t.base.typ = PROG.tRECORD, pos, 58)
792
            check(t.base.typ = PROG.tRECORD, pos, 58)
772
        ELSE
793
        ELSE
773
            PROG.frwPtr(unit, t, baseIdent, pos)
794
            PROG.frwPtr(unit, t, baseIdent, pos)
774
        END
795
        END
775
 
796
 
776
    ELSIF parser.sym = SCAN.lxPROCEDURE THEN
797
    ELSIF parser.sym = SCAN.lxPROCEDURE THEN
777
        NextPos(parser, pos);
798
        NextPos(parser, pos);
Line 778... Line 799...
778
        t := PROG.enterType(program, PROG.tPROCEDURE, TARGETS.AdrSize, 0, unit);
799
        t := PROG.enterType(PROG.tPROCEDURE, TARGETS.AdrSize, 0, unit);
Line 779... Line 800...
779
        t.align := TARGETS.AdrSize;
800
        t.align := TARGETS.AdrSize;
780
        t.call := procflag(parser, import, FALSE);
801
        t.call := procflag(parser, _import, FALSE);
781
        FormalParameters(parser, t)
802
        FormalParameters(parser, t)
Line 809... Line 830...
809
 
830
 
810
    RETURN ident
831
    RETURN ident
Line 811... Line 832...
811
END IdentDef;
832
END IdentDef;
812
 
833
 
813
 
834
 
814
PROCEDURE ConstTypeDeclaration (parser: PARSER; const: BOOLEAN);
835
PROCEDURE ConstTypeDeclaration (parser: PARSER; _const: BOOLEAN);
815
VAR
836
VAR
Line 816... Line 837...
816
    ident: PROG.IDENT;
837
    ident: PROG.IDENT;
817
    name:  SCAN.IDENT;
838
    name:  SCAN.IDENT;
818
    pos:   POSITION;
839
    pos:   POSITION;
819
 
840
 
820
BEGIN
841
BEGIN
821
    IF const THEN
842
    IF _const THEN
Line 822... Line 843...
822
        ident := IdentDef(parser, PROG.idNONE, name)
843
        ident := IdentDef(parser, PROG.idNONE, name)
823
    ELSE
844
    ELSE
Line 824... Line 845...
824
        ident := IdentDef(parser, PROG.idTYPE, name)
845
        ident := IdentDef(parser, PROG.idTYPE, name)
825
    END;
846
    END;
826
 
847
 
827
    checklex(parser, SCAN.lxEQ);
848
    checklex(parser, SCAN.lxEQ);
828
    NextPos(parser, pos);
849
    NextPos(parser, pos);
829
 
850
 
830
    IF const THEN
851
    IF _const THEN
831
        ConstExpression(parser, ident.value);
852
        ConstExpression(parser, ident.value);
832
        IF ident.value.typ = ARITH.tINTEGER THEN
853
        IF ident.value.typ = ARITH.tINTEGER THEN
833
            check(ARITH.check(ident.value), pos, 39)
854
            check(ARITH.check(ident.value), pos, 39)
834
        ELSIF ident.value.typ = ARITH.tREAL THEN
855
        ELSIF ident.value.typ = ARITH.tREAL THEN
835
            check(ARITH.check(ident.value), pos, 40)
856
            check(ARITH.check(ident.value), pos, 40)
Line 836... Line 857...
836
        END;
857
        END;
837
        ident.typ  := PROG.idCONST;
858
        ident.typ  := PROG.idCONST;
Line 848... Line 869...
848
 
869
 
849
PROCEDURE VarDeclaration (parser: PARSER);
870
PROCEDURE VarDeclaration (parser: PARSER);
850
VAR
871
VAR
851
    ident: PROG.IDENT;
872
    ident: PROG.IDENT;
852
    name:  SCAN.IDENT;
873
    name:  SCAN.IDENT;
Line 853... Line 874...
853
    t:     PROG.TYPE_;
874
    t:     PROG._TYPE;
Line 854... Line 875...
854
 
875
 
855
BEGIN
876
BEGIN
Line 856... Line 877...
856
 
877
 
857
    REPEAT
878
    REPEAT
858
        ident := IdentDef(parser, PROG.idVAR, name);
879
        ident := IdentDef(parser, PROG.idVAR, name);
859
 
880
 
860
        IF parser.sym = SCAN.lxCOMMA THEN
881
        IF parser.sym = SCAN.lxCOMMA THEN
861
            ExpectSym(parser, SCAN.lxIDENT)
882
            ExpectSym(parser, SCAN.lxIDENT)
862
        ELSIF parser.sym = SCAN.lxCOLON THEN
883
        ELSIF parser.sym = SCAN.lxCOLON THEN
863
            Next(parser);
884
            Next(parser);
864
            type(parser, t, {});
885
            _type(parser, t, {});
865
            PROG.setVarsType(parser.unit, t);
886
            PROG.setVarsType(parser.unit, t);
Line 893... Line 914...
893
        pos, pos1,
914
        pos, pos1,
894
        pos2:       POSITION;
915
        pos2:       POSITION;
895
        label:      INTEGER;
916
        label:      INTEGER;
896
        enter:      IL.COMMAND;
917
        enter:      IL.COMMAND;
897
        call:       INTEGER;
918
        call:       INTEGER;
898
        t:          PROG.TYPE_;
919
        t:          PROG._TYPE;
899
        import:     IL.IMPORT_PROC;
920
        _import:    IL.IMPORT_PROC;
900
        endmod, b:  BOOLEAN;
921
        endmod, b:  BOOLEAN;
901
        fparams:    SET;
922
        fparams:    SET;
902
        variables:  LISTS.LIST;
923
        variables:  LISTS.LIST;
903
        int, flt:   INTEGER;
924
        int, flt:   INTEGER;
904
        comma:      BOOLEAN;
925
        comma:      BOOLEAN;
Line 910... Line 931...
910
        endmod := FALSE;
931
        endmod := FALSE;
911
        handler := FALSE;
932
        handler := FALSE;
Line 912... Line 933...
912
 
933
 
Line 913... Line 934...
913
        unit := parser.unit;
934
        unit := parser.unit;
Line 914... Line 935...
914
 
935
 
915
        call := procflag(parser, import, TRUE);
936
        call := procflag(parser, _import, TRUE);
916
 
937
 
Line 917... Line 938...
917
        getpos(parser, pos);
938
        getpos(parser, pos);
918
        pos1 := pos;
939
        pos1 := pos;
919
        checklex(parser, SCAN.lxIDENT);
940
        checklex(parser, SCAN.lxIDENT);
-
 
941
 
-
 
942
        IF _import # NIL THEN
-
 
943
            proc := IdentDef(parser, PROG.idIMP, name);
920
 
944
            proc._import := _import;
921
        IF import # NIL THEN
945
            IF _import.name = "" THEN
922
            proc := IdentDef(parser, PROG.idIMP, name);
946
                _import.name := name.s
923
            proc.import := import;
947
            END;
Line 924... Line 948...
924
            program.procs.last(PROG.PROC).import := import
948
            PROG.program.procs.last(PROG.PROC)._import := _import
Line 925... Line 949...
925
        ELSE
949
        ELSE
926
            proc := IdentDef(parser, PROG.idPROC, name)
950
            proc := IdentDef(parser, PROG.idPROC, name)
927
        END;
951
        END;
928
 
952
 
Line 929... Line 953...
929
        check(PROG.openScope(unit, proc.proc), pos, 116);
953
        check(PROG.openScope(unit, proc.proc), pos, 116);
Line 957... Line 981...
957
 
981
 
958
        param := t.params.first(PROG.PARAM);
982
        param := t.params.first(PROG.PARAM);
959
        WHILE param # NIL DO
983
        WHILE param # NIL DO
960
            ident := PROG.addIdent(unit, param.name, PROG.idPARAM);
984
            ident := PROG.addIdent(unit, param.name, PROG.idPARAM);
961
            ASSERT(ident # NIL);
985
            ASSERT(ident # NIL);
962
            ident.type := param.type;
986
            ident._type := param._type;
963
            ident.offset := param.offset;
987
            ident.offset := param.offset;
964
            IF param.vPar THEN
988
            IF param.vPar THEN
965
                ident.typ := PROG.idVPAR
989
                ident.typ := PROG.idVPAR
966
            END;
990
            END;
967
            param := param.next(PROG.PARAM)
991
            param := param.next(PROG.PARAM)
Line 968... Line 992...
968
        END;
992
        END;
969
 
993
 
970
        IF import = NIL THEN
994
        IF _import = NIL THEN
971
            label := IL.NewLabel();
995
            label := IL.NewLabel();
972
            proc.proc.label := label;
996
            proc.proc.label := label;
973
            proc.proc.used  := handler;
997
            proc.proc.used  := handler;
Line 981... Line 1005...
981
            comma := FALSE;
1005
            comma := FALSE;
982
            WHILE (parser.sym # SCAN.lxSEMI) OR comma DO
1006
            WHILE (parser.sym # SCAN.lxSEMI) OR comma DO
983
                getpos(parser, pos2);
1007
                getpos(parser, pos2);
984
                ConstExpression(parser, code);
1008
                ConstExpression(parser, code);
985
                check(code.typ = ARITH.tINTEGER, pos2, 43);
1009
                check(code.typ = ARITH.tINTEGER, pos2, 43);
986
                IF TARGETS.CPU IN {TARGETS.cpuX86, TARGETS.cpuAMD64} THEN
1010
                IF TARGETS.WordSize > TARGETS.InstrSize THEN
987
                    check(ARITH.range(code, 0, 255), pos2, 42)
1011
                    CASE TARGETS.InstrSize OF
988
                ELSIF TARGETS.CPU = TARGETS.cpuTHUMB THEN
1012
                    |1: check(ARITH.range(code, 0, 255), pos, 42)
989
                    check(ARITH.range(code, 0, 65535), pos2, 110)
1013
                    |2: check(ARITH.range(code, 0, 65535), pos, 110)
-
 
1014
                    END
990
                END;
1015
                END;
991
                IL.AddCmd(IL.opCODE, ARITH.getInt(code));
1016
                IL.AddCmd(IL.opCODE, ARITH.getInt(code));
992
                comma := parser.sym = SCAN.lxCOMMA;
1017
                comma := parser.sym = SCAN.lxCOMMA;
993
                IF comma THEN
1018
                IF comma THEN
994
                    Next(parser)
1019
                    Next(parser)
Line 999... Line 1024...
999
        END;
1024
        END;
Line 1000... Line 1025...
1000
 
1025
 
1001
        checklex(parser, SCAN.lxSEMI);
1026
        checklex(parser, SCAN.lxSEMI);
Line 1002... Line 1027...
1002
        Next(parser);
1027
        Next(parser);
Line 1003... Line 1028...
1003
 
1028
 
1004
        IF import = NIL THEN
1029
        IF _import = NIL THEN
1005
 
1030
 
1006
            IF parser.main & proc.export & TARGETS.Dll THEN
1031
            IF parser.main & proc.export & TARGETS.Dll THEN
Line 1013... Line 1038...
1013
 
1038
 
1014
            IF ~codeProc THEN
1039
            IF ~codeProc THEN
1015
                b := DeclarationSequence(parser)
1040
                b := DeclarationSequence(parser)
Line 1016... Line 1041...
1016
            END;
1041
            END;
1017
 
1042
 
1018
            program.locsize := 0;
1043
            PROG.ResetLocSize;
1019
            IF call IN {PROG._win64, PROG.win64} THEN
1044
            IF call IN {PROG._win64, PROG.win64} THEN
1020
                fparams := PROG.getFloatParamsPos(proc.type, 3, int, flt);
1045
                fparams := PROG.getFloatParamsPos(proc._type, 3, int, flt);
1021
                enter := IL.Enter(label, LSL(ORD(fparams), 5) + MIN(proc.type.parSize, 4))
1046
                enter := IL.Enter(label, LSL(ORD(fparams), 5) + MIN(proc._type.parSize, 4))
1022
            ELSIF call IN {PROG._systemv, PROG.systemv} THEN
1047
            ELSIF call IN {PROG._systemv, PROG.systemv} THEN
1023
                fparams := PROG.getFloatParamsPos(proc.type, PROG.MAXSYSVPARAM - 1, int, flt);
1048
                fparams := PROG.getFloatParamsPos(proc._type, PROG.MAXSYSVPARAM - 1, int, flt);
Line 1024... Line 1049...
1024
                enter := IL.Enter(label, -(LSL(ORD(fparams), 5) + proc.type.parSize))
1049
                enter := IL.Enter(label, -(LSL(ORD(fparams), 5) + proc._type.parSize))
1025
            ELSIF codeProc THEN
1050
            ELSIF codeProc THEN
1026
 
1051
 
Line 1040... Line 1065...
1040
                parser.expression(parser, e);
1065
                parser.expression(parser, e);
1041
                check(parser.chkreturn(parser, e, t.base, pos), pos, 87)
1066
                check(parser.chkreturn(parser, e, t.base, pos), pos, 87)
1042
            END;
1067
            END;
Line 1043... Line 1068...
1043
 
1068
 
1044
            IF ~codeProc THEN
1069
            IF ~codeProc THEN
1045
                proc.proc.leave := IL.Leave(t.base # NIL, (t.base # NIL) & (t.base.typ = PROG.tREAL), program.locsize,
1070
                proc.proc.leave := IL.Leave(t.base # NIL, (t.base # NIL) & (t.base.typ = PROG.tREAL), PROG.program.locsize,
1046
                    t.parSize * ORD((t.call IN PROG.callee_clean_up) OR (t.call IN {PROG.systemv, PROG._systemv})));
1071
                    t.parSize * ORD((t.call IN PROG.callee_clean_up) OR (t.call IN {PROG.systemv, PROG._systemv})));
1047
                enter.param2 := program.locsize;
1072
                enter.param2 := PROG.program.locsize;
1048
                checklex(parser, SCAN.lxEND)
1073
                checklex(parser, SCAN.lxEND)
1049
            ELSE
1074
            ELSE
1050
                proc.proc.leave := IL.LeaveC()
1075
                proc.proc.leave := IL.LeaveC()
Line 1051... Line 1076...
1051
            END;
1076
            END;
1052
 
1077
 
1053
            IF TARGETS.CPU = TARGETS.cpuMSP430 THEN
1078
            IF TARGETS.CPU = TARGETS.cpuMSP430 THEN
1054
                check((enter.param2 * ORD(~codeProc) + proc.type.parSize) * 2 + 16 < program.options.ram, pos1, 63)
1079
                check((enter.param2 * ORD(~codeProc) + proc._type.parSize) * 2 + 16 < PROG.program.options.ram, pos1, 63)
Line 1055... Line 1080...
1055
            END
1080
            END
-
 
1081
        END;
1056
        END;
1082
 
1057
 
1083
        IF parser.sym = SCAN.lxEND THEN
1058
        IF parser.sym = SCAN.lxEND THEN
1084
            Next(parser);
1059
            ExpectSym(parser, SCAN.lxIDENT);
1085
            IF parser.sym = SCAN.lxIDENT THEN
1060
            getpos(parser, pos);
1086
                getpos(parser, pos);
1061
            endname := parser.lex.ident;
1087
                endname := parser.lex.ident;
1062
            IF ~codeProc & (import = NIL) THEN
1088
                IF ~codeProc & (_import = NIL) THEN
1063
                check(endname = name, pos, 60);
1089
                    check(endname = name, pos, 60);
1064
                ExpectSym(parser, SCAN.lxSEMI);
1090
                    ExpectSym(parser, SCAN.lxSEMI);
Line 1073... Line 1099...
1073
                    Next(parser)
1099
                        Next(parser)
1074
                ELSE
1100
                    ELSE
1075
                    error(pos, 60)
1101
                        error(pos, 60)
1076
                END
1102
                    END
1077
            END
1103
                END
-
 
1104
            ELSIF parser.sym = SCAN.lxSEMI THEN
-
 
1105
                Next(parser)
-
 
1106
            ELSE
-
 
1107
                checklex(parser, SCAN.lxIDENT)
-
 
1108
            END
1078
        END;
1109
        END;
Line 1079... Line 1110...
1079
 
1110
 
1080
        IF ~codeProc & (import = NIL) THEN
1111
        IF ~codeProc & (_import = NIL) THEN
1081
            variables := LISTS.create(NIL);
1112
            variables := LISTS.create(NIL);
1082
        ELSE
1113
        ELSE
1083
            variables := NIL
1114
            variables := NIL
Line 1084... Line 1115...
1084
        END;
1115
        END;
Line 1085... Line 1116...
1085
 
1116
 
1086
        PROG.closeScope(unit, variables);
1117
        PROG.closeScope(unit, variables);
1087
 
1118
 
Line 1088... Line 1119...
1088
        IF ~codeProc & (import = NIL) THEN
1119
        IF ~codeProc & (_import = NIL) THEN
1089
            enter.variables := variables
1120
            enter.variables := variables
Line 1155... Line 1186...
1155
 
1186
 
1156
    IF ~parser.main THEN
1187
    IF ~parser.main THEN
1157
        check1(parser.lex.s = parser.modname, parser, 23)
1188
        check1(parser.lex.s = parser.modname, parser, 23)
Line 1158... Line 1189...
1158
    END;
1189
    END;
Line 1159... Line 1190...
1159
 
1190
 
Line 1160... Line 1191...
1160
    unit := PROG.newUnit(program, parser.lex.ident);
1191
    unit := PROG.newUnit(parser.lex.ident);
Line 1169... Line 1200...
1169
    END;
1200
    END;
Line 1170... Line 1201...
1170
 
1201
 
Line 1171... Line 1202...
1171
    INC(modules);
1202
    INC(modules);
1172
 
-
 
1173
    CONSOLE.String("compiling ");
1203
 
1174
    IF TARGETS.CPU IN {TARGETS.cpuTHUMB, TARGETS.cpuMSP430} THEN
-
 
1175
        CONSOLE.String("("); CONSOLE.Int(modules); CONSOLE.String(") ")
1204
    CONSOLE.String("compiling ");
1176
    END;
1205
    CONSOLE.String("("); CONSOLE.Int(modules); CONSOLE.String(") ");
1177
    CONSOLE.String(unit.name.s);
1206
    CONSOLE.String(unit.name.s);
1178
    IF parser.unit.sysimport THEN
1207
    IF parser.unit.sysimport THEN
1179
        CONSOLE.String(" (SYSTEM)")
1208
        CONSOLE.String(" (SYSTEM)")
Line -... Line 1209...
-
 
1209
    END;
-
 
1210
    CONSOLE.Ln;
-
 
1211
 
-
 
1212
    IF TARGETS.CPU IN {TARGETS.cpuX86, TARGETS.cpuAMD64} THEN
1180
    END;
1213
        IL.fname(parser.fname)
1181
    CONSOLE.Ln;
1214
    END;
Line 1182... Line 1215...
1182
 
1215
 
Line 1183... Line 1216...
1183
    label := IL.NewLabel();
1216
    label := IL.NewLabel();
1184
    IL.AddJmpCmd(IL.opJMP, label);
1217
    IL.AddJmpCmd(IL.opJMP, label);
1185
 
1218
 
1186
    name := IL.putstr(unit.name.s);
1219
    name := IL.putstr(unit.name.s);
1187
 
-
 
1188
    errlabel := IL.NewLabel();
1220
 
1189
    IL.SetLabel(errlabel);
-
 
1190
    IL.StrAdr(name);
1221
    errlabel := IL.NewLabel();
Line 1191... Line 1222...
1191
    IL.Param1;
1222
    IL.SetLabel(errlabel);
1192
    IF TARGETS.CPU IN {TARGETS.cpuTHUMB, TARGETS.cpuMSP430} THEN
1223
    IL.StrAdr(name);
1193
        IL.AddCmd(IL.opPUSHC, modules)
1224
    IL.Param1;
Line 1283... Line 1314...
1283
END create;
1314
END create;
Line 1284... Line 1315...
1284
 
1315
 
1285
 
1316
 
1286
PROCEDURE init* (options: PROG.OPTIONS);
1317
PROCEDURE init* (options: PROG.OPTIONS);
1287
BEGIN
1318
BEGIN
1288
    program := PROG.create(options);
1319
    PROG.create(options);
1289
    parsers := C.create();
1320
    parsers := C.create();
1290
    lines   := 0;
1321
    lines   := 0;