Преглед изворни кода

Sol Part 65: WHY IS IT STILL WORKING?!

Graham Northup пре 3 година
родитељ
комит
babcf57409
Signed by: Graham Northup <grissess@nexusg.org> GPG Key ID: 5D000E6F539376FB
18 измењених фајлова са 6779 додато и 5941 уклоњено
  1. 1
    0
      .gitignore
  2. 10
    7
      Makefile
  3. 4
    1
      ast.h
  4. 2
    0
      builtins.c
  5. 166
    159
      lex.yy.c
  6. 10
    0
      object.c
  7. 5851
    5193
      parser.output
  8. 558
    513
      parser.tab.c
  9. 54
    53
      parser.tab.h
  10. 24
    1
      parser.y
  11. 25
    13
      runtime.c
  12. 3
    0
      ser.c
  13. 16
    1
      sol.h
  14. 10
    0
      state.c
  15. 13
    0
      tests/_crasher_tco.sol
  16. 16
    0
      tests/crasher_multiple_loops.sol
  17. 14
    0
      tests/lang_macro.sol
  18. 2
    0
      tokenizer.lex

+ 1
- 0
.gitignore Прегледај датотеку

@@ -1,6 +1,7 @@
1 1
 /sol*
2 2
 !sol_help.txt
3 3
 *.o
4
+*.a
4 5
 stdout
5 6
 .submodule_stamp
6 7
 *.orig

+ 10
- 7
Makefile Прегледај датотеку

@@ -1,5 +1,5 @@
1
-override CFLAGS:= -g $(BUILD_DEFINES) $(CFLAGS)
2
-override LDFLAGS:= -lfl -lm -ldl -lreadline $(LDFLAGS)
1
+_CFLAGS= -g $(BUILD_DEFINES) $(CFLAGS)
2
+_LDFLAGS= -lfl -lm -ldl -lreadline $(LDFLAGS)
3 3
 OBJ= lex.yy.o parser.tab.o dsl/seq.o dsl/list.o dsl/array.o dsl/generic.o astprint.o runtime.o gc.o object.o state.o builtins.o solrun.o ser.o
4 4
 
5 5
 ifndef CC
@@ -19,7 +19,7 @@ ifndef DESTDIR
19 19
 endif
20 20
 
21 21
 ifdef NO_HELP
22
-	override CFLAGS+= -DNO_HELP
22
+	_CFLAGS+= -DNO_HELP
23 23
 else
24 24
 	OBJ+= sol_help.o
25 25
 endif
@@ -38,7 +38,7 @@ LINKED_VERS:=sol sol$(MAJOR) sol$(MAJOR).$(MINOR)
38 38
 
39 39
 .PHONY: install install_bin install_bindir install_lib install_libdir uninstall uninstall_bin uninstall_lib all test clean docs
40 40
 
41
-all: dsl $(LINKED_VERS)
41
+all: dsl libsol.a $(LINKED_VERS)
42 42
 
43 43
 install: install_bindir install_libdir install_bin install_lib
44 44
 
@@ -67,9 +67,12 @@ $(LINKED_VERS): sol$(SOL_VER)
67 67
 	rm $@; ln -s $? $@
68 68
 	
69 69
 sol$(SOL_VER): $(OBJ)
70
-	$(CC) $(CFLAGS) $^ $(LDFLAGS) -o $@
70
+	$(CC) $(_CFLAGS) $^ $(_LDFLAGS) -o $@
71 71
 
72
-test: all $(sort $(patsubst tests/%.sol,test_%,$(wildcard tests/*.sol))) $(sort $(patsubst tests/%.sol,testcomp_%,$(wildcard tests/*.sol)))
72
+libsol.a: $(OBJ)
73
+	$(AR) rcs $@ $^
74
+
75
+test: all $(sort $(patsubst tests/%.sol,test_%,$(filter-out tests/_%,$(wildcard tests/*.sol)))) $(sort $(patsubst tests/%.sol,testcomp_%,$(filter-out tests/_%,$(wildcard tests/*.sol))))
73 76
 
74 77
 
75 78
 test_%: tests/%.sol
@@ -111,7 +114,7 @@ ARCH_INFO: gc.o
111 114
 	$(OBJDUMP) -f $? | perl -n -e '/file format ([^-]+-(.+))$$/ && print "HOST_ARCH:=$$2\nHOST_ELF:=$$1\n"' > $@
112 115
 
113 116
 %.o: %.c
114
-	$(CC) -c -o $@ $? $(CFLAGS)
117
+	$(CC) -c -o $@ $? $(_CFLAGS)
115 118
 
116 119
 %.o: %.txt | ARCH_INFO
117 120
 	$(OBJCOPY) -B i386 -I binary -O $(HOST_ELF) $? $@

+ 4
- 1
ast.h Прегледај датотеку

@@ -3,6 +3,8 @@
3 3
 
4 4
 #include "sol.h"
5 5
 
6
+#define FUNC_IS_MACRO 1
7
+
6 8
 #include <stdio.h>
7 9
 
8 10
 /** Locator structure.
@@ -148,6 +150,7 @@ typedef struct {
148 150
 	paramlist_node *params;
149 151
 	expr_node *anno;
150 152
 	stmt_node *body;
153
+	unsigned short flags;  // FUNC_IS_MACRO
151 154
 } funcdecl_node;
152 155
 
153 156
 typedef struct {
@@ -294,7 +297,7 @@ typedef enum {
294 297
 		res;\
295 298
 })
296 299
 
297
-sol_object_t *sol_new_func(sol_state_t *, identlist_node *, stmt_node *, char *, paramlist_node *, expr_node *);
300
+sol_object_t *sol_new_func(sol_state_t *, identlist_node *, stmt_node *, char *, paramlist_node *, expr_node *, unsigned short);
298 301
 sol_object_t *sol_new_stmtnode(sol_state_t *, stmt_node *);
299 302
 sol_object_t *sol_new_exprnode(sol_state_t *, expr_node *);
300 303
 

+ 2
- 0
builtins.c Прегледај датотеку

@@ -535,6 +535,8 @@ sol_object_t *sol_f_debug_scopes(sol_state_t *state, sol_object_t *args) {
535 535
 
536 536
 sol_object_t *sol_f_debug_getops(sol_state_t *state, sol_object_t *args) {
537 537
 	sol_object_t *obj = sol_list_get_index(state, args, 0), *res = sol_new_map(state);
538
+	sol_map_borrow_name(state, res, "name", sol_new_buffer(state, obj->ops->tname, strlen(obj->ops->tname), OWN_NONE, NULL, NULL));
539
+	sol_map_borrow_name(state, res, "flags", sol_new_int(state, obj->ops->tflags));
538 540
 	sol_map_borrow_name(state, res, "add", sol_new_cfunc(state, obj->ops->add, "add"));
539 541
 	sol_map_borrow_name(state, res, "sub", sol_new_cfunc(state, obj->ops->sub, "sub"));
540 542
 	sol_map_borrow_name(state, res, "mul", sol_new_cfunc(state, obj->ops->mul, "mul"));

+ 166
- 159
lex.yy.c Прегледај датотеку

@@ -375,8 +375,8 @@ static void yynoreturn yy_fatal_error ( const char* msg  );
375 375
 	(yy_hold_char) = *yy_cp; \
376 376
 	*yy_cp = '\0'; \
377 377
 	(yy_c_buf_p) = yy_cp;
378
-#define YY_NUM_RULES 74
379
-#define YY_END_OF_BUFFER 75
378
+#define YY_NUM_RULES 75
379
+#define YY_END_OF_BUFFER 76
380 380
 /* This struct is not used in this scanner,
381 381
    but its presence is necessary. */
382 382
 struct yy_trans_info
@@ -384,25 +384,25 @@ struct yy_trans_info
384 384
 	flex_int32_t yy_verify;
385 385
 	flex_int32_t yy_nxt;
386 386
 	};
387
-static const flex_int16_t yy_accept[154] =
387
+static const flex_int16_t yy_accept[158] =
388 388
     {   0,
389
-        0,    0,   75,   74,   73,   35,   74,   69,   24,   27,
390
-       74,   63,   64,   22,   20,   68,   21,   65,   23,    2,
391
-       66,   67,   52,   41,   53,   71,   71,   71,   71,   60,
392
-       61,   29,   71,   71,   71,   71,   71,   71,   71,   71,
393
-       71,   71,   71,   71,   71,   71,   58,   28,   59,   30,
394
-       73,   62,   73,    0,   51,    0,    3,   31,   47,    0,
395
-        4,   26,   44,   42,    0,   43,   45,    1,    2,   57,
396
-       54,   50,   55,   56,   71,   71,   71,   71,   49,   71,
397
-       71,   71,   12,   71,   71,   71,   71,   71,    5,   11,
398
-       71,   71,   71,   34,   71,   71,   71,   71,   48,   33,
399
-
400
-       73,   62,   70,   46,    0,   72,    1,   71,   71,   71,
401
-       32,   71,   71,   71,   18,   71,   10,   71,   71,   25,
402
-       36,   71,   71,   71,   71,   71,   19,   38,   71,   71,
403
-        7,   71,   13,   71,   71,    6,   37,   71,   40,   16,
404
-       71,   71,   39,   71,   71,    9,   71,    8,   14,   15,
405
-       71,   17,    0
389
+        0,    0,   76,   75,   74,   36,   75,   70,   25,   28,
390
+       75,   64,   65,   23,   21,   69,   22,   66,   24,    2,
391
+       67,   68,   53,   42,   54,   72,   72,   72,   72,   61,
392
+       62,   30,   72,   72,   72,   72,   72,   72,   72,   72,
393
+       72,   72,   72,   72,   72,   72,   59,   29,   60,   31,
394
+       74,   63,   74,    0,   52,    0,    3,   32,   48,    0,
395
+        4,   27,   45,   43,    0,   44,   46,    1,    2,   58,
396
+       55,   51,   56,   57,   72,   72,   72,   72,   50,   72,
397
+       72,   72,   12,   72,   72,   72,   72,   72,    5,   11,
398
+       72,   72,   72,   72,   35,   72,   72,   72,   72,   49,
399
+
400
+       34,   74,   63,   71,   47,    0,   73,    1,   72,   72,
401
+       72,   33,   72,   72,   72,   19,   72,   10,   72,   72,
402
+       72,   26,   37,   72,   72,   72,   72,   72,   20,   39,
403
+       72,   72,    7,   72,   13,   72,   72,   72,    6,   38,
404
+       72,   41,   17,   72,   72,   40,   72,   14,   72,    9,
405
+       72,    8,   15,   16,   72,   18,    0
406 406
     } ;
407 407
 
408 408
 static const YY_CHAR yy_ec[256] =
@@ -447,49 +447,51 @@ static const YY_CHAR yy_meta[53] =
447 447
         1,    1
448 448
     } ;
449 449
 
450
-static const flex_int16_t yy_base[158] =
450
+static const flex_int16_t yy_base[162] =
451 451
     {   0,
452
-        0,   51,  171,  172,   52,   52,  165,  172,  172,   49,
453
-      160,  172,  172,   46,  146,  172,   44,  172,  145,   44,
454
-      172,  172,   42,  144,   47,    0,  134,  121,  119,  172,
455
-      172,  140,  119,  116,  116,  115,   25,   41,   37,  126,
456
-      113,  112,  110,  118,   38,  115,  172,   54,  172,  172,
457
-       75,  172,   78,  147,  172,  145,  172,  172,  172,  140,
458
-      172,  126,  172,  172,  144,  172,  172,  128,   71,  172,
459
-      172,  172,  172,  172,    0,  105,  102,   96,  172,  108,
460
-      106,   98,    0,   94,  104,   97,   92,   93,    0,    0,
461
-       93,   99,   86,    0,   85,   95,   82,   90,  172,  172,
462
-
463
-       88,  172,  172,  172,  124,  172,  108,   80,   89,   88,
464
-        0,   91,   75,   85,    0,   74,    0,   85,   85,    0,
465
-        0,   69,   73,   79,   73,   77,    0,    0,   72,   65,
466
-       64,   66,    0,   66,   55,    0,    0,   62,    0,    0,
467
-       54,   59,    0,   63,   51,    0,   45,    0,    0,    0,
468
-       51,    0,  172,  104,  106,   81,  108
452
+        0,   51,  175,  176,   52,   52,  169,  176,  176,   49,
453
+      164,  176,  176,   46,  150,  176,   44,  176,  149,   44,
454
+      176,  176,   42,  148,   47,    0,  138,  125,  123,  176,
455
+      176,  144,  123,  120,  120,  119,   25,   41,   37,  130,
456
+       44,  117,  115,  123,   39,  120,  176,   55,  176,  176,
457
+       79,  176,   83,  152,  176,  150,  176,  176,  176,  145,
458
+      176,  131,  176,  176,  149,  176,  176,  133,   62,  176,
459
+      176,  176,  176,  176,    0,  110,  107,  101,  176,  113,
460
+      111,  103,    0,   99,  109,  102,   97,   98,    0,    0,
461
+       98,  105,  103,   90,    0,   89,   99,   86,   94,  176,
462
+
463
+      176,   88,  176,  176,  176,  128,  176,  112,   84,   93,
464
+       92,    0,   95,   79,   89,    0,   78,    0,   89,   89,
465
+       76,    0,    0,   72,   76,   82,   76,   80,    0,    0,
466
+       75,   75,   74,   69,    0,   69,   59,   57,    0,    0,
467
+       65,    0,    0,   57,   61,    0,   65,    0,   53,    0,
468
+       47,    0,    0,    0,   58,    0,  176,  105,  107,   90,
469
+      109
469 470
     } ;
470 471
 
471
-static const flex_int16_t yy_def[158] =
472
+static const flex_int16_t yy_def[162] =
472 473
     {   0,
473
-      153,    1,  153,  153,  153,  153,  154,  153,  153,  153,
474
-      155,  153,  153,  153,  153,  153,  153,  153,  153,  153,
475
-      153,  153,  153,  153,  153,  156,  156,  156,  156,  153,
476
-      153,  153,  156,  156,  156,  156,  156,  156,  156,  156,
477
-      156,  156,  156,  156,  156,  156,  153,  153,  153,  153,
478
-      153,  153,  153,  153,  153,  154,  153,  153,  153,  155,
479
-      153,  153,  153,  153,  157,  153,  153,  153,  153,  153,
480
-      153,  153,  153,  153,  156,  156,  156,  156,  153,  156,
481
-      156,  156,  156,  156,  156,  156,  156,  156,  156,  156,
482
-      156,  156,  156,  156,  156,  156,  156,  156,  153,  153,
483
-
484
-      153,  153,  153,  153,  157,  153,  153,  156,  156,  156,
485
-      156,  156,  156,  156,  156,  156,  156,  156,  156,  156,
486
-      156,  156,  156,  156,  156,  156,  156,  156,  156,  156,
487
-      156,  156,  156,  156,  156,  156,  156,  156,  156,  156,
488
-      156,  156,  156,  156,  156,  156,  156,  156,  156,  156,
489
-      156,  156,    0,  153,  153,  153,  153
474
+      157,    1,  157,  157,  157,  157,  158,  157,  157,  157,
475
+      159,  157,  157,  157,  157,  157,  157,  157,  157,  157,
476
+      157,  157,  157,  157,  157,  160,  160,  160,  160,  157,
477
+      157,  157,  160,  160,  160,  160,  160,  160,  160,  160,
478
+      160,  160,  160,  160,  160,  160,  157,  157,  157,  157,
479
+      157,  157,  157,  157,  157,  158,  157,  157,  157,  159,
480
+      157,  157,  157,  157,  161,  157,  157,  157,  157,  157,
481
+      157,  157,  157,  157,  160,  160,  160,  160,  157,  160,
482
+      160,  160,  160,  160,  160,  160,  160,  160,  160,  160,
483
+      160,  160,  160,  160,  160,  160,  160,  160,  160,  157,
484
+
485
+      157,  157,  157,  157,  157,  161,  157,  157,  160,  160,
486
+      160,  160,  160,  160,  160,  160,  160,  160,  160,  160,
487
+      160,  160,  160,  160,  160,  160,  160,  160,  160,  160,
488
+      160,  160,  160,  160,  160,  160,  160,  160,  160,  160,
489
+      160,  160,  160,  160,  160,  160,  160,  160,  160,  160,
490
+      160,  160,  160,  160,  160,  160,    0,  157,  157,  157,
491
+      157
490 492
     } ;
491 493
 
492
-static const flex_int16_t yy_nxt[225] =
494
+static const flex_int16_t yy_nxt[229] =
493 495
     {   0,
494 496
         4,    5,    5,    6,    7,    8,    9,   10,   11,   12,
495 497
        13,   14,   15,   16,   17,   18,   19,   20,   21,   22,
@@ -498,27 +500,27 @@ static const flex_int16_t yy_nxt[225] =
498 500
        41,   42,   43,   44,   26,   45,   26,   46,   47,   48,
499 501
        49,   50,   51,   53,   53,   54,   58,   62,   65,   68,
500 502
        52,   69,   70,   71,   84,   66,   85,   63,   73,   74,
501
-       59,   86,   89,   55,   96,   99,  101,   53,   90,   53,
502
-       53,   97,   75,   87,  102,  152,   68,   88,   69,  101,
503
-       53,  151,  150,  149,  148,  147,  146,  102,  145,  144,
504
-
505
-      143,  142,  141,  100,   56,   56,   60,   60,  105,  105,
506
-      140,  139,  138,  137,  136,  135,  134,  133,  132,  131,
507
-      130,  129,  128,  127,  126,  107,  106,  125,  124,  123,
508
-      122,  121,  120,  119,  118,  117,  116,  115,  114,  113,
509
-      112,  111,  110,  109,  108,  107,  106,  104,   61,   57,
510
-      103,   98,   95,   94,   93,   92,   91,   83,   82,   81,
511
-       80,   79,   78,   77,   76,   72,   67,   64,   61,   57,
512
-      153,    3,  153,  153,  153,  153,  153,  153,  153,  153,
513
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
514
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
515
-
516
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
517
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
518
-      153,  153,  153,  153
503
+       59,   86,   89,   55,   92,   97,  100,   68,   90,   69,
504
+      102,   53,   98,   87,   53,   53,   93,   88,  103,  102,
505
+       53,   75,  156,  155,  154,  153,  152,  103,  151,  150,
506
+
507
+      149,  148,  147,  146,  101,   56,   56,   60,   60,  106,
508
+      106,  145,  144,  143,  142,  141,  140,  139,  138,  137,
509
+      136,  135,  134,  133,  132,  131,  130,  129,  128,  108,
510
+      107,  127,  126,  125,  124,  123,  122,  121,  120,  119,
511
+      118,  117,  116,  115,  114,  113,  112,  111,  110,  109,
512
+      108,  107,  105,   61,   57,  104,   99,   96,   95,   94,
513
+       91,   83,   82,   81,   80,   79,   78,   77,   76,   72,
514
+       67,   64,   61,   57,  157,    3,  157,  157,  157,  157,
515
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
516
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
517
+
518
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
519
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
520
+      157,  157,  157,  157,  157,  157,  157,  157
519 521
     } ;
520 522
 
521
-static const flex_int16_t yy_chk[225] =
523
+static const flex_int16_t yy_chk[229] =
522 524
     {   0,
523 525
         1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
524 526
         1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
@@ -527,24 +529,24 @@ static const flex_int16_t yy_chk[225] =
527 529
         1,    1,    1,    1,    1,    1,    1,    1,    1,    1,
528 530
         1,    1,    2,    5,    5,    6,   10,   14,   17,   20,
529 531
         2,   20,   23,   23,   37,   17,   37,   14,   25,   25,
530
-       10,   38,   39,    6,   45,   48,   51,   51,   39,   53,
531
-       53,   45,  156,   38,   51,  151,   69,   38,   69,  101,
532
-      101,  147,  145,  144,  142,  141,  138,  101,  135,  134,
533
-
534
-      132,  131,  130,   48,  154,  154,  155,  155,  157,  157,
535
-      129,  126,  125,  124,  123,  122,  119,  118,  116,  114,
536
-      113,  112,  110,  109,  108,  107,  105,   98,   97,   96,
537
-       95,   93,   92,   91,   88,   87,   86,   85,   84,   82,
538
-       81,   80,   78,   77,   76,   68,   65,   62,   60,   56,
539
-       54,   46,   44,   43,   42,   41,   40,   36,   35,   34,
540
-       33,   32,   29,   28,   27,   24,   19,   15,   11,    7,
541
-        3,  153,  153,  153,  153,  153,  153,  153,  153,  153,
542
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
543
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
544
-
545
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
546
-      153,  153,  153,  153,  153,  153,  153,  153,  153,  153,
547
-      153,  153,  153,  153
532
+       10,   38,   39,    6,   41,   45,   48,   69,   39,   69,
533
+       51,   51,   45,   38,   53,   53,   41,   38,   51,  102,
534
+      102,  160,  155,  151,  149,  147,  145,  102,  144,  141,
535
+
536
+      138,  137,  136,  134,   48,  158,  158,  159,  159,  161,
537
+      161,  133,  132,  131,  128,  127,  126,  125,  124,  121,
538
+      120,  119,  117,  115,  114,  113,  111,  110,  109,  108,
539
+      106,   99,   98,   97,   96,   94,   93,   92,   91,   88,
540
+       87,   86,   85,   84,   82,   81,   80,   78,   77,   76,
541
+       68,   65,   62,   60,   56,   54,   46,   44,   43,   42,
542
+       40,   36,   35,   34,   33,   32,   29,   28,   27,   24,
543
+       19,   15,   11,    7,    3,  157,  157,  157,  157,  157,
544
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
545
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
546
+
547
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
548
+      157,  157,  157,  157,  157,  157,  157,  157,  157,  157,
549
+      157,  157,  157,  157,  157,  157,  157,  157
548 550
     } ;
549 551
 
550 552
 static yy_state_type yy_last_accepting_state;
@@ -621,7 +623,7 @@ static void update_loc(YYLTYPE *yylloc, char *yytext){
621 623
 
622 624
 #define YY_USER_ACTION update_loc(yylloc, yytext);
623 625
 
624
-#line 624 "lex.yy.c"
626
+#line 626 "lex.yy.c"
625 627
 /* This is the right way to do it, but it keeps generating token $undefined.
626 628
 
627 629
 %x STRING
@@ -637,7 +639,7 @@ static void update_loc(YYLTYPE *yylloc, char *yytext){
637 639
 <STRING>. { str_putc(*yytext); }
638 640
 
639 641
 */
640
-#line 640 "lex.yy.c"
642
+#line 642 "lex.yy.c"
641 643
 
642 644
 #define INITIAL 0
643 645
 
@@ -878,7 +880,7 @@ YY_DECL
878 880
 #line 85 "tokenizer.lex"
879 881
 
880 882
 
881
-#line 881 "lex.yy.c"
883
+#line 883 "lex.yy.c"
882 884
 
883 885
 	while ( /*CONSTCOND*/1 )		/* loops until end-of-file is reached */
884 886
 		{
@@ -906,13 +908,13 @@ yy_match:
906 908
 			while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
907 909
 				{
908 910
 				yy_current_state = (int) yy_def[yy_current_state];
909
-				if ( yy_current_state >= 154 )
911
+				if ( yy_current_state >= 158 )
910 912
 					yy_c = yy_meta[yy_c];
911 913
 				}
912 914
 			yy_current_state = yy_nxt[yy_base[yy_current_state] + yy_c];
913 915
 			++yy_cp;
914 916
 			}
915
-		while ( yy_base[yy_current_state] != 172 );
917
+		while ( yy_base[yy_current_state] != 176 );
916 918
 
917 919
 yy_find_action:
918 920
 		yy_act = yy_accept[yy_current_state];
@@ -1003,57 +1005,57 @@ YY_RULE_SETUP
1003 1005
 case 14:
1004 1006
 YY_RULE_SETUP
1005 1007
 #line 112 "tokenizer.lex"
1006
-{ return LAMBDA; }
1008
+{ return MACRO; }
1007 1009
 	YY_BREAK
1008 1010
 case 15:
1009 1011
 YY_RULE_SETUP
1010 1012
 #line 114 "tokenizer.lex"
1011
-{ return RETURN; }
1013
+{ return LAMBDA; }
1012 1014
 	YY_BREAK
1013 1015
 case 16:
1014 1016
 YY_RULE_SETUP
1015 1017
 #line 116 "tokenizer.lex"
1016
-{ return BREAK; }
1018
+{ return RETURN; }
1017 1019
 	YY_BREAK
1018 1020
 case 17:
1019 1021
 YY_RULE_SETUP
1020 1022
 #line 118 "tokenizer.lex"
1021
-{ return CONTINUE; }
1023
+{ return BREAK; }
1022 1024
 	YY_BREAK
1023 1025
 case 18:
1024 1026
 YY_RULE_SETUP
1025 1027
 #line 120 "tokenizer.lex"
1026
-{ return END; }
1028
+{ return CONTINUE; }
1027 1029
 	YY_BREAK
1028 1030
 case 19:
1029 1031
 YY_RULE_SETUP
1030 1032
 #line 122 "tokenizer.lex"
1031
-{ return NONE; }
1033
+{ return END; }
1032 1034
 	YY_BREAK
1033 1035
 case 20:
1034 1036
 YY_RULE_SETUP
1035 1037
 #line 124 "tokenizer.lex"
1036
-{ return PLUS; }
1038
+{ return NONE; }
1037 1039
 	YY_BREAK
1038 1040
 case 21:
1039 1041
 YY_RULE_SETUP
1040 1042
 #line 126 "tokenizer.lex"
1041
-{ return MINUS; }
1043
+{ return PLUS; }
1042 1044
 	YY_BREAK
1043 1045
 case 22:
1044 1046
 YY_RULE_SETUP
1045 1047
 #line 128 "tokenizer.lex"
1046
-{ return STAR; }
1048
+{ return MINUS; }
1047 1049
 	YY_BREAK
1048 1050
 case 23:
1049 1051
 YY_RULE_SETUP
1050 1052
 #line 130 "tokenizer.lex"
1051
-{ return SLASH; }
1053
+{ return STAR; }
1052 1054
 	YY_BREAK
1053 1055
 case 24:
1054 1056
 YY_RULE_SETUP
1055 1057
 #line 132 "tokenizer.lex"
1056
-{ return PERCENT; }
1058
+{ return SLASH; }
1057 1059
 	YY_BREAK
1058 1060
 case 25:
1059 1061
 YY_RULE_SETUP
@@ -1063,32 +1065,32 @@ YY_RULE_SETUP
1063 1065
 case 26:
1064 1066
 YY_RULE_SETUP
1065 1067
 #line 136 "tokenizer.lex"
1066
-{ return DSTAR; }
1068
+{ return PERCENT; }
1067 1069
 	YY_BREAK
1068 1070
 case 27:
1069 1071
 YY_RULE_SETUP
1070 1072
 #line 138 "tokenizer.lex"
1071
-{ return BAND; }
1073
+{ return DSTAR; }
1072 1074
 	YY_BREAK
1073 1075
 case 28:
1074 1076
 YY_RULE_SETUP
1075 1077
 #line 140 "tokenizer.lex"
1076
-{ return BOR; }
1078
+{ return BAND; }
1077 1079
 	YY_BREAK
1078 1080
 case 29:
1079 1081
 YY_RULE_SETUP
1080 1082
 #line 142 "tokenizer.lex"
1081
-{ return BXOR; }
1083
+{ return BOR; }
1082 1084
 	YY_BREAK
1083 1085
 case 30:
1084 1086
 YY_RULE_SETUP
1085 1087
 #line 144 "tokenizer.lex"
1086
-{ return BNOT; }
1088
+{ return BXOR; }
1087 1089
 	YY_BREAK
1088 1090
 case 31:
1089 1091
 YY_RULE_SETUP
1090 1092
 #line 146 "tokenizer.lex"
1091
-{ return LAND; }
1093
+{ return BNOT; }
1092 1094
 	YY_BREAK
1093 1095
 case 32:
1094 1096
 YY_RULE_SETUP
@@ -1098,7 +1100,7 @@ YY_RULE_SETUP
1098 1100
 case 33:
1099 1101
 YY_RULE_SETUP
1100 1102
 #line 150 "tokenizer.lex"
1101
-{ return LOR; }
1103
+{ return LAND; }
1102 1104
 	YY_BREAK
1103 1105
 case 34:
1104 1106
 YY_RULE_SETUP
@@ -1108,7 +1110,7 @@ YY_RULE_SETUP
1108 1110
 case 35:
1109 1111
 YY_RULE_SETUP
1110 1112
 #line 154 "tokenizer.lex"
1111
-{ return LNOT; }
1113
+{ return LOR; }
1112 1114
 	YY_BREAK
1113 1115
 case 36:
1114 1116
 YY_RULE_SETUP
@@ -1118,7 +1120,7 @@ YY_RULE_SETUP
1118 1120
 case 37:
1119 1121
 YY_RULE_SETUP
1120 1122
 #line 158 "tokenizer.lex"
1121
-{ *yylval = malloc(sizeof(long)); *((long *) *yylval) = 1; return INT;  }
1123
+{ return LNOT; }
1122 1124
 	YY_BREAK
1123 1125
 case 38:
1124 1126
 YY_RULE_SETUP
@@ -1128,7 +1130,7 @@ YY_RULE_SETUP
1128 1130
 case 39:
1129 1131
 YY_RULE_SETUP
1130 1132
 #line 162 "tokenizer.lex"
1131
-{ *yylval = malloc(sizeof(long)); *((long *) *yylval) = 0; return INT;  }
1133
+{ *yylval = malloc(sizeof(long)); *((long *) *yylval) = 1; return INT;  }
1132 1134
 	YY_BREAK
1133 1135
 case 40:
1134 1136
 YY_RULE_SETUP
@@ -1138,176 +1140,181 @@ YY_RULE_SETUP
1138 1140
 case 41:
1139 1141
 YY_RULE_SETUP
1140 1142
 #line 166 "tokenizer.lex"
1141
-{ return ASSIGN; }
1143
+{ *yylval = malloc(sizeof(long)); *((long *) *yylval) = 0; return INT;  }
1142 1144
 	YY_BREAK
1143 1145
 case 42:
1144 1146
 YY_RULE_SETUP
1145 1147
 #line 168 "tokenizer.lex"
1146
-{ return ASSIGNPLUS; }
1148
+{ return ASSIGN; }
1147 1149
 	YY_BREAK
1148 1150
 case 43:
1149 1151
 YY_RULE_SETUP
1150 1152
 #line 170 "tokenizer.lex"
1151
-{ return ASSIGNMINUS; }
1153
+{ return ASSIGNPLUS; }
1152 1154
 	YY_BREAK
1153 1155
 case 44:
1154 1156
 YY_RULE_SETUP
1155 1157
 #line 172 "tokenizer.lex"
1156
-{ return ASSIGNSTAR; }
1158
+{ return ASSIGNMINUS; }
1157 1159
 	YY_BREAK
1158 1160
 case 45:
1159 1161
 YY_RULE_SETUP
1160 1162
 #line 174 "tokenizer.lex"
1161
-{ return ASSIGNSLASH; }
1163
+{ return ASSIGNSTAR; }
1162 1164
 	YY_BREAK
1163 1165
 case 46:
1164 1166
 YY_RULE_SETUP
1165 1167
 #line 176 "tokenizer.lex"
1166
-{ return ASSIGNDSTAR; }
1168
+{ return ASSIGNSLASH; }
1167 1169
 	YY_BREAK
1168 1170
 case 47:
1169 1171
 YY_RULE_SETUP
1170 1172
 #line 178 "tokenizer.lex"
1171
-{ return ASSIGNBAND; }
1173
+{ return ASSIGNDSTAR; }
1172 1174
 	YY_BREAK
1173 1175
 case 48:
1174 1176
 YY_RULE_SETUP
1175 1177
 #line 180 "tokenizer.lex"
1176
-{ return ASSIGNBOR; }
1178
+{ return ASSIGNBAND; }
1177 1179
 	YY_BREAK
1178 1180
 case 49:
1179 1181
 YY_RULE_SETUP
1180 1182
 #line 182 "tokenizer.lex"
1181
-{ return ASSIGNBXOR; }
1183
+{ return ASSIGNBOR; }
1182 1184
 	YY_BREAK
1183 1185
 case 50:
1184 1186
 YY_RULE_SETUP
1185 1187
 #line 184 "tokenizer.lex"
1186
-{ return EQUAL; }
1188
+{ return ASSIGNBXOR; }
1187 1189
 	YY_BREAK
1188 1190
 case 51:
1189 1191
 YY_RULE_SETUP
1190 1192
 #line 186 "tokenizer.lex"
1191
-{ return NEQUAL; }
1193
+{ return EQUAL; }
1192 1194
 	YY_BREAK
1193 1195
 case 52:
1194 1196
 YY_RULE_SETUP
1195 1197
 #line 188 "tokenizer.lex"
1196
-{ return LESS; }
1198
+{ return NEQUAL; }
1197 1199
 	YY_BREAK
1198 1200
 case 53:
1199 1201
 YY_RULE_SETUP
1200 1202
 #line 190 "tokenizer.lex"
1201
-{ return GREATER; }
1203
+{ return LESS; }
1202 1204
 	YY_BREAK
1203 1205
 case 54:
1204 1206
 YY_RULE_SETUP
1205 1207
 #line 192 "tokenizer.lex"
1206
-{ return LESSEQ; }
1208
+{ return GREATER; }
1207 1209
 	YY_BREAK
1208 1210
 case 55:
1209 1211
 YY_RULE_SETUP
1210 1212
 #line 194 "tokenizer.lex"
1211
-{ return GREATEREQ; }
1213
+{ return LESSEQ; }
1212 1214
 	YY_BREAK
1213 1215
 case 56:
1214 1216
 YY_RULE_SETUP
1215 1217
 #line 196 "tokenizer.lex"
1216
-{ return RSHIFT; }
1218
+{ return GREATEREQ; }
1217 1219
 	YY_BREAK
1218 1220
 case 57:
1219 1221
 YY_RULE_SETUP
1220 1222
 #line 198 "tokenizer.lex"
1221
-{ return LSHIFT; }
1223
+{ return RSHIFT; }
1222 1224
 	YY_BREAK
1223 1225
 case 58:
1224 1226
 YY_RULE_SETUP
1225 1227
 #line 200 "tokenizer.lex"
1226
-{ return LBRACE; }
1228
+{ return LSHIFT; }
1227 1229
 	YY_BREAK
1228 1230
 case 59:
1229 1231
 YY_RULE_SETUP
1230 1232
 #line 202 "tokenizer.lex"
1231
-{ return RBRACE; }
1233
+{ return LBRACE; }
1232 1234
 	YY_BREAK
1233 1235
 case 60:
1234 1236
 YY_RULE_SETUP
1235 1237
 #line 204 "tokenizer.lex"
1236
-{ return LBRACKET; }
1238
+{ return RBRACE; }
1237 1239
 	YY_BREAK
1238 1240
 case 61:
1239 1241
 YY_RULE_SETUP
1240 1242
 #line 206 "tokenizer.lex"
1241
-{ return RBRACKET; }
1243
+{ return LBRACKET; }
1242 1244
 	YY_BREAK
1243 1245
 case 62:
1244 1246
 YY_RULE_SETUP
1245 1247
 #line 208 "tokenizer.lex"
1246
-{ return BLPAREN; } /* "Breaking" paren, not allowed to introduce a call_expr */
1248
+{ return RBRACKET; }
1247 1249
 	YY_BREAK
1248 1250
 case 63:
1249 1251
 YY_RULE_SETUP
1250 1252
 #line 210 "tokenizer.lex"
1251
-{ return LPAREN; } 
1253
+{ return BLPAREN; } /* "Breaking" paren, not allowed to introduce a call_expr */
1252 1254
 	YY_BREAK
1253 1255
 case 64:
1254 1256
 YY_RULE_SETUP
1255 1257
 #line 212 "tokenizer.lex"
1256
-{ return RPAREN; }
1258
+{ return LPAREN; } 
1257 1259
 	YY_BREAK
1258 1260
 case 65:
1259 1261
 YY_RULE_SETUP
1260 1262
 #line 214 "tokenizer.lex"
1261
-{ return DOT; }
1263
+{ return RPAREN; }
1262 1264
 	YY_BREAK
1263 1265
 case 66:
1264 1266
 YY_RULE_SETUP
1265 1267
 #line 216 "tokenizer.lex"
1266
-{ return COLON; }
1268
+{ return DOT; }
1267 1269
 	YY_BREAK
1268 1270
 case 67:
1269 1271
 YY_RULE_SETUP
1270 1272
 #line 218 "tokenizer.lex"
1271
-{ return SEMICOLON; }
1273
+{ return COLON; }
1272 1274
 	YY_BREAK
1273 1275
 case 68:
1274 1276
 YY_RULE_SETUP
1275 1277
 #line 220 "tokenizer.lex"
1276
-{ return COMMA; }
1278
+{ return SEMICOLON; }
1277 1279
 	YY_BREAK
1278 1280
 case 69:
1279 1281
 YY_RULE_SETUP
1280 1282
 #line 222 "tokenizer.lex"
1281
-{ return POUND; }
1283
+{ return COMMA; }
1282 1284
 	YY_BREAK
1283 1285
 case 70:
1284 1286
 YY_RULE_SETUP
1285 1287
 #line 224 "tokenizer.lex"
1286
-{ return TBANG; }
1288
+{ return POUND; }
1287 1289
 	YY_BREAK
1288 1290
 case 71:
1289 1291
 YY_RULE_SETUP
1290 1292
 #line 226 "tokenizer.lex"
1291
-{ *yylval = (void *) strdup(yytext); return IDENT; }
1293
+{ return TBANG; }
1292 1294
 	YY_BREAK
1293 1295
 case 72:
1294
-/* rule 72 can match eol */
1295 1296
 YY_RULE_SETUP
1296 1297
 #line 228 "tokenizer.lex"
1297
-/* Skip comments */
1298
+{ *yylval = (void *) strdup(yytext); return IDENT; }
1298 1299
 	YY_BREAK
1299 1300
 case 73:
1300 1301
 /* rule 73 can match eol */
1301 1302
 YY_RULE_SETUP
1302 1303
 #line 230 "tokenizer.lex"
1303
-/* Skip whitespace */
1304
+/* Skip comments */
1304 1305
 	YY_BREAK
1305 1306
 case 74:
1307
+/* rule 74 can match eol */
1306 1308
 YY_RULE_SETUP
1307 1309
 #line 232 "tokenizer.lex"
1310
+/* Skip whitespace */
1311
+	YY_BREAK
1312
+case 75:
1313
+YY_RULE_SETUP
1314
+#line 234 "tokenizer.lex"
1308 1315
 ECHO;
1309 1316
 	YY_BREAK
1310
-#line 1310 "lex.yy.c"
1317
+#line 1317 "lex.yy.c"
1311 1318
 case YY_STATE_EOF(INITIAL):
1312 1319
 	yyterminate();
1313 1320
 
@@ -1605,7 +1612,7 @@ static int yy_get_next_buffer (void)
1605 1612
 		while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
1606 1613
 			{
1607 1614
 			yy_current_state = (int) yy_def[yy_current_state];
1608
-			if ( yy_current_state >= 154 )
1615
+			if ( yy_current_state >= 158 )
1609 1616
 				yy_c = yy_meta[yy_c];
1610 1617
 			}
1611 1618
 		yy_current_state = yy_nxt[yy_base[yy_current_state] + yy_c];
@@ -1633,11 +1640,11 @@ static int yy_get_next_buffer (void)
1633 1640
 	while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state )
1634 1641
 		{
1635 1642
 		yy_current_state = (int) yy_def[yy_current_state];
1636
-		if ( yy_current_state >= 154 )
1643
+		if ( yy_current_state >= 158 )
1637 1644
 			yy_c = yy_meta[yy_c];
1638 1645
 		}
1639 1646
 	yy_current_state = yy_nxt[yy_base[yy_current_state] + yy_c];
1640
-	yy_is_jam = (yy_current_state == 153);
1647
+	yy_is_jam = (yy_current_state == 157);
1641 1648
 
1642 1649
 		return yy_is_jam ? 0 : yy_current_state;
1643 1650
 }
@@ -2315,7 +2322,7 @@ void yyfree (void * ptr )
2315 2322
 
2316 2323
 #define YYTABLES_NAME "yytables"
2317 2324
 
2318
-#line 232 "tokenizer.lex"
2325
+#line 234 "tokenizer.lex"
2319 2326
 
2320 2327
 
2321 2328
 int yywrap(void) {

+ 10
- 0
object.c Прегледај датотеку

@@ -526,6 +526,16 @@ sol_object_t *sol_new_cfunc(sol_state_t *state, sol_cfunc_t cfunc, char *name) {
526 526
 	return res;
527 527
 }
528 528
 
529
+sol_object_t *sol_new_cmacro(sol_state_t *state, sol_cfunc_t cfunc, char *name) {
530
+	sol_object_t *res = sol_alloc_object(state);
531
+	res->type = SOL_CMACRO;
532
+	res->ops = &(state->CMacroOps);
533
+	res->cfunc = cfunc;
534
+	res->cfname = name ? strdup(name) : NULL;
535
+	sol_init_object(state, res);
536
+	return res;
537
+}
538
+
529 539
 sol_object_t *sol_f_cfunc_free(sol_state_t *state, sol_object_t *cfunc) {
530 540
 	free(cfunc->cfname);
531 541
 	return cfunc;

+ 5851
- 5193
parser.output
Разлика између датотеке није приказан због своје велике величине
Прегледај датотеку


+ 558
- 513
parser.tab.c
Разлика између датотеке није приказан због своје велике величине
Прегледај датотеку


+ 54
- 53
parser.tab.h Прегледај датотеку

@@ -54,59 +54,60 @@ extern int yydebug;
54 54
     IN = 264,
55 55
     DO = 265,
56 56
     FUNC = 266,
57
-    LAMBDA = 267,
58
-    RETURN = 268,
59
-    BREAK = 269,
60
-    CONTINUE = 270,
61
-    END = 271,
62
-    NONE = 272,
63
-    IDENT = 273,
64
-    INT = 274,
65
-    FLOAT = 275,
66
-    STRING = 276,
67
-    PLUS = 277,
68
-    MINUS = 278,
69
-    STAR = 279,
70
-    SLASH = 280,
71
-    PERCENT = 281,
72
-    DSTAR = 282,
73
-    BAND = 283,
74
-    BOR = 284,
75
-    BXOR = 285,
76
-    BNOT = 286,
77
-    LAND = 287,
78
-    LOR = 288,
79
-    LNOT = 289,
80
-    ASSIGN = 290,
81
-    ASSIGNPLUS = 291,
82
-    ASSIGNMINUS = 292,
83
-    ASSIGNSTAR = 293,
84
-    ASSIGNSLASH = 294,
85
-    ASSIGNDSTAR = 295,
86
-    ASSIGNBAND = 296,
87
-    ASSIGNBOR = 297,
88
-    ASSIGNBXOR = 298,
89
-    EQUAL = 299,
90
-    NEQUAL = 300,
91
-    LESS = 301,
92
-    GREATER = 302,
93
-    LESSEQ = 303,
94
-    GREATEREQ = 304,
95
-    RSHIFT = 305,
96
-    LSHIFT = 306,
97
-    LBRACE = 307,
98
-    RBRACE = 308,
99
-    BLPAREN = 309,
100
-    LPAREN = 310,
101
-    RPAREN = 311,
102
-    LBRACKET = 312,
103
-    RBRACKET = 313,
104
-    DOT = 314,
105
-    COLON = 315,
106
-    SEMICOLON = 316,
107
-    COMMA = 317,
108
-    POUND = 318,
109
-    TBANG = 319
57
+    MACRO = 267,
58
+    LAMBDA = 268,
59
+    RETURN = 269,
60
+    BREAK = 270,
61
+    CONTINUE = 271,
62
+    END = 272,
63
+    NONE = 273,
64
+    IDENT = 274,
65
+    INT = 275,
66
+    FLOAT = 276,
67
+    STRING = 277,
68
+    PLUS = 278,
69
+    MINUS = 279,
70
+    STAR = 280,
71
+    SLASH = 281,
72
+    PERCENT = 282,
73
+    DSTAR = 283,
74
+    BAND = 284,
75
+    BOR = 285,
76
+    BXOR = 286,
77
+    BNOT = 287,
78
+    LAND = 288,
79
+    LOR = 289,
80
+    LNOT = 290,
81
+    ASSIGN = 291,
82
+    ASSIGNPLUS = 292,
83
+    ASSIGNMINUS = 293,
84
+    ASSIGNSTAR = 294,
85
+    ASSIGNSLASH = 295,
86
+    ASSIGNDSTAR = 296,
87
+    ASSIGNBAND = 297,
88
+    ASSIGNBOR = 298,
89
+    ASSIGNBXOR = 299,
90
+    EQUAL = 300,
91
+    NEQUAL = 301,
92
+    LESS = 302,
93
+    GREATER = 303,
94
+    LESSEQ = 304,
95
+    GREATEREQ = 305,
96
+    RSHIFT = 306,
97
+    LSHIFT = 307,
98
+    LBRACE = 308,
99
+    RBRACE = 309,
100
+    BLPAREN = 310,
101
+    LPAREN = 311,
102
+    RPAREN = 312,
103
+    LBRACKET = 313,
104
+    RBRACKET = 314,
105
+    DOT = 315,
106
+    COLON = 316,
107
+    SEMICOLON = 317,
108
+    COMMA = 318,
109
+    POUND = 319,
110
+    TBANG = 320
110 111
   };
111 112
 #endif
112 113
 

+ 24
- 1
parser.y Прегледај датотеку

@@ -23,7 +23,7 @@ void yyerror(loc_t *, stmt_node **, char *);
23 23
 
24 24
 %token IF THEN ELSEIF ELSE
25 25
 %token WHILE FOR IN DO
26
-%token FUNC LAMBDA RETURN BREAK CONTINUE
26
+%token FUNC MACRO LAMBDA RETURN BREAK CONTINUE
27 27
 %token END NONE
28 28
 %token IDENT
29 29
 %token INT FLOAT STRING
@@ -392,6 +392,7 @@ funcdecl_expr:
392 392
 	AS_EX($$)->funcdecl->params = $4;
393 393
 	AS_EX($$)->funcdecl->anno = $6;
394 394
 	AS_EX($$)->funcdecl->body = $7;
395
+	AS_EX($$)->funcdecl->flags = 0;
395 396
 }
396 397
 | FUNC any_lparen param_list RPAREN maybe_anno stmt_list END {
397 398
 	$$ = NEW_EX();
@@ -401,6 +402,27 @@ funcdecl_expr:
401 402
 	AS_EX($$)->funcdecl->params = $3;
402 403
 	AS_EX($$)->funcdecl->anno = $5;
403 404
 	AS_EX($$)->funcdecl->body = $6;
405
+	AS_EX($$)->funcdecl->flags = 0;
406
+}
407
+| MACRO IDENT any_lparen param_list RPAREN maybe_anno stmt_list END {
408
+	$$ = NEW_EX();
409
+	AS_EX($$)->type = EX_FUNCDECL;
410
+	AS_EX($$)->funcdecl = NEW(funcdecl_node);
411
+	AS_EX($$)->funcdecl->name = $2;
412
+	AS_EX($$)->funcdecl->params = $4;
413
+	AS_EX($$)->funcdecl->anno = $6;
414
+	AS_EX($$)->funcdecl->body = $7;
415
+	AS_EX($$)->funcdecl->flags = FUNC_IS_MACRO;
416
+}
417
+| MACRO any_lparen param_list RPAREN maybe_anno stmt_list END {
418
+	$$ = NEW_EX();
419
+	AS_EX($$)->type = EX_FUNCDECL;
420
+	AS_EX($$)->funcdecl = NEW(funcdecl_node);
421
+	AS_EX($$)->funcdecl->name = NULL;
422
+	AS_EX($$)->funcdecl->params = $3;
423
+	AS_EX($$)->funcdecl->anno = $5;
424
+	AS_EX($$)->funcdecl->body = $6;
425
+	AS_EX($$)->funcdecl->flags = FUNC_IS_MACRO;
404 426
 }
405 427
 | LAMBDA any_lparen param_list RPAREN maybe_anno expr END {
406 428
 	$$ = NEW_EX();
@@ -413,6 +435,7 @@ funcdecl_expr:
413 435
 	AS_EX($$)->funcdecl->body->type = ST_RET;
414 436
 	AS_EX($$)->funcdecl->body->ret = NEW(ret_node);
415 437
 	AS_EX($$)->funcdecl->body->ret->ret = $6;
438
+	AS_EX($$)->funcdecl->flags = 0;
416 439
 }
417 440
 | index_expr { $$ = $1; }
418 441
 ;

+ 25
- 13
runtime.c Прегледај датотеку

@@ -187,6 +187,7 @@ expr_node *ex_copy(expr_node *old) {
187 187
 			new->funcdecl->params = pl_copy(old->funcdecl->params);
188 188
 			new->funcdecl->anno = ex_copy(old->funcdecl->anno);
189 189
 			new->funcdecl->body = st_copy(old->funcdecl->body);
190
+			new->funcdecl->flags = old->funcdecl->flags;
190 191
 			break;
191 192
 
192 193
 		case EX_IFELSE:
@@ -807,7 +808,11 @@ sol_object_t *sol_eval_inner(sol_state_t *state, expr_node *expr, jmp_buf jmp) {
807 808
 			cure = expr->call->args;
808 809
 			while(cure) {
809 810
 				if(cure->expr) {
810
-					sol_list_insert(state, list, sol_list_len(state, list), sol_eval_inner(state, cure->expr, jmp));
811
+					if(value->ops->tflags & SOL_TF_NO_EVAL_CALL_ARGS) {
812
+						sol_list_insert(state, list, sol_list_len(state, list), sol_new_exprnode(state, cure->expr));
813
+					} else {
814
+						sol_list_insert(state, list, sol_list_len(state, list), sol_eval_inner(state, cure->expr, jmp));
815
+					}
811 816
 				}
812 817
 				ERR_CHECK(state);
813 818
 				cure = cure->next;
@@ -820,7 +825,7 @@ sol_object_t *sol_eval_inner(sol_state_t *state, expr_node *expr, jmp_buf jmp) {
820 825
 			break;
821 826
 
822 827
 		case EX_FUNCDECL:
823
-			res = sol_new_func(state, expr->funcdecl->params ? expr->funcdecl->params->args : NULL, expr->funcdecl->body, expr->funcdecl->name, expr->funcdecl->params, expr->funcdecl->anno);
828
+			res = sol_new_func(state, expr->funcdecl->params ? expr->funcdecl->params->args : NULL, expr->funcdecl->body, expr->funcdecl->name, expr->funcdecl->params, expr->funcdecl->anno, expr->funcdecl->flags);
824 829
 			ERR_CHECK(state);
825 830
 			if(expr->funcdecl->name) {
826 831
 				sol_state_assign_l_name(state, expr->funcdecl->name, res);
@@ -847,13 +852,14 @@ sol_object_t *sol_eval_inner(sol_state_t *state, expr_node *expr, jmp_buf jmp) {
847 852
 			break;
848 853
 
849 854
 		case EX_LOOP:
850
-			sol_obj_free(state->loopvalue);
851
-			state->loopvalue = sol_new_list(state);
855
+			left = state->loopvalue;
856
+			res = sol_new_list(state);
852 857
 			value = sol_eval_inner(state, expr->loop->cond, jmp);
853 858
 			vint = sol_cast_int(state, value);
854 859
 			while(vint->ival) {
855 860
 				sol_obj_free(value);
856 861
 				sol_obj_free(vint);
862
+				state->loopvalue = res;
857 863
 				sol_exec(state, expr->loop->loop);
858 864
 				if(state->ret || state->sflag == SF_BREAKING || sol_has_error(state)) {
859 865
 					value = sol_incref(state->None);
@@ -867,12 +873,13 @@ sol_object_t *sol_eval_inner(sol_state_t *state, expr_node *expr, jmp_buf jmp) {
867 873
 			state->sflag = SF_NORMAL;
868 874
 			sol_obj_free(value);
869 875
 			sol_obj_free(vint);
870
-			return sol_incref(state->loopvalue);
876
+			state->loopvalue = left;
877
+			return sol_incref(res);
871 878
 			break;
872 879
 
873 880
 		case EX_ITER:
874
-			sol_obj_free(state->loopvalue);
875
-			state->loopvalue = sol_new_list(state);
881
+			left = state->loopvalue;
882
+			res = sol_new_list(state);
876 883
 			value = sol_eval_inner(state, expr->iter->iter, jmp);
877 884
 			if(value->ops->iter && value->ops->iter != sol_f_not_impl) {
878 885
 				list = sol_new_list(state);
@@ -893,6 +900,7 @@ sol_object_t *sol_eval_inner(sol_state_t *state, expr_node *expr, jmp_buf jmp) {
893 900
 			item = CALL_METHOD(state, iter, call, list);
894 901
 			while(item != state->None) {
895 902
 				sol_state_assign_l_name(state, expr->iter->var, item);
903
+				state->loopvalue = res;
896 904
 				sol_exec(state, expr->iter->loop);
897 905
 				sol_obj_free(item);
898 906
 				if(state->ret || state->sflag == SF_BREAKING || sol_has_error(state)) {
@@ -902,12 +910,16 @@ sol_object_t *sol_eval_inner(sol_state_t *state, expr_node *expr, jmp_buf jmp) {
902 910
 				state->sflag = SF_NORMAL;
903 911
 				item = CALL_METHOD(state, iter, call, list);
904 912
 			}
913
+			if(state->sflag == SF_BREAKING) {
914
+				res = state->loopvalue;
915
+			}
905 916
 			state->sflag = SF_NORMAL;
906 917
 			sol_obj_free(iter);
907 918
 			sol_obj_free(value);
908 919
 			sol_obj_free(list);
909 920
 			sol_obj_free(item);
910
-			return sol_incref(state->loopvalue);
921
+			state->loopvalue = left;
922
+			return sol_incref(res);
911 923
 			break;
912 924
 	}
913 925
 	printf("WARNING: Unhandled expression (type %d) returning None\n", expr->type);
@@ -993,7 +1005,7 @@ void sol_exec(sol_state_t *state, stmt_node *stmt) {
993 1005
 }
994 1006
 
995 1007
 sol_object_t *sol_f_func_call(sol_state_t *state, sol_object_t *args) {
996
-	sol_object_t *res, *scope, *value, *key;
1008
+	sol_object_t *res, *scope, *value, *key, *tmp;
997 1009
 	identlist_node *curi;
998 1010
 	dsl_seq_iter *iter;
999 1011
 	int argcnt = 0;
@@ -1003,7 +1015,7 @@ sol_object_t *sol_f_func_call(sol_state_t *state, sol_object_t *args) {
1003 1015
 		return sol_incref(state->None);
1004 1016
 	}
1005 1017
 	value = dsl_seq_iter_at(iter);
1006
-	if(!value || !sol_is_func(value)) {
1018
+	if(!value || !(sol_is_func(value) || sol_is_macro(value))) {
1007 1019
 		printf("WARNING: Function call without function as first parameter\n");
1008 1020
 		return sol_incref(state->None);
1009 1021
 	}
@@ -1058,7 +1070,7 @@ sol_object_t *sol_f_func_call(sol_state_t *state, sol_object_t *args) {
1058 1070
 	return res;
1059 1071
 }
1060 1072
 
1061
-sol_object_t *sol_new_func(sol_state_t *state, identlist_node *identlist, stmt_node *body, char *name, paramlist_node *params, expr_node *func_anno) {
1073
+sol_object_t *sol_new_func(sol_state_t *state, identlist_node *identlist, stmt_node *body, char *name, paramlist_node *params, expr_node *func_anno, unsigned short flags) {
1062 1074
 	identlist_node *cura;
1063 1075
 	exprlist_node *cure;
1064 1076
 	sol_object_t *obj = sol_alloc_object(state);
@@ -1069,8 +1081,8 @@ sol_object_t *sol_new_func(sol_state_t *state, identlist_node *identlist, stmt_n
1069 1081
 	obj->udata = sol_new_map(state);
1070 1082
 	obj->rest = NULL;
1071 1083
 	obj->annos = sol_new_map(state);
1072
-	obj->type = SOL_FUNCTION;
1073
-	obj->ops = &(state->FuncOps);
1084
+	obj->type = (flags & FUNC_IS_MACRO ? SOL_MACRO : SOL_FUNCTION);
1085
+	obj->ops = (flags & FUNC_IS_MACRO ? &(state->MacroOps) : &(state->FuncOps));
1074 1086
 	if(params) {
1075 1087
 		obj->rest = params->rest ? strdup(params->rest) : NULL;
1076 1088
 		cura = params->clkeys;

+ 3
- 0
ser.c Прегледај датотеку

@@ -160,6 +160,7 @@ void sol_ser_expr(FILE *io, expr_node *ex) {
160 160
 			sol_ser_pl(io, ex->funcdecl->params);
161 161
 			sol_ser_expr(io, ex->funcdecl->anno);
162 162
 			sol_ser_stmt(io, ex->funcdecl->body);
163
+			fwrite(&ex->funcdecl->flags, sizeof(unsigned short), 1, io);
163 164
 			break;
164 165
 
165 166
 		case EX_IFELSE:
@@ -504,6 +505,8 @@ void *sol_deser(FILE *io) {
504 505
 			AS_EX(obj)->funcdecl->params = sol_deser_checked(io, BC_LIST_PM);
505 506
 			AS_EX(obj)->funcdecl->anno = sol_deser_expr(io);
506 507
 			AS_EX(obj)->funcdecl->body = sol_deser_stmt(io);
508
+			fread(&node, sizeof(unsigned short), 1, io);
509
+			AS_EX(obj)->funcdecl->flags = (unsigned short) node;
507 510
 			return obj;
508 511
 
509 512
 		case BC_EX_IFELSE:

+ 16
- 1
sol.h Прегледај датотеку

@@ -10,7 +10,7 @@
10 10
 #include "dsl/dsl.h"
11 11
 
12 12
 /** The version of the project, as made available through `debug.version`. */
13
-#define SOL_VERSION "0.4a1"
13
+#define SOL_VERSION "0.5a0"
14 14
 /** The hexadecimal version of the project, formatted 0xAAIIRPP where:
15 15
  * 
16 16
  * - AA is the two-digit major version
@@ -116,6 +116,8 @@ typedef void (*sol_printfunc_t)(sol_object_t *);
116 116
 typedef struct {
117 117
 	/** A C-string naming the type, for use by the built-in `type` function. */
118 118
 	char *tname;
119
+	/** Some type-specific flags for this type. */
120
+	unsigned short tflags;
119 121
 	/** Called with [this, rhs] to perform binary addition ("+"). */
120 122
 	sol_cfunc_t add;
121 123
 	/** Called with [this, rhs] to perform binary subtraction ("-"). */
@@ -170,6 +172,11 @@ typedef struct {
170 172
 	sol_cfunc_t free;
171 173
 } sol_ops_t;
172 174
 
175
+/** Don't eval arguments passed to ops->call; you will get AST expr_nodes
176
+ *  instead (wrapped up in SOL_EXPR objects). Call sol_eval to evaluate them when
177
+ *  desired. */
178
+#define SOL_TF_NO_EVAL_CALL_ARGS 1
179
+
173 180
 /** Object types known to Sol.
174 181
  *
175 182
  * This is rarely checked and generally only used where necessary, as there is
@@ -195,8 +202,12 @@ typedef enum {
195 202
 	SOL_MCELL,
196 203
 	/** The function type, the type of all user-defined functions in Sol. */
197 204
 	SOL_FUNCTION,
205
+	/** The macro type, the type of all user-defined macros in Sol. */
206
+	SOL_MACRO,
198 207
 	/** The cfunction type, the type of objects wrapping a `sol_cfunc_t`. */
199 208
 	SOL_CFUNCTION,
209
+	/** The cfunction type, the type of objects wrapping a `sol_cfunc_t` without evaluating their arguments. */
210
+	SOL_CMACRO,
200 211
 	/** The statement type, the type of objects wrapping a `stmt_node`. */
201 212
 	SOL_STMT,
202 213
 	/** The expression type, the type of objects wrapping an `expr_node`. */
@@ -431,7 +442,9 @@ typedef struct sol_tag_state_t {
431 442
 	sol_ops_t MapOps; ///< Operations on maps
432 443
 	sol_ops_t MCellOps; ///< Operations on map cells (rarely used)
433 444
 	sol_ops_t FuncOps; ///< Operations on functions
445
+	sol_ops_t MacroOps; ///< Operations on macros
434 446
 	sol_ops_t CFuncOps; ///< Operations on C functions
447
+	sol_ops_t CMacroOps; ///< Operations on C macros
435 448
 	sol_ops_t ASTNodeOps; ///< Operations on AST nodes
436 449
 	sol_ops_t BufferOps; ///< Operations on buffers
437 450
 	sol_ops_t DyLibOps; ///< Operations on dynamic library objects
@@ -921,6 +934,7 @@ sol_object_t *sol_f_stream_open(sol_state_t *, sol_object_t *);
921 934
 #define sol_is_list(obj) ((obj)->type == SOL_LIST)
922 935
 #define sol_is_map(obj) ((obj)->type == SOL_MAP || (obj)->type == SOL_MCELL)
923 936
 #define sol_is_func(obj) ((obj)->type == SOL_FUNCTION)
937
+#define sol_is_macro(obj) ((obj)->type == SOL_MACRO)
924 938
 #define sol_is_cfunc(obj) ((obj)->type == SOL_CFUNCTION)
925 939
 #define sol_is_aststmt(obj) ((obj)->type == SOL_STMT)
926 940
 #define sol_is_astexpr(obj) ((obj)->type == SOL_EXPR)
@@ -1089,6 +1103,7 @@ void sol_map_invert(sol_state_t *, sol_object_t *);
1089 1103
 // sol_object_t *sol_new_exprnode(sol_state_t *, expr_node *);
1090 1104
 
1091 1105
 sol_object_t *sol_new_cfunc(sol_state_t *, sol_cfunc_t, char *);
1106
+sol_object_t *sol_new_cmacro(sol_state_t *, sol_cfunc_t, char *);
1092 1107
 sol_object_t *sol_new_cdata(sol_state_t *, void *, sol_ops_t *);
1093 1108
 
1094 1109
 sol_object_t *sol_new_buffer(sol_state_t *, void *, ssize_t, sol_owntype_t, sol_freefunc_t, sol_movefunc_t);

+ 10
- 0
state.c Прегледај датотеку

@@ -70,6 +70,7 @@ int sol_state_init(sol_state_t *state) {
70 70
 	state->MapOps = state->NullOps;
71 71
 	state->MCellOps = state->NullOps;
72 72
 	state->FuncOps = state->NullOps;
73
+	state->MacroOps = state->NullOps;
73 74
 	state->CFuncOps = state->NullOps;
74 75
 	state->ASTNodeOps = state->NullOps;
75 76
 	state->BufferOps = state->NullOps;
@@ -158,11 +159,19 @@ int sol_state_init(sol_state_t *state) {
158 159
 	state->FuncOps.tostring = sol_f_func_tostring;
159 160
 	state->FuncOps.free = sol_f_func_free;
160 161
 
162
+	state->MacroOps = state->FuncOps;  // XXX Hack
163
+	state->MacroOps.tname = "macro";
164
+	state->MacroOps.tflags = SOL_TF_NO_EVAL_CALL_ARGS;
165
+
161 166
 	state->CFuncOps.tname = "cfunction";
162 167
 	state->CFuncOps.call = sol_f_cfunc_call;
163 168
 	state->CFuncOps.tostring = sol_f_cfunc_tostring;
164 169
 	state->CFuncOps.free = sol_f_cfunc_free;
165 170
 
171
+	state->CMacroOps = state->CFuncOps;
172
+	state->CMacroOps.tname = "cmacro";
173
+	state->CMacroOps.tflags = SOL_TF_NO_EVAL_CALL_ARGS;
174
+
166 175
 	state->ASTNodeOps.tname = "astnode";
167 176
 	state->ASTNodeOps.call = sol_f_astnode_call;
168 177
 	state->ASTNodeOps.index = sol_f_astnode_index;
@@ -864,6 +873,7 @@ sol_object_t *sol_get_stderr(sol_state_t *state) {
864 873
 
865 874
 void sol_ops_init(sol_ops_t *ops) {
866 875
 	ops->tname = "unknown";
876
+	ops->tflags = 0;
867 877
 	ops->add = sol_f_not_impl;
868 878
 	ops->sub = sol_f_not_impl;
869 879
 	ops->mul = sol_f_not_impl;

+ 13
- 0
tests/_crasher_tco.sol Прегледај датотеку

@@ -0,0 +1,13 @@
1
+execfile("tests/_lib.sol")
2
+
3
+func blow_up_stack(n)
4
+	return if n > 0 then
5
+		1 + blow_up_stack(n - 1)
6
+	else
7
+		0
8
+	end
9
+end
10
+
11
+assert_eq(blow_up_stack(5), 5, "blow_up_stack 5 deep")
12
+assert_eq(blow_up_stack(5000), 5000, "blow_up_stack 5000 deep")
13
+assert_eq(blow_up_stack(5000000), 5000000, "blow_up_stack 5000000 deep")

+ 16
- 0
tests/crasher_multiple_loops.sol Прегледај датотеку

@@ -0,0 +1,16 @@
1
+execfile("tests/_lib.sol")
2
+
3
+func rec_tostring(v)
4
+	return for i in v do
5
+		continue if type(i) == "list" then
6
+			rec_tostring(i)
7
+		else
8
+			tostring(i)
9
+		end
10
+	end
11
+end
12
+
13
+l = [ [1, 2, 3], [4, 5, 6], [7, 8, 9] ]
14
+q = [ ["1", "2", "3"], ["4", "5", "6"], ["7", "8", "9"] ]
15
+
16
+assert_eq(rec_tostring(l), q, "nested continue-map fors")

+ 14
- 0
tests/lang_macro.sol Прегледај датотеку

@@ -0,0 +1,14 @@
1
+execfile("tests/_lib.sol")
2
+
3
+macro shitty_eval(x, y)
4
+	--ast.print(x)
5
+	return [x(), y()]
6
+end
7
+
8
+assert_eq(shitty_eval(3 + 2, 7 + 9), [5, 16], "macro 1")
9
+
10
+macro stupid(ex)
11
+	return ex({this_var_does_not_exist = 77})
12
+end
13
+
14
+assert_eq(stupid(this_var_does_not_exist - 7), 70, "macro 2")

+ 2
- 0
tokenizer.lex Прегледај датотеку

@@ -109,6 +109,8 @@ do { return DO; }
109 109
 
110 110
 func { return FUNC; }
111 111
 
112
+macro { return MACRO; }
113
+
112 114
 lambda { return LAMBDA; }
113 115
 
114 116
 return { return RETURN; }

Loading…
Откажи
Сачувај