nendo 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/bin/nendo +37 -2
- data/example/cgi/dekamoji.cgi +100 -0
- data/example/cgi/sample.cgi +32 -0
- data/{sample → example}/exit.nnd +0 -0
- data/{sample → example}/fact.nnd +2 -2
- data/{sample → example}/fizzbuzz1.nnd +2 -2
- data/example/html-lite-sample.nnd +51 -0
- data/{sample → example}/scratch.nnd +1 -5
- data/{sample → example}/tak.nnd +0 -0
- data/lib/init.nnd +171 -30
- data/lib/init.nndc +3736 -2009
- data/lib/nendo.rb +322 -127
- data/lib/text/html-lite.nnd +231 -0
- data/lib/text/html-lite.nndc +2652 -0
- data/lib/text/tree.nnd +23 -0
- data/lib/text/tree.nndc +215 -0
- metadata +14 -7
data/lib/nendo.rb
CHANGED
@@ -6,7 +6,6 @@
|
|
6
6
|
#
|
7
7
|
#
|
8
8
|
require 'stringio'
|
9
|
-
require 'pp'
|
10
9
|
|
11
10
|
class Nil
|
12
11
|
include Enumerable
|
@@ -127,6 +126,51 @@ class Array
|
|
127
126
|
end
|
128
127
|
end
|
129
128
|
|
129
|
+
class Hash
|
130
|
+
def to_list
|
131
|
+
arr = Array.new
|
132
|
+
self.each_pair { |key,val|
|
133
|
+
arr << Cell.new( key, val )
|
134
|
+
}
|
135
|
+
arr.to_list
|
136
|
+
end
|
137
|
+
end
|
138
|
+
|
139
|
+
class LispValues
|
140
|
+
def initialize( arr )
|
141
|
+
if 1 == arr.size
|
142
|
+
raise ArgumentError, "Error: LispValues object expects 0 or 2+ length of array"
|
143
|
+
else
|
144
|
+
@values = arr
|
145
|
+
end
|
146
|
+
end
|
147
|
+
attr_reader :values
|
148
|
+
end
|
149
|
+
|
150
|
+
class LispKeyword
|
151
|
+
def initialize( str )
|
152
|
+
@key = str.intern
|
153
|
+
end
|
154
|
+
|
155
|
+
def ==(other)
|
156
|
+
if other.is_a? LispKeyword
|
157
|
+
self.key == other.key
|
158
|
+
else
|
159
|
+
false
|
160
|
+
end
|
161
|
+
end
|
162
|
+
|
163
|
+
def ===(other)
|
164
|
+
self.==(other)
|
165
|
+
end
|
166
|
+
|
167
|
+
def to_s
|
168
|
+
self.key.to_s
|
169
|
+
end
|
170
|
+
|
171
|
+
attr_reader :key
|
172
|
+
end
|
173
|
+
|
130
174
|
class Token
|
131
175
|
def initialize( kind, str, sourcefile, lineno = nil, column = nil )
|
132
176
|
@kind = kind
|
@@ -189,6 +233,7 @@ class Reader
|
|
189
233
|
T_LPAREN = :t_lparen
|
190
234
|
T_RPAREN = :t_rparen
|
191
235
|
T_SYMBOL = :t_symbol
|
236
|
+
T_KEYWORD = :t_keyword
|
192
237
|
T_NUM = :t_num
|
193
238
|
T_STRING = :t_string
|
194
239
|
T_QUOTE = :t_quote
|
@@ -293,12 +338,12 @@ class Reader
|
|
293
338
|
else
|
294
339
|
T_UNQUOTE_SPLICING
|
295
340
|
end
|
296
|
-
when '('
|
341
|
+
when '(', '['
|
297
342
|
T_LPAREN
|
298
|
-
when ')'
|
343
|
+
when ')', ']'
|
299
344
|
T_RPAREN
|
300
345
|
when '.'
|
301
|
-
str += readwhile( /[_a-zA-Z0-9
|
346
|
+
str += readwhile( /[_a-zA-Z0-9!?.]/ )
|
302
347
|
if 1 == str.length
|
303
348
|
T_DOT
|
304
349
|
else
|
@@ -311,7 +356,7 @@ class Reader
|
|
311
356
|
str = ""
|
312
357
|
T_COMMENT
|
313
358
|
when /[#]/
|
314
|
-
keyword = readwhile( /[?=!
|
359
|
+
keyword = readwhile( /[?=!]/ )
|
315
360
|
case keyword
|
316
361
|
when /[?=]/
|
317
362
|
str = ""
|
@@ -320,30 +365,29 @@ class Reader
|
|
320
365
|
readwhile( /[^\r\n]/ )
|
321
366
|
str = ""
|
322
367
|
T_COMMENT
|
323
|
-
when "t"
|
324
|
-
str = "true"
|
325
|
-
T_SYMBOL
|
326
|
-
when "f"
|
327
|
-
str = "false"
|
328
|
-
T_SYMBOL
|
329
368
|
else
|
330
|
-
|
331
|
-
|
369
|
+
keyword = readwhile( /[a-z]/ )
|
370
|
+
case keyword
|
371
|
+
when "t"
|
372
|
+
str = "true"
|
373
|
+
T_SYMBOL
|
374
|
+
when "f"
|
375
|
+
str = "false"
|
376
|
+
T_SYMBOL
|
377
|
+
else
|
378
|
+
str += readwhile( /[^ \t\r\n]/ )
|
379
|
+
raise NameError, sprintf( "Error: unknown #xxxx syntax for Nendo %s", str )
|
380
|
+
end
|
332
381
|
end
|
333
|
-
when /[_a-zA-Z]/ # symbol
|
334
|
-
str += readwhile( /[_a-zA-
|
335
|
-
T_SYMBOL
|
336
|
-
when /[*\/=!<>&|%]/ # symbol
|
337
|
-
str += readwhile( /[+*\/=!<>&|?%-]/ )
|
382
|
+
when /[_a-zA-Z!$%&*+\/:<=>?@^~-]/ # symbol
|
383
|
+
str += readwhile( /[0-9._a-zA-Z!$%&*+\/:<=>?@^~-]/ )
|
338
384
|
if str.match( /^[=][>]$/ )
|
339
385
|
T_FEEDTO
|
340
|
-
|
341
|
-
T_SYMBOL
|
342
|
-
end
|
343
|
-
when /[+-]/ # number
|
344
|
-
str += readwhile( /[0-9.]/ )
|
345
|
-
if 1 < str.length
|
386
|
+
elsif str.match( /^[+-][0-9.]+$/ )
|
346
387
|
T_NUM
|
388
|
+
elsif str.match( /^[:]/ )
|
389
|
+
str = str[1..-1]
|
390
|
+
T_KEYWORD
|
347
391
|
else
|
348
392
|
T_SYMBOL
|
349
393
|
end
|
@@ -410,13 +454,15 @@ class Reader
|
|
410
454
|
when T_UNQUOTE
|
411
455
|
:unquote
|
412
456
|
when T_UNQUOTE_SPLICING
|
413
|
-
:
|
457
|
+
:"unquote-splicing"
|
414
458
|
when T_DOT
|
415
|
-
:
|
459
|
+
:"dot-operator"
|
416
460
|
when T_FEEDTO
|
417
461
|
:feedto
|
418
462
|
when T_DEBUG_PRINT
|
419
463
|
"debug-print".intern
|
464
|
+
when T_KEYWORD
|
465
|
+
LispKeyword.new( cur.str )
|
420
466
|
else
|
421
467
|
raise "Error: Unknown token in atom()"
|
422
468
|
end
|
@@ -445,9 +491,12 @@ class Reader
|
|
445
491
|
# (. symbol1 symbol2 ... ) form
|
446
492
|
cells << Cell.new( atom() )
|
447
493
|
else
|
448
|
-
# ( symbol1
|
494
|
+
# ( symbol1 ... symbol2 . symbol3 ) form
|
449
495
|
token
|
450
496
|
lastAtom = sexp()
|
497
|
+
if lastAtom.is_a? Cell and lastAtom.isNull
|
498
|
+
lastAtom = Nil.new # the null list "()" could not be a lastAtom.
|
499
|
+
end
|
451
500
|
end
|
452
501
|
when T_QUOTE , T_QUASIQUOTE , T_UNQUOTE , T_UNQUOTE_SPLICING, T_DEBUG_PRINT
|
453
502
|
cells << Cell.new( sexp() )
|
@@ -553,14 +602,14 @@ module BuiltinFunctions
|
|
553
602
|
end
|
554
603
|
end
|
555
604
|
|
556
|
-
def
|
605
|
+
def _equal_QUMARK( a, b )
|
557
606
|
if a.class != b.class
|
558
607
|
false
|
559
608
|
elsif a.class == Cell
|
560
609
|
if a.isNull and b.isNull
|
561
610
|
true
|
562
611
|
else
|
563
|
-
|
612
|
+
_equal_QUMARK( a.car, b.car ) and _equal_QUMARK( a.cdr, b.cdr )
|
564
613
|
end
|
565
614
|
elsif a.class == Nil and b.class == Nil
|
566
615
|
true
|
@@ -569,41 +618,61 @@ module BuiltinFunctions
|
|
569
618
|
end
|
570
619
|
end
|
571
620
|
|
572
|
-
def
|
573
|
-
|
574
|
-
|
575
|
-
|
576
|
-
|
577
|
-
first
|
621
|
+
def __PLMARK( *args )
|
622
|
+
arr = args[0].to_arr
|
623
|
+
case args[0].length
|
624
|
+
when 0
|
625
|
+
0
|
578
626
|
else
|
579
|
-
|
627
|
+
__assertFlat( arr )
|
628
|
+
arr.each { |x|
|
629
|
+
if not (_number_QUMARK(x) or _string_QUMARK(x))
|
630
|
+
raise TypeError
|
631
|
+
end
|
632
|
+
}
|
633
|
+
case args[0].length
|
634
|
+
when 1
|
635
|
+
args[0].car
|
636
|
+
else
|
637
|
+
arr[1..-1].inject(arr[0]){|x,y| x+y}
|
638
|
+
end
|
580
639
|
end
|
581
640
|
end
|
582
641
|
|
583
|
-
def
|
584
|
-
|
585
|
-
|
586
|
-
|
587
|
-
|
588
|
-
- first
|
642
|
+
def __ASMARK( *args )
|
643
|
+
arr = args[0].to_arr
|
644
|
+
case args[0].length
|
645
|
+
when 0
|
646
|
+
1
|
589
647
|
else
|
590
|
-
|
648
|
+
__assertFlat( arr )
|
649
|
+
arr.each { |x|
|
650
|
+
if not _number_QUMARK(x)
|
651
|
+
raise TypeError
|
652
|
+
end
|
653
|
+
}
|
654
|
+
case args[0].length
|
655
|
+
when 1
|
656
|
+
args[0].car
|
657
|
+
else
|
658
|
+
arr[1..-1].inject(arr[0]){|x,y| x*y}
|
659
|
+
end
|
591
660
|
end
|
592
661
|
end
|
593
662
|
|
594
|
-
def
|
595
|
-
raise TypeError if not
|
663
|
+
def __MIMARK( first, *rest )
|
664
|
+
raise TypeError if not _number_QUMARK(first)
|
596
665
|
rest = rest[0].to_arr
|
597
666
|
__assertFlat( rest )
|
598
667
|
if 0 == rest.length
|
599
|
-
first
|
668
|
+
- first
|
600
669
|
else
|
601
|
-
rest.inject(first){|x,y| x
|
670
|
+
rest.inject(first){|x,y| x-y}
|
602
671
|
end
|
603
672
|
end
|
604
673
|
|
605
|
-
def
|
606
|
-
raise TypeError if not
|
674
|
+
def __SLMARK( first, *rest )
|
675
|
+
raise TypeError if not _number_QUMARK(first)
|
607
676
|
rest = rest[0].to_arr
|
608
677
|
__assertFlat( rest )
|
609
678
|
if 0 == rest.length
|
@@ -613,8 +682,8 @@ module BuiltinFunctions
|
|
613
682
|
end
|
614
683
|
end
|
615
684
|
|
616
|
-
def
|
617
|
-
raise TypeError if not
|
685
|
+
def __PAMARK( first, *rest )
|
686
|
+
raise TypeError if not _number_QUMARK(first)
|
618
687
|
rest = rest[0].to_arr
|
619
688
|
__assertFlat( rest )
|
620
689
|
if 0 == rest.length
|
@@ -630,7 +699,15 @@ module BuiltinFunctions
|
|
630
699
|
end
|
631
700
|
|
632
701
|
def _cons( first, second )
|
633
|
-
|
702
|
+
if second.is_a? Cell
|
703
|
+
if second.isNull
|
704
|
+
Cell.new( first )
|
705
|
+
else
|
706
|
+
Cell.new( first, second )
|
707
|
+
end
|
708
|
+
else
|
709
|
+
Cell.new( first, second )
|
710
|
+
end
|
634
711
|
end
|
635
712
|
|
636
713
|
def _exit( *args )
|
@@ -654,7 +731,7 @@ module BuiltinFunctions
|
|
654
731
|
Kernel::sprintf( format, *(rest[0].to_arr) )
|
655
732
|
end
|
656
733
|
|
657
|
-
def
|
734
|
+
def _null_QUMARK( arg )
|
658
735
|
if Nil == arg.class
|
659
736
|
true
|
660
737
|
elsif Cell == arg.class
|
@@ -664,7 +741,7 @@ module BuiltinFunctions
|
|
664
741
|
end
|
665
742
|
end
|
666
743
|
def _length( arg )
|
667
|
-
if
|
744
|
+
if _null_QUMARK( arg )
|
668
745
|
0
|
669
746
|
elsif arg.is_a? Cell
|
670
747
|
arg.length
|
@@ -676,43 +753,64 @@ module BuiltinFunctions
|
|
676
753
|
def _sort( arg ) arg.to_arr.sort.to_list end
|
677
754
|
def _reverse( arg ) arg.to_arr.reverse.to_list end
|
678
755
|
def _uniq( arg ) arg.to_arr.uniq.to_list end
|
679
|
-
def _range( num )
|
680
|
-
|
681
|
-
|
682
|
-
|
683
|
-
|
684
|
-
|
685
|
-
|
756
|
+
def _range( num, *args )
|
757
|
+
arr = args[0].to_arr
|
758
|
+
if 0 < arr.length
|
759
|
+
if arr[0].is_a? Fixnum
|
760
|
+
(0..num-1).to_a.map { |x| x + arr[0] }.to_list
|
761
|
+
else
|
762
|
+
raise TypeError, "Error range's start expects number."
|
763
|
+
end
|
764
|
+
else
|
765
|
+
(0..num-1).to_a.to_list
|
766
|
+
end
|
767
|
+
end
|
768
|
+
def __EQMARK( a,b ) a == b end
|
769
|
+
def __GTMARK( a,b ) a > b end
|
770
|
+
def __GTMARK_EQMARK( a,b ) a >= b end
|
771
|
+
def __LTMARK( a,b ) a < b end
|
772
|
+
def __LTMARK_EQMARK( a,b ) a <= b end
|
773
|
+
def _eqv_QUMARK( a,b ) a === b end
|
774
|
+
def _eq_QUMARK( a,b ) a == b end
|
775
|
+
def _gt_QUMARK( a,b ) a > b end
|
776
|
+
def _ge_QUMARK( a,b ) a >= b end
|
777
|
+
def _lt_QUMARK( a,b ) a < b end
|
778
|
+
def _le_QUMARK( a,b ) a <= b end
|
779
|
+
def _eqv_QUMARK( a,b ) a === b end
|
686
780
|
def _car( cell ) cell.car end
|
687
781
|
def _cdr( cell ) cell.cdr end
|
688
782
|
def _write( arg ) printer = Printer.new ; print printer._write( arg ) ; arg end
|
689
|
-
def
|
783
|
+
def _write_MIMARKto_MIMARKstring( arg ) printer = Printer.new ; printer._write( arg ) end
|
690
784
|
def _display( arg ) printer = Printer.new ; print printer._print( arg ) ; arg end
|
691
785
|
def _print( arg ) self._display( arg ) ; self._newline() ; arg end
|
692
786
|
def _newline( ) print "\n" end
|
693
|
-
def
|
694
|
-
def
|
695
|
-
def
|
696
|
-
def
|
697
|
-
|
787
|
+
def _procedure_QUMARK( arg ) ((Proc == arg.class) or (Method == arg.class)) end
|
788
|
+
def _macro_QUMARK( arg ) (LispMacro == arg.class) end
|
789
|
+
def _symbol_QUMARK( arg ) (Symbol == arg.class) end
|
790
|
+
def _keyword_QUMARK( arg ) (arg.is_a? LispKeyword) end
|
791
|
+
def _pair_QUMARK( arg )
|
792
|
+
if _null_QUMARK( arg )
|
698
793
|
false
|
699
794
|
else
|
700
795
|
(Cell == arg.class)
|
701
796
|
end
|
702
797
|
end
|
703
|
-
def
|
704
|
-
def
|
705
|
-
def
|
706
|
-
if
|
798
|
+
def _number_QUMARK( arg ) ((Fixnum == arg.class) or (Float == arg.class)) end
|
799
|
+
def _string_QUMARK( arg ) String == arg.class end
|
800
|
+
def _macroexpand_MIMARK1( arg )
|
801
|
+
if _pair_QUMARK( arg )
|
707
802
|
macroexpand_1( arg )
|
708
803
|
else
|
709
804
|
arg
|
710
805
|
end
|
711
806
|
end
|
712
|
-
def _to_s( arg )
|
713
|
-
def
|
714
|
-
def
|
715
|
-
def
|
807
|
+
def _to_s( arg ) _to_MIMARKs( arg ) end
|
808
|
+
def _to_MIMARKs( arg ) arg.to_s end
|
809
|
+
def _to_i( arg ) _to_MIMARKi( arg ) end
|
810
|
+
def _to_MIMARKi( arg ) arg.to_i end
|
811
|
+
def _nil_QUMARK( arg ) arg.nil? end
|
812
|
+
def _to_list( arg ) _to_MIMARKlist( arg ) end
|
813
|
+
def _to_MIMARKlist( arg )
|
716
814
|
case arg
|
717
815
|
when Array
|
718
816
|
arg.to_list
|
@@ -722,8 +820,10 @@ module BuiltinFunctions
|
|
722
820
|
raise TypeError
|
723
821
|
end
|
724
822
|
end
|
725
|
-
def _intern( arg )
|
726
|
-
def
|
823
|
+
def _intern( arg ) arg.intern end
|
824
|
+
def _string_MIMARK_GTMARKsymbol( arg ) arg.intern end
|
825
|
+
def _symbol_MIMARK_GTMARKstring( arg ) arg.to_s end
|
826
|
+
def _string_MIMARKjoin( lst, delim )
|
727
827
|
lst.to_a.map{ |x| x.car }.join( delim )
|
728
828
|
end
|
729
829
|
def _require( arg )
|
@@ -754,16 +854,78 @@ module BuiltinFunctions
|
|
754
854
|
callProcedure( "(apply1 genereate func)", first, arg )
|
755
855
|
end
|
756
856
|
|
757
|
-
def
|
857
|
+
def _global_MIMARKvariables
|
758
858
|
self.instance_variables.select { |x|
|
759
859
|
x.match( /^[@]_[a-zA-Z]/ )
|
760
860
|
}.map{ |name|
|
761
861
|
self.toLispSymbol( name[1..-1] ).intern
|
762
862
|
}.to_list
|
763
863
|
end
|
864
|
+
|
865
|
+
def _make_MIMARKvalues( lst )
|
866
|
+
if _pair_QUMARK( lst )
|
867
|
+
LispValues.new( lst.to_arr )
|
868
|
+
elsif _null_QUMARK( lst )
|
869
|
+
LispValues.new( [] )
|
870
|
+
else
|
871
|
+
raise ArgumentError, "Error: make-values expects a list argument."
|
872
|
+
end
|
873
|
+
end
|
874
|
+
|
875
|
+
def _values_QUMARK( arg ) arg.is_a? LispValues end
|
876
|
+
|
877
|
+
def _values_MIMARKvalues( arg )
|
878
|
+
if _values_QUMARK( arg )
|
879
|
+
arg.values.to_list
|
880
|
+
else
|
881
|
+
raise TypeError, "Error: values-values expects only LispValues object."
|
882
|
+
end
|
883
|
+
end
|
884
|
+
|
885
|
+
def _make_MIMARKkeyword( arg )
|
886
|
+
if _symbol_QUMARK( arg ) or _string_QUMARK( arg )
|
887
|
+
LispKeyword.new( arg.to_s )
|
888
|
+
else
|
889
|
+
raise TypeError, "Error: make-keyword expects symbol or string object."
|
890
|
+
end
|
891
|
+
end
|
892
|
+
|
893
|
+
def _keyword_MIMARK_GTMARKstring( arg )
|
894
|
+
if _keyword_QUMARK( arg )
|
895
|
+
arg.key.to_s
|
896
|
+
else
|
897
|
+
raise TypeError, "Error: keyword->string expects only keyword object."
|
898
|
+
end
|
899
|
+
end
|
900
|
+
|
901
|
+
def _get_MIMARKnendo_MIMARKhome
|
902
|
+
File.dirname(__FILE__)
|
903
|
+
end
|
904
|
+
|
905
|
+
def _hash_MIMARKtable_MIMARKget( h, key, *args )
|
906
|
+
if h.has_key?( key )
|
907
|
+
h[key]
|
908
|
+
else
|
909
|
+
arr = args[0].to_arr
|
910
|
+
if 0 < arr.length
|
911
|
+
arr[0]
|
912
|
+
else
|
913
|
+
raise RuntimeError, sprintf( "Error: in hash-table-get() key [%s] was not exist.\n", key )
|
914
|
+
end
|
915
|
+
end
|
916
|
+
end
|
917
|
+
|
918
|
+
def _hash_MIMARKtable_MIMARKput_EXMARK( h, key, value )
|
919
|
+
h[key] = value
|
920
|
+
end
|
921
|
+
|
922
|
+
def _raise( exception, message )
|
923
|
+
raise exception, message
|
924
|
+
end
|
764
925
|
end
|
765
926
|
|
766
927
|
|
928
|
+
|
767
929
|
# Translate S expression to Ruby expression and Evaluation
|
768
930
|
class Evaluator
|
769
931
|
include BuiltinFunctions
|
@@ -771,31 +933,35 @@ class Evaluator
|
|
771
933
|
@indent = " "
|
772
934
|
@binding = binding
|
773
935
|
@debug = debug
|
774
|
-
@
|
775
|
-
|
776
|
-
|
777
|
-
|
778
|
-
|
779
|
-
|
780
|
-
|
781
|
-
|
782
|
-
|
783
|
-
|
784
|
-
|
785
|
-
|
936
|
+
@char_table_lisp_to_ruby = {
|
937
|
+
# list (! $ % & * + - . / : < = > ? @ ^ _ ~)
|
938
|
+
'!' => '_EXMARK',
|
939
|
+
'$' => '_DOMARK',
|
940
|
+
'%' => '_PAMARK',
|
941
|
+
'&' => '_ANMARK',
|
942
|
+
'*' => '_ASMARK',
|
943
|
+
'+' => '_PLMARK',
|
944
|
+
'-' => '_MIMARK',
|
945
|
+
# '.'
|
946
|
+
'/' => '_SLMARK',
|
947
|
+
':' => '_COMARK',
|
948
|
+
'<' => '_LTMARK',
|
949
|
+
'=' => '_EQMARK',
|
950
|
+
'>' => '_GTMARK',
|
951
|
+
'?' => '_QUMARK',
|
952
|
+
'@' => '_ATMARK',
|
953
|
+
'^' => '_NKMARK',
|
954
|
+
# '_'
|
955
|
+
'~' => '_CHMARK',
|
786
956
|
}
|
957
|
+
@char_table_ruby_to_lisp = @char_table_lisp_to_ruby.invert
|
958
|
+
|
787
959
|
# built-in functions
|
788
|
-
@sym = Hash.new
|
789
960
|
self.methods.grep( /^_/ ) { |rubySymbol|
|
790
|
-
@
|
961
|
+
@___tmp = self.method( rubySymbol )
|
962
|
+
eval( sprintf( "@%s = @___tmp", rubySymbol ), @binding )
|
791
963
|
}
|
792
964
|
|
793
|
-
# initialize global symbols
|
794
|
-
rubyExp = @sym.keys.map { |name|
|
795
|
-
sprintf( "@%s = @sym[ '%s' ] ", name, name )
|
796
|
-
}.join( " ; " )
|
797
|
-
eval( rubyExp, @binding )
|
798
|
-
|
799
965
|
# initialize buildin functions as Proc objects
|
800
966
|
rubyExp = self.methods.select { |x|
|
801
967
|
x.to_s.match( /^_/ )
|
@@ -808,13 +974,19 @@ class Evaluator
|
|
808
974
|
@gensym_counter = 0
|
809
975
|
|
810
976
|
# compiled ruby code
|
811
|
-
|
977
|
+
# { 'filename1' => [ 'code1' 'code2' ... ],
|
978
|
+
# 'filename2' => [ 'code1' 'code2' ... ], ... }
|
979
|
+
@compiled_code = Hash.new
|
812
980
|
end
|
813
981
|
|
814
982
|
def _gensym( )
|
815
983
|
@gensym_counter += 1
|
816
984
|
sprintf( "__gensym__%d", @gensym_counter ).intern
|
817
985
|
end
|
986
|
+
|
987
|
+
def forward_gensym_counter( )
|
988
|
+
@gensym_counter += 10000
|
989
|
+
end
|
818
990
|
|
819
991
|
def toRubyValue( val )
|
820
992
|
if NilClass == val.class
|
@@ -834,7 +1006,12 @@ class Evaluator
|
|
834
1006
|
""
|
835
1007
|
else
|
836
1008
|
arr = name.gsub( /["]/, '' ).split( /[.]/ )
|
837
|
-
|
1009
|
+
tmp = arr[0]
|
1010
|
+
tmp.gsub!( /[:][:]/, " " ) # save '::'
|
1011
|
+
@char_table_lisp_to_ruby.each_pair { |key,val|
|
1012
|
+
tmp.gsub!( Regexp.new( Regexp.escape( key )), val )
|
1013
|
+
}
|
1014
|
+
arr[0] = tmp.gsub( /[ ][ ]/, "::" )
|
838
1015
|
if arr[0].match( /^[A-Z]/ )
|
839
1016
|
# nothing to do
|
840
1017
|
elsif arr[0] == ""
|
@@ -854,7 +1031,10 @@ class Evaluator
|
|
854
1031
|
name = name.to_s if Symbol == name.class
|
855
1032
|
raise ArgumentError, sprintf( "Error: `%s' is not a lisp symbol", name ) if not ('_' == name[0])
|
856
1033
|
name = name[1..-1]
|
857
|
-
|
1034
|
+
@char_table_ruby_to_lisp.each_pair { |key,val|
|
1035
|
+
name = name.gsub( Regexp.new( key ), val )
|
1036
|
+
}
|
1037
|
+
name
|
858
1038
|
end
|
859
1039
|
|
860
1040
|
def toRubyArgument( origname, pred, args )
|
@@ -920,10 +1100,16 @@ class Evaluator
|
|
920
1100
|
when :define, :set! # `define' special form
|
921
1101
|
ar = args.cdr.map { |x| x.car }
|
922
1102
|
variable_sym = toRubySymbol( args.car.to_s.sub( /^:/, "" ))
|
923
|
-
global_cap = locals.flatten.include?( variable_sym ) ? nil : "@"
|
1103
|
+
global_cap = locals.flatten.include?( variable_sym.split( /[.]/ )[0] ) ? nil : "@"
|
924
1104
|
[ sprintf( "%s%s = ", global_cap, variable_sym ), ar ]
|
925
1105
|
when :error
|
926
|
-
|
1106
|
+
[
|
1107
|
+
'begin raise RuntimeError, ',
|
1108
|
+
args.car,
|
1109
|
+
"rescue => __e ",
|
1110
|
+
sprintf( " __e.set_backtrace( [\"%s:%d\"] + __e.backtrace )", sourcefile, lineno ),
|
1111
|
+
" raise __e",
|
1112
|
+
"end "]
|
927
1113
|
else
|
928
1114
|
if (not lambda_flag) and isRubyInterface( funcname )
|
929
1115
|
# Ruby method
|
@@ -947,7 +1133,6 @@ class Evaluator
|
|
947
1133
|
else
|
948
1134
|
origname = funcname.to_s
|
949
1135
|
funcname = funcname.to_s
|
950
|
-
funcname = @alias[ funcname ] if @alias[ funcname ]
|
951
1136
|
sym = toRubySymbol( funcname )
|
952
1137
|
[sprintf( "callProcedure( '%s',", origname ),
|
953
1138
|
[lispSymbolReference( sym, locals, nil, sourcefile, lineno )] + [","],
|
@@ -1094,7 +1279,7 @@ class Evaluator
|
|
1094
1279
|
case sexp
|
1095
1280
|
when Cell
|
1096
1281
|
if sexp.isNull
|
1097
|
-
str += "
|
1282
|
+
str += "Cell.new()"
|
1098
1283
|
else
|
1099
1284
|
arr = sexp.map { |x| genQuote( x.car ) }
|
1100
1285
|
str += "Cell.new("
|
@@ -1107,6 +1292,8 @@ class Evaluator
|
|
1107
1292
|
str += sprintf( ":\"%s\"", sexp.to_s )
|
1108
1293
|
when String
|
1109
1294
|
str += sprintf( "\"%s\"", LispString.escape( sexp ))
|
1295
|
+
when LispKeyword
|
1296
|
+
str += sprintf( "LispKeyword.new( \"%s\" )", sexp.key.to_s )
|
1110
1297
|
when TrueClass, FalseClass, NilClass # reserved symbols
|
1111
1298
|
str += toRubyValue( sexp )
|
1112
1299
|
else
|
@@ -1162,11 +1349,7 @@ class Evaluator
|
|
1162
1349
|
elsif sexp.isNull
|
1163
1350
|
[ "Cell.new()" ]
|
1164
1351
|
elsif Cell == sexp.car.class
|
1165
|
-
|
1166
|
-
self.apply( translate( sexp.car, locals ), sexp.cdr, sexp.car.car.sourcefile, sexp.car.car.lineno, locals, true )
|
1167
|
-
else
|
1168
|
-
translate( sexp.car, locals )
|
1169
|
-
end
|
1352
|
+
self.apply( translate( sexp.car, locals ), sexp.cdr, sexp.car.car.sourcefile, sexp.car.car.lineno, locals, true )
|
1170
1353
|
elsif :begin == sexp.car
|
1171
1354
|
self.makeBegin( sexp.cdr, locals )
|
1172
1355
|
elsif :lambda == sexp.car
|
@@ -1186,13 +1369,14 @@ class Evaluator
|
|
1186
1369
|
case sexp
|
1187
1370
|
when Symbol
|
1188
1371
|
sym = sexp.to_s
|
1189
|
-
sym = @alias[ sym ] if @alias[ sym ]
|
1190
1372
|
sym = toRubySymbol( sym )
|
1191
1373
|
lispSymbolReference( sym, locals, nil, sexp.sourcefile, sexp.lineno )
|
1192
1374
|
when Fixnum
|
1193
1375
|
sexp.to_s
|
1194
1376
|
when String
|
1195
1377
|
sprintf( "\"%s\"", LispString.escape( sexp ))
|
1378
|
+
when LispKeyword
|
1379
|
+
sprintf( "LispKeyword.new( \"%s\" )", sexp.key )
|
1196
1380
|
when Nil
|
1197
1381
|
"Nil.new"
|
1198
1382
|
when TrueClass, FalseClass, NilClass # reserved symbols
|
@@ -1229,7 +1413,7 @@ class Evaluator
|
|
1229
1413
|
sexp.cdr.cdr = quoting( sexp.cdr.cdr )
|
1230
1414
|
sexp
|
1231
1415
|
elsif :let == sexp.car
|
1232
|
-
if
|
1416
|
+
if _null_QUMARK( sexp.cdr )
|
1233
1417
|
# do nothing
|
1234
1418
|
p "kiyoka1"
|
1235
1419
|
else
|
@@ -1266,7 +1450,7 @@ class Evaluator
|
|
1266
1450
|
sexp
|
1267
1451
|
else
|
1268
1452
|
newSexp = macroexpand_1_sub( sexp )
|
1269
|
-
if not
|
1453
|
+
if not _equal_QUMARK( newSexp, sexp )
|
1270
1454
|
@expand_flag = false
|
1271
1455
|
end
|
1272
1456
|
newSexp
|
@@ -1280,7 +1464,6 @@ class Evaluator
|
|
1280
1464
|
sexp
|
1281
1465
|
else
|
1282
1466
|
sym = sexp.car.to_s
|
1283
|
-
sym = @alias[ sym ] if @alias[ sym ]
|
1284
1467
|
sym = toRubySymbol( sym )
|
1285
1468
|
newSexp = sexp
|
1286
1469
|
if isRubyInterface( sym )
|
@@ -1289,7 +1472,7 @@ class Evaluator
|
|
1289
1472
|
eval( sprintf( "@__macro = @%s", sym ), @binding )
|
1290
1473
|
newSexp = callProcedure( sym, @__macro, sexp.cdr )
|
1291
1474
|
end
|
1292
|
-
if
|
1475
|
+
if _equal_QUMARK( newSexp, sexp )
|
1293
1476
|
sexp.map { |x|
|
1294
1477
|
if x.car.is_a? Cell
|
1295
1478
|
macroexpand_1_check( x.car )
|
@@ -1315,7 +1498,7 @@ class Evaluator
|
|
1315
1498
|
converge = true
|
1316
1499
|
begin
|
1317
1500
|
newSexp = macroexpand_1( sexp )
|
1318
|
-
converge =
|
1501
|
+
converge = _equal_QUMARK( newSexp, sexp )
|
1319
1502
|
sexp = newSexp
|
1320
1503
|
end until converge
|
1321
1504
|
sexp
|
@@ -1345,14 +1528,17 @@ class Evaluator
|
|
1345
1528
|
end
|
1346
1529
|
arr = [ translate( sexp, [] ) ]
|
1347
1530
|
rubyExp = ppRubyExp( 0, arr ).flatten.join
|
1348
|
-
@compiled_code
|
1531
|
+
if not @compiled_code.has_key?( sourcefile )
|
1532
|
+
@compiled_code[ sourcefile ] = Array.new
|
1533
|
+
end
|
1534
|
+
@compiled_code[ sourcefile ] << rubyExp
|
1349
1535
|
printf( " rubyExp=<<<\n%s\n>>>\n", rubyExp ) if @debug
|
1350
1536
|
eval( rubyExp, @binding, sourcefile, lineno );
|
1351
1537
|
end
|
1352
1538
|
|
1353
1539
|
def _load( filename )
|
1354
1540
|
printer = Printer.new( @debug )
|
1355
|
-
open( filename ) {|f|
|
1541
|
+
open( filename, "r:utf-8" ) {|f|
|
1356
1542
|
reader = Reader.new( f, filename, false )
|
1357
1543
|
while true
|
1358
1544
|
lineno = reader.lineno
|
@@ -1367,25 +1553,32 @@ class Evaluator
|
|
1367
1553
|
}
|
1368
1554
|
end
|
1369
1555
|
|
1370
|
-
def
|
1371
|
-
open( filename ) { |f|
|
1556
|
+
def _load_MIMARKcompiled_MIMARKcode( filename )
|
1557
|
+
open( filename, "r:utf-8" ) { |f|
|
1372
1558
|
rubyExp = f.read
|
1373
1559
|
eval( rubyExp, @binding )
|
1374
1560
|
}
|
1561
|
+
forward_gensym_counter()
|
1375
1562
|
end
|
1376
1563
|
|
1377
|
-
def
|
1378
|
-
@compiled_code
|
1564
|
+
def _get_MIMARKcompiled_MIMARKcode
|
1565
|
+
@compiled_code
|
1566
|
+
ret = Hash.new
|
1567
|
+
@compiled_code.each_key { |key|
|
1568
|
+
ret[key] = @compiled_code[key].to_list
|
1569
|
+
ret[key]
|
1570
|
+
}
|
1571
|
+
ret.to_list
|
1379
1572
|
end
|
1380
1573
|
|
1381
1574
|
def _eval( sexp )
|
1382
1575
|
self.lispEval( sexp, "dynamic S-expression ( no source )", 1 )
|
1383
1576
|
end
|
1384
1577
|
|
1385
|
-
def
|
1578
|
+
def _enable_MIMARKidebug()
|
1386
1579
|
@debug = true
|
1387
1580
|
end
|
1388
|
-
def
|
1581
|
+
def _disable_MIMARKidebug()
|
1389
1582
|
@debug = false
|
1390
1583
|
end
|
1391
1584
|
end
|
@@ -1404,9 +1597,9 @@ class Printer
|
|
1404
1597
|
"`"
|
1405
1598
|
when :unquote
|
1406
1599
|
","
|
1407
|
-
when :
|
1600
|
+
when :"unquote-splicing"
|
1408
1601
|
",@"
|
1409
|
-
when :
|
1602
|
+
when :"dot-operator"
|
1410
1603
|
"."
|
1411
1604
|
else
|
1412
1605
|
false
|
@@ -1436,6 +1629,8 @@ class Printer
|
|
1436
1629
|
else
|
1437
1630
|
sexp.to_s
|
1438
1631
|
end
|
1632
|
+
when LispKeyword
|
1633
|
+
":" + sexp.key.to_s
|
1439
1634
|
when Nil
|
1440
1635
|
"()"
|
1441
1636
|
when nil
|
@@ -1466,7 +1661,7 @@ class Nendo
|
|
1466
1661
|
if use_compiled
|
1467
1662
|
compiled_file = File.dirname(__FILE__) + "/init.nndc"
|
1468
1663
|
if File.exist?( compiled_file )
|
1469
|
-
@evaluator.
|
1664
|
+
@evaluator._load_MIMARKcompiled_MIMARKcode( compiled_file )
|
1470
1665
|
done = true
|
1471
1666
|
end
|
1472
1667
|
end
|