prism 0.17.1 → 0.18.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG.md +30 -1
- data/Makefile +5 -5
- data/README.md +2 -2
- data/config.yml +26 -13
- data/docs/build_system.md +6 -6
- data/docs/building.md +1 -1
- data/docs/configuration.md +1 -0
- data/docs/encoding.md +68 -32
- data/docs/heredocs.md +1 -1
- data/docs/javascript.md +29 -1
- data/docs/ruby_api.md +14 -0
- data/ext/prism/api_node.c +74 -45
- data/ext/prism/extconf.rb +91 -127
- data/ext/prism/extension.c +1 -1
- data/ext/prism/extension.h +1 -1
- data/include/prism/ast.h +148 -133
- data/include/prism/diagnostic.h +27 -1
- data/include/prism/enc/pm_encoding.h +42 -1
- data/include/prism/parser.h +6 -0
- data/include/prism/version.h +3 -3
- data/lib/prism/compiler.rb +3 -3
- data/lib/prism/debug.rb +4 -0
- data/lib/prism/desugar_compiler.rb +1 -0
- data/lib/prism/dispatcher.rb +14 -14
- data/lib/prism/dot_visitor.rb +4334 -0
- data/lib/prism/dsl.rb +11 -11
- data/lib/prism/ffi.rb +3 -3
- data/lib/prism/mutation_compiler.rb +6 -6
- data/lib/prism/node.rb +182 -113
- data/lib/prism/node_ext.rb +61 -3
- data/lib/prism/parse_result.rb +46 -12
- data/lib/prism/serialize.rb +125 -131
- data/lib/prism/visitor.rb +3 -3
- data/lib/prism.rb +1 -0
- data/prism.gemspec +5 -1
- data/rbi/prism.rbi +83 -54
- data/sig/prism.rbs +47 -32
- data/src/diagnostic.c +61 -3
- data/src/enc/pm_big5.c +63 -0
- data/src/enc/pm_cp51932.c +57 -0
- data/src/enc/pm_euc_jp.c +10 -0
- data/src/enc/pm_gbk.c +5 -2
- data/src/enc/pm_tables.c +1478 -148
- data/src/node.c +33 -21
- data/src/prettyprint.c +1027 -925
- data/src/prism.c +925 -374
- data/src/regexp.c +12 -12
- data/src/serialize.c +36 -9
- metadata +6 -2
data/rbi/prism.rbi
CHANGED
@@ -1025,6 +1025,56 @@ class Prism::CapturePatternNode < Prism::Node
|
|
1025
1025
|
def inspect(inspector); end
|
1026
1026
|
end
|
1027
1027
|
|
1028
|
+
# Represents the use of a case statement for pattern matching.
|
1029
|
+
#
|
1030
|
+
# case true
|
1031
|
+
# in false
|
1032
|
+
# end
|
1033
|
+
# ^^^^^^^^^
|
1034
|
+
class Prism::CaseMatchNode < Prism::Node
|
1035
|
+
sig { returns(T.nilable(Prism::Node)) }
|
1036
|
+
def predicate; end
|
1037
|
+
|
1038
|
+
sig { returns(T::Array[Prism::Node]) }
|
1039
|
+
def conditions; end
|
1040
|
+
|
1041
|
+
sig { returns(T.nilable(Prism::ElseNode)) }
|
1042
|
+
def consequent; end
|
1043
|
+
|
1044
|
+
sig { returns(Prism::Location) }
|
1045
|
+
def case_keyword_loc; end
|
1046
|
+
|
1047
|
+
sig { returns(Prism::Location) }
|
1048
|
+
def end_keyword_loc; end
|
1049
|
+
|
1050
|
+
sig { params(predicate: T.nilable(Prism::Node), conditions: T::Array[Prism::Node], consequent: T.nilable(Prism::ElseNode), case_keyword_loc: Prism::Location, end_keyword_loc: Prism::Location, location: Prism::Location).void }
|
1051
|
+
def initialize(predicate, conditions, consequent, case_keyword_loc, end_keyword_loc, location); end
|
1052
|
+
|
1053
|
+
sig { params(visitor: Prism::Visitor).void }
|
1054
|
+
def accept(visitor); end
|
1055
|
+
|
1056
|
+
sig { returns(T::Array[T.nilable(Prism::Node)]) }
|
1057
|
+
def child_nodes; end
|
1058
|
+
|
1059
|
+
sig { returns(T::Array[T.nilable(Prism::Node)]) }
|
1060
|
+
def deconstruct; end
|
1061
|
+
|
1062
|
+
sig { params(params: T.untyped).returns(Prism::CaseMatchNode) }
|
1063
|
+
def copy(**params); end
|
1064
|
+
|
1065
|
+
sig { params(keys: T::Array[Symbol]).returns(T::Hash[Symbol, T.nilable(T.any(Prism::Node, T::Array[Prism::Node], String, Prism::Token, T::Array[Prism::Token], Prism::Location))]) }
|
1066
|
+
def deconstruct_keys(keys); end
|
1067
|
+
|
1068
|
+
sig { returns(String) }
|
1069
|
+
def case_keyword; end
|
1070
|
+
|
1071
|
+
sig { returns(String) }
|
1072
|
+
def end_keyword; end
|
1073
|
+
|
1074
|
+
sig { params(inspector: Prism::NodeInspector).returns(String) }
|
1075
|
+
def inspect(inspector); end
|
1076
|
+
end
|
1077
|
+
|
1028
1078
|
# Represents the use of a case statement.
|
1029
1079
|
#
|
1030
1080
|
# case true
|
@@ -2765,6 +2815,9 @@ class Prism::IfNode < Prism::Node
|
|
2765
2815
|
sig { returns(Prism::Node) }
|
2766
2816
|
def predicate; end
|
2767
2817
|
|
2818
|
+
sig { returns(T.nilable(Prism::Location)) }
|
2819
|
+
def then_keyword_loc; end
|
2820
|
+
|
2768
2821
|
sig { returns(T.nilable(Prism::StatementsNode)) }
|
2769
2822
|
def statements; end
|
2770
2823
|
|
@@ -2774,8 +2827,8 @@ class Prism::IfNode < Prism::Node
|
|
2774
2827
|
sig { returns(T.nilable(Prism::Location)) }
|
2775
2828
|
def end_keyword_loc; end
|
2776
2829
|
|
2777
|
-
sig { params(if_keyword_loc: T.nilable(Prism::Location), predicate: Prism::Node, statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::Node), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).void }
|
2778
|
-
def initialize(if_keyword_loc, predicate, statements, consequent, end_keyword_loc, location); end
|
2830
|
+
sig { params(if_keyword_loc: T.nilable(Prism::Location), predicate: Prism::Node, then_keyword_loc: T.nilable(Prism::Location), statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::Node), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).void }
|
2831
|
+
def initialize(if_keyword_loc, predicate, then_keyword_loc, statements, consequent, end_keyword_loc, location); end
|
2779
2832
|
|
2780
2833
|
sig { params(visitor: Prism::Visitor).void }
|
2781
2834
|
def accept(visitor); end
|
@@ -2797,6 +2850,9 @@ class Prism::IfNode < Prism::Node
|
|
2797
2850
|
sig { returns(T.nilable(String)) }
|
2798
2851
|
def if_keyword; end
|
2799
2852
|
|
2853
|
+
sig { returns(T.nilable(String)) }
|
2854
|
+
def then_keyword; end
|
2855
|
+
|
2800
2856
|
sig { returns(T.nilable(String)) }
|
2801
2857
|
def end_keyword; end
|
2802
2858
|
|
@@ -4211,11 +4267,11 @@ class Prism::MatchWriteNode < Prism::Node
|
|
4211
4267
|
sig { returns(Prism::CallNode) }
|
4212
4268
|
def call; end
|
4213
4269
|
|
4214
|
-
sig { returns(T::Array[
|
4215
|
-
def
|
4270
|
+
sig { returns(T::Array[Prism::Node]) }
|
4271
|
+
def targets; end
|
4216
4272
|
|
4217
|
-
sig { params(call: Prism::CallNode,
|
4218
|
-
def initialize(call,
|
4273
|
+
sig { params(call: Prism::CallNode, targets: T::Array[Prism::Node], location: Prism::Location).void }
|
4274
|
+
def initialize(call, targets, location); end
|
4219
4275
|
|
4220
4276
|
sig { params(visitor: Prism::Visitor).void }
|
4221
4277
|
def accept(visitor); end
|
@@ -5651,39 +5707,6 @@ class Prism::StatementsNode < Prism::Node
|
|
5651
5707
|
def inspect(inspector); end
|
5652
5708
|
end
|
5653
5709
|
|
5654
|
-
# Represents the use of compile-time string concatenation.
|
5655
|
-
#
|
5656
|
-
# "foo" "bar"
|
5657
|
-
# ^^^^^^^^^^^
|
5658
|
-
class Prism::StringConcatNode < Prism::Node
|
5659
|
-
sig { returns(Prism::Node) }
|
5660
|
-
def left; end
|
5661
|
-
|
5662
|
-
sig { returns(Prism::Node) }
|
5663
|
-
def right; end
|
5664
|
-
|
5665
|
-
sig { params(left: Prism::Node, right: Prism::Node, location: Prism::Location).void }
|
5666
|
-
def initialize(left, right, location); end
|
5667
|
-
|
5668
|
-
sig { params(visitor: Prism::Visitor).void }
|
5669
|
-
def accept(visitor); end
|
5670
|
-
|
5671
|
-
sig { returns(T::Array[T.nilable(Prism::Node)]) }
|
5672
|
-
def child_nodes; end
|
5673
|
-
|
5674
|
-
sig { returns(T::Array[T.nilable(Prism::Node)]) }
|
5675
|
-
def deconstruct; end
|
5676
|
-
|
5677
|
-
sig { params(params: T.untyped).returns(Prism::StringConcatNode) }
|
5678
|
-
def copy(**params); end
|
5679
|
-
|
5680
|
-
sig { params(keys: T::Array[Symbol]).returns(T::Hash[Symbol, T.nilable(T.any(Prism::Node, T::Array[Prism::Node], String, Prism::Token, T::Array[Prism::Token], Prism::Location))]) }
|
5681
|
-
def deconstruct_keys(keys); end
|
5682
|
-
|
5683
|
-
sig { params(inspector: Prism::NodeInspector).returns(String) }
|
5684
|
-
def inspect(inspector); end
|
5685
|
-
end
|
5686
|
-
|
5687
5710
|
# Represents a string literal, a string contained within a `%w` list, or
|
5688
5711
|
# plain string content within an interpolated string.
|
5689
5712
|
#
|
@@ -5927,6 +5950,9 @@ class Prism::UnlessNode < Prism::Node
|
|
5927
5950
|
sig { returns(Prism::Node) }
|
5928
5951
|
def predicate; end
|
5929
5952
|
|
5953
|
+
sig { returns(T.nilable(Prism::Location)) }
|
5954
|
+
def then_keyword_loc; end
|
5955
|
+
|
5930
5956
|
sig { returns(T.nilable(Prism::StatementsNode)) }
|
5931
5957
|
def statements; end
|
5932
5958
|
|
@@ -5936,8 +5962,8 @@ class Prism::UnlessNode < Prism::Node
|
|
5936
5962
|
sig { returns(T.nilable(Prism::Location)) }
|
5937
5963
|
def end_keyword_loc; end
|
5938
5964
|
|
5939
|
-
sig { params(keyword_loc: Prism::Location, predicate: Prism::Node, statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::ElseNode), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).void }
|
5940
|
-
def initialize(keyword_loc, predicate, statements, consequent, end_keyword_loc, location); end
|
5965
|
+
sig { params(keyword_loc: Prism::Location, predicate: Prism::Node, then_keyword_loc: T.nilable(Prism::Location), statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::ElseNode), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).void }
|
5966
|
+
def initialize(keyword_loc, predicate, then_keyword_loc, statements, consequent, end_keyword_loc, location); end
|
5941
5967
|
|
5942
5968
|
sig { params(visitor: Prism::Visitor).void }
|
5943
5969
|
def accept(visitor); end
|
@@ -5959,6 +5985,9 @@ class Prism::UnlessNode < Prism::Node
|
|
5959
5985
|
sig { returns(String) }
|
5960
5986
|
def keyword; end
|
5961
5987
|
|
5988
|
+
sig { returns(T.nilable(String)) }
|
5989
|
+
def then_keyword; end
|
5990
|
+
|
5962
5991
|
sig { returns(T.nilable(String)) }
|
5963
5992
|
def end_keyword; end
|
5964
5993
|
|
@@ -6370,6 +6399,10 @@ class Prism::Visitor < Prism::BasicVisitor
|
|
6370
6399
|
sig { params(node: Prism::CapturePatternNode).void }
|
6371
6400
|
def visit_capture_pattern_node(node); end
|
6372
6401
|
|
6402
|
+
# Visit a CaseMatchNode node
|
6403
|
+
sig { params(node: Prism::CaseMatchNode).void }
|
6404
|
+
def visit_case_match_node(node); end
|
6405
|
+
|
6373
6406
|
# Visit a CaseNode node
|
6374
6407
|
sig { params(node: Prism::CaseNode).void }
|
6375
6408
|
def visit_case_node(node); end
|
@@ -6810,10 +6843,6 @@ class Prism::Visitor < Prism::BasicVisitor
|
|
6810
6843
|
sig { params(node: Prism::StatementsNode).void }
|
6811
6844
|
def visit_statements_node(node); end
|
6812
6845
|
|
6813
|
-
# Visit a StringConcatNode node
|
6814
|
-
sig { params(node: Prism::StringConcatNode).void }
|
6815
|
-
def visit_string_concat_node(node); end
|
6816
|
-
|
6817
6846
|
# Visit a StringNode node
|
6818
6847
|
sig { params(node: Prism::StringNode).void }
|
6819
6848
|
def visit_string_node(node); end
|
@@ -6932,6 +6961,9 @@ module Prism::DSL
|
|
6932
6961
|
# Create a new CapturePatternNode node
|
6933
6962
|
sig { params(value: Prism::Node, target: Prism::Node, operator_loc: Prism::Location, location: Prism::Location).returns(Prism::CapturePatternNode) }
|
6934
6963
|
def CapturePatternNode(value, target, operator_loc, location); end
|
6964
|
+
# Create a new CaseMatchNode node
|
6965
|
+
sig { params(predicate: T.nilable(Prism::Node), conditions: T::Array[Prism::Node], consequent: T.nilable(Prism::ElseNode), case_keyword_loc: Prism::Location, end_keyword_loc: Prism::Location, location: Prism::Location).returns(Prism::CaseMatchNode) }
|
6966
|
+
def CaseMatchNode(predicate, conditions, consequent, case_keyword_loc, end_keyword_loc, location); end
|
6935
6967
|
# Create a new CaseNode node
|
6936
6968
|
sig { params(predicate: T.nilable(Prism::Node), conditions: T::Array[Prism::Node], consequent: T.nilable(Prism::ElseNode), case_keyword_loc: Prism::Location, end_keyword_loc: Prism::Location, location: Prism::Location).returns(Prism::CaseNode) }
|
6937
6969
|
def CaseNode(predicate, conditions, consequent, case_keyword_loc, end_keyword_loc, location); end
|
@@ -7059,8 +7091,8 @@ module Prism::DSL
|
|
7059
7091
|
sig { params(constant: T.nilable(Prism::Node), elements: T::Array[Prism::Node], rest: T.nilable(Prism::Node), opening_loc: T.nilable(Prism::Location), closing_loc: T.nilable(Prism::Location), location: Prism::Location).returns(Prism::HashPatternNode) }
|
7060
7092
|
def HashPatternNode(constant, elements, rest, opening_loc, closing_loc, location); end
|
7061
7093
|
# Create a new IfNode node
|
7062
|
-
sig { params(if_keyword_loc: T.nilable(Prism::Location), predicate: Prism::Node, statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::Node), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).returns(Prism::IfNode) }
|
7063
|
-
def IfNode(if_keyword_loc, predicate, statements, consequent, end_keyword_loc, location); end
|
7094
|
+
sig { params(if_keyword_loc: T.nilable(Prism::Location), predicate: Prism::Node, then_keyword_loc: T.nilable(Prism::Location), statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::Node), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).returns(Prism::IfNode) }
|
7095
|
+
def IfNode(if_keyword_loc, predicate, then_keyword_loc, statements, consequent, end_keyword_loc, location); end
|
7064
7096
|
# Create a new ImaginaryNode node
|
7065
7097
|
sig { params(numeric: Prism::Node, location: Prism::Location).returns(Prism::ImaginaryNode) }
|
7066
7098
|
def ImaginaryNode(numeric, location); end
|
@@ -7152,8 +7184,8 @@ module Prism::DSL
|
|
7152
7184
|
sig { params(value: Prism::Node, pattern: Prism::Node, operator_loc: Prism::Location, location: Prism::Location).returns(Prism::MatchRequiredNode) }
|
7153
7185
|
def MatchRequiredNode(value, pattern, operator_loc, location); end
|
7154
7186
|
# Create a new MatchWriteNode node
|
7155
|
-
sig { params(call: Prism::CallNode,
|
7156
|
-
def MatchWriteNode(call,
|
7187
|
+
sig { params(call: Prism::CallNode, targets: T::Array[Prism::Node], location: Prism::Location).returns(Prism::MatchWriteNode) }
|
7188
|
+
def MatchWriteNode(call, targets, location); end
|
7157
7189
|
# Create a new MissingNode node
|
7158
7190
|
sig { params(location: Prism::Location).returns(Prism::MissingNode) }
|
7159
7191
|
def MissingNode(location); end
|
@@ -7262,9 +7294,6 @@ module Prism::DSL
|
|
7262
7294
|
# Create a new StatementsNode node
|
7263
7295
|
sig { params(body: T::Array[Prism::Node], location: Prism::Location).returns(Prism::StatementsNode) }
|
7264
7296
|
def StatementsNode(body, location); end
|
7265
|
-
# Create a new StringConcatNode node
|
7266
|
-
sig { params(left: Prism::Node, right: Prism::Node, location: Prism::Location).returns(Prism::StringConcatNode) }
|
7267
|
-
def StringConcatNode(left, right, location); end
|
7268
7297
|
# Create a new StringNode node
|
7269
7298
|
sig { params(flags: Integer, opening_loc: T.nilable(Prism::Location), content_loc: Prism::Location, closing_loc: T.nilable(Prism::Location), unescaped: String, location: Prism::Location).returns(Prism::StringNode) }
|
7270
7299
|
def StringNode(flags, opening_loc, content_loc, closing_loc, unescaped, location); end
|
@@ -7281,8 +7310,8 @@ module Prism::DSL
|
|
7281
7310
|
sig { params(names: T::Array[Prism::Node], keyword_loc: Prism::Location, location: Prism::Location).returns(Prism::UndefNode) }
|
7282
7311
|
def UndefNode(names, keyword_loc, location); end
|
7283
7312
|
# Create a new UnlessNode node
|
7284
|
-
sig { params(keyword_loc: Prism::Location, predicate: Prism::Node, statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::ElseNode), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).returns(Prism::UnlessNode) }
|
7285
|
-
def UnlessNode(keyword_loc, predicate, statements, consequent, end_keyword_loc, location); end
|
7313
|
+
sig { params(keyword_loc: Prism::Location, predicate: Prism::Node, then_keyword_loc: T.nilable(Prism::Location), statements: T.nilable(Prism::StatementsNode), consequent: T.nilable(Prism::ElseNode), end_keyword_loc: T.nilable(Prism::Location), location: Prism::Location).returns(Prism::UnlessNode) }
|
7314
|
+
def UnlessNode(keyword_loc, predicate, then_keyword_loc, statements, consequent, end_keyword_loc, location); end
|
7286
7315
|
# Create a new UntilNode node
|
7287
7316
|
sig { params(keyword_loc: Prism::Location, closing_loc: T.nilable(Prism::Location), predicate: Prism::Node, statements: T.nilable(Prism::StatementsNode), flags: Integer, location: Prism::Location).returns(Prism::UntilNode) }
|
7288
7317
|
def UntilNode(keyword_loc, closing_loc, predicate, statements, flags, location); end
|
data/sig/prism.rbs
CHANGED
@@ -605,6 +605,35 @@ module Prism
|
|
605
605
|
|
606
606
|
def inspect: (inspector: NodeInspector) -> String
|
607
607
|
end
|
608
|
+
# Represents the use of a case statement for pattern matching.
|
609
|
+
#
|
610
|
+
# case true
|
611
|
+
# in false
|
612
|
+
# end
|
613
|
+
# ^^^^^^^^^
|
614
|
+
class CaseMatchNode < Node
|
615
|
+
attr_reader predicate: Node?
|
616
|
+
attr_reader conditions: Array[Node]
|
617
|
+
attr_reader consequent: ElseNode?
|
618
|
+
attr_reader case_keyword_loc: Location
|
619
|
+
attr_reader end_keyword_loc: Location
|
620
|
+
|
621
|
+
def initialize: (predicate: Node?, conditions: Array[Node], consequent: ElseNode?, case_keyword_loc: Location, end_keyword_loc: Location, location: Location) -> void
|
622
|
+
def accept: (visitor: Visitor) -> void
|
623
|
+
def set_newline_flag: (newline_marked: Array[bool]) -> void
|
624
|
+
def child_nodes: () -> Array[Node?]
|
625
|
+
def deconstruct: () -> Array[Node?]
|
626
|
+
|
627
|
+
def copy: (**untyped) -> CaseMatchNode
|
628
|
+
|
629
|
+
def deconstruct_keys: (keys: Array[Symbol]) -> Hash[Symbol, (Node | Array[Node] | String | Token | Array[Token] | Location)?]
|
630
|
+
|
631
|
+
def case_keyword: () -> String
|
632
|
+
|
633
|
+
def end_keyword: () -> String
|
634
|
+
|
635
|
+
def inspect: (inspector: NodeInspector) -> String
|
636
|
+
end
|
608
637
|
# Represents the use of a case statement.
|
609
638
|
#
|
610
639
|
# case true
|
@@ -1632,11 +1661,12 @@ module Prism
|
|
1632
1661
|
class IfNode < Node
|
1633
1662
|
attr_reader if_keyword_loc: Location?
|
1634
1663
|
attr_reader predicate: Node
|
1664
|
+
attr_reader then_keyword_loc: Location?
|
1635
1665
|
attr_reader statements: StatementsNode?
|
1636
1666
|
attr_reader consequent: Node?
|
1637
1667
|
attr_reader end_keyword_loc: Location?
|
1638
1668
|
|
1639
|
-
def initialize: (if_keyword_loc: Location?, predicate: Node, statements: StatementsNode?, consequent: Node?, end_keyword_loc: Location?, location: Location) -> void
|
1669
|
+
def initialize: (if_keyword_loc: Location?, predicate: Node, then_keyword_loc: Location?, statements: StatementsNode?, consequent: Node?, end_keyword_loc: Location?, location: Location) -> void
|
1640
1670
|
def accept: (visitor: Visitor) -> void
|
1641
1671
|
def set_newline_flag: (newline_marked: Array[bool]) -> void
|
1642
1672
|
def child_nodes: () -> Array[Node?]
|
@@ -1648,6 +1678,8 @@ module Prism
|
|
1648
1678
|
|
1649
1679
|
def if_keyword: () -> String?
|
1650
1680
|
|
1681
|
+
def then_keyword: () -> String?
|
1682
|
+
|
1651
1683
|
def end_keyword: () -> String?
|
1652
1684
|
|
1653
1685
|
def inspect: (inspector: NodeInspector) -> String
|
@@ -2471,9 +2503,9 @@ module Prism
|
|
2471
2503
|
# ^^^^^^^^^^^^^^^^^^^^
|
2472
2504
|
class MatchWriteNode < Node
|
2473
2505
|
attr_reader call: CallNode
|
2474
|
-
attr_reader
|
2506
|
+
attr_reader targets: Array[Node]
|
2475
2507
|
|
2476
|
-
def initialize: (call: CallNode,
|
2508
|
+
def initialize: (call: CallNode, targets: Array[Node], location: Location) -> void
|
2477
2509
|
def accept: (visitor: Visitor) -> void
|
2478
2510
|
def set_newline_flag: (newline_marked: Array[bool]) -> void
|
2479
2511
|
def child_nodes: () -> Array[Node?]
|
@@ -3334,26 +3366,6 @@ module Prism
|
|
3334
3366
|
|
3335
3367
|
def inspect: (inspector: NodeInspector) -> String
|
3336
3368
|
end
|
3337
|
-
# Represents the use of compile-time string concatenation.
|
3338
|
-
#
|
3339
|
-
# "foo" "bar"
|
3340
|
-
# ^^^^^^^^^^^
|
3341
|
-
class StringConcatNode < Node
|
3342
|
-
attr_reader left: Node
|
3343
|
-
attr_reader right: Node
|
3344
|
-
|
3345
|
-
def initialize: (left: Node, right: Node, location: Location) -> void
|
3346
|
-
def accept: (visitor: Visitor) -> void
|
3347
|
-
def set_newline_flag: (newline_marked: Array[bool]) -> void
|
3348
|
-
def child_nodes: () -> Array[Node?]
|
3349
|
-
def deconstruct: () -> Array[Node?]
|
3350
|
-
|
3351
|
-
def copy: (**untyped) -> StringConcatNode
|
3352
|
-
|
3353
|
-
def deconstruct_keys: (keys: Array[Symbol]) -> Hash[Symbol, (Node | Array[Node] | String | Token | Array[Token] | Location)?]
|
3354
|
-
|
3355
|
-
def inspect: (inspector: NodeInspector) -> String
|
3356
|
-
end
|
3357
3369
|
# Represents a string literal, a string contained within a `%w` list, or
|
3358
3370
|
# plain string content within an interpolated string.
|
3359
3371
|
#
|
@@ -3505,11 +3517,12 @@ module Prism
|
|
3505
3517
|
class UnlessNode < Node
|
3506
3518
|
attr_reader keyword_loc: Location
|
3507
3519
|
attr_reader predicate: Node
|
3520
|
+
attr_reader then_keyword_loc: Location?
|
3508
3521
|
attr_reader statements: StatementsNode?
|
3509
3522
|
attr_reader consequent: ElseNode?
|
3510
3523
|
attr_reader end_keyword_loc: Location?
|
3511
3524
|
|
3512
|
-
def initialize: (keyword_loc: Location, predicate: Node, statements: StatementsNode?, consequent: ElseNode?, end_keyword_loc: Location?, location: Location) -> void
|
3525
|
+
def initialize: (keyword_loc: Location, predicate: Node, then_keyword_loc: Location?, statements: StatementsNode?, consequent: ElseNode?, end_keyword_loc: Location?, location: Location) -> void
|
3513
3526
|
def accept: (visitor: Visitor) -> void
|
3514
3527
|
def set_newline_flag: (newline_marked: Array[bool]) -> void
|
3515
3528
|
def child_nodes: () -> Array[Node?]
|
@@ -3521,6 +3534,8 @@ module Prism
|
|
3521
3534
|
|
3522
3535
|
def keyword: () -> String
|
3523
3536
|
|
3537
|
+
def then_keyword: () -> String?
|
3538
|
+
|
3524
3539
|
def end_keyword: () -> String?
|
3525
3540
|
|
3526
3541
|
def inspect: (inspector: NodeInspector) -> String
|
@@ -3803,6 +3818,9 @@ module Prism
|
|
3803
3818
|
# Visit a CapturePatternNode node
|
3804
3819
|
def visit_capture_pattern_node: (node: CapturePatternNode) -> void
|
3805
3820
|
|
3821
|
+
# Visit a CaseMatchNode node
|
3822
|
+
def visit_case_match_node: (node: CaseMatchNode) -> void
|
3823
|
+
|
3806
3824
|
# Visit a CaseNode node
|
3807
3825
|
def visit_case_node: (node: CaseNode) -> void
|
3808
3826
|
|
@@ -4133,9 +4151,6 @@ module Prism
|
|
4133
4151
|
# Visit a StatementsNode node
|
4134
4152
|
def visit_statements_node: (node: StatementsNode) -> void
|
4135
4153
|
|
4136
|
-
# Visit a StringConcatNode node
|
4137
|
-
def visit_string_concat_node: (node: StringConcatNode) -> void
|
4138
|
-
|
4139
4154
|
# Visit a StringNode node
|
4140
4155
|
def visit_string_node: (node: StringNode) -> void
|
4141
4156
|
|
@@ -4220,6 +4235,8 @@ module Prism
|
|
4220
4235
|
def CallOrWriteNode: (receiver: Node?, call_operator_loc: Location?, message_loc: Location?, flags: Integer, read_name: Symbol, write_name: Symbol, operator_loc: Location, value: Node, location: Location) -> CallOrWriteNode
|
4221
4236
|
# Create a new CapturePatternNode node
|
4222
4237
|
def CapturePatternNode: (value: Node, target: Node, operator_loc: Location, location: Location) -> CapturePatternNode
|
4238
|
+
# Create a new CaseMatchNode node
|
4239
|
+
def CaseMatchNode: (predicate: Node?, conditions: Array[Node], consequent: ElseNode?, case_keyword_loc: Location, end_keyword_loc: Location, location: Location) -> CaseMatchNode
|
4223
4240
|
# Create a new CaseNode node
|
4224
4241
|
def CaseNode: (predicate: Node?, conditions: Array[Node], consequent: ElseNode?, case_keyword_loc: Location, end_keyword_loc: Location, location: Location) -> CaseNode
|
4225
4242
|
# Create a new ClassNode node
|
@@ -4305,7 +4322,7 @@ module Prism
|
|
4305
4322
|
# Create a new HashPatternNode node
|
4306
4323
|
def HashPatternNode: (constant: Node?, elements: Array[Node], rest: Node?, opening_loc: Location?, closing_loc: Location?, location: Location) -> HashPatternNode
|
4307
4324
|
# Create a new IfNode node
|
4308
|
-
def IfNode: (if_keyword_loc: Location?, predicate: Node, statements: StatementsNode?, consequent: Node?, end_keyword_loc: Location?, location: Location) -> IfNode
|
4325
|
+
def IfNode: (if_keyword_loc: Location?, predicate: Node, then_keyword_loc: Location?, statements: StatementsNode?, consequent: Node?, end_keyword_loc: Location?, location: Location) -> IfNode
|
4309
4326
|
# Create a new ImaginaryNode node
|
4310
4327
|
def ImaginaryNode: (numeric: Node, location: Location) -> ImaginaryNode
|
4311
4328
|
# Create a new ImplicitNode node
|
@@ -4367,7 +4384,7 @@ module Prism
|
|
4367
4384
|
# Create a new MatchRequiredNode node
|
4368
4385
|
def MatchRequiredNode: (value: Node, pattern: Node, operator_loc: Location, location: Location) -> MatchRequiredNode
|
4369
4386
|
# Create a new MatchWriteNode node
|
4370
|
-
def MatchWriteNode: (call: CallNode,
|
4387
|
+
def MatchWriteNode: (call: CallNode, targets: Array[Node], location: Location) -> MatchWriteNode
|
4371
4388
|
# Create a new MissingNode node
|
4372
4389
|
def MissingNode: (location: Location) -> MissingNode
|
4373
4390
|
# Create a new ModuleNode node
|
@@ -4440,8 +4457,6 @@ module Prism
|
|
4440
4457
|
def SplatNode: (operator_loc: Location, expression: Node?, location: Location) -> SplatNode
|
4441
4458
|
# Create a new StatementsNode node
|
4442
4459
|
def StatementsNode: (body: Array[Node], location: Location) -> StatementsNode
|
4443
|
-
# Create a new StringConcatNode node
|
4444
|
-
def StringConcatNode: (left: Node, right: Node, location: Location) -> StringConcatNode
|
4445
4460
|
# Create a new StringNode node
|
4446
4461
|
def StringNode: (flags: Integer, opening_loc: Location?, content_loc: Location, closing_loc: Location?, unescaped: String, location: Location) -> StringNode
|
4447
4462
|
# Create a new SuperNode node
|
@@ -4453,7 +4468,7 @@ module Prism
|
|
4453
4468
|
# Create a new UndefNode node
|
4454
4469
|
def UndefNode: (names: Array[Node], keyword_loc: Location, location: Location) -> UndefNode
|
4455
4470
|
# Create a new UnlessNode node
|
4456
|
-
def UnlessNode: (keyword_loc: Location, predicate: Node, statements: StatementsNode?, consequent: ElseNode?, end_keyword_loc: Location?, location: Location) -> UnlessNode
|
4471
|
+
def UnlessNode: (keyword_loc: Location, predicate: Node, then_keyword_loc: Location?, statements: StatementsNode?, consequent: ElseNode?, end_keyword_loc: Location?, location: Location) -> UnlessNode
|
4457
4472
|
# Create a new UntilNode node
|
4458
4473
|
def UntilNode: (keyword_loc: Location, closing_loc: Location?, predicate: Node, statements: StatementsNode?, flags: Integer, location: Location) -> UntilNode
|
4459
4474
|
# Create a new WhenNode node
|
data/src/diagnostic.c
CHANGED
@@ -54,12 +54,14 @@ static const char* const diagnostic_messages[PM_DIAGNOSTIC_ID_LEN] = {
|
|
54
54
|
[PM_ERR_ALIAS_ARGUMENT] = "Invalid argument being passed to `alias`; expected a bare word, symbol, constant, or global variable",
|
55
55
|
[PM_ERR_AMPAMPEQ_MULTI_ASSIGN] = "Unexpected `&&=` in a multiple assignment",
|
56
56
|
[PM_ERR_ARGUMENT_AFTER_BLOCK] = "Unexpected argument after a block argument",
|
57
|
+
[PM_ERR_ARGUMENT_AFTER_FORWARDING_ELLIPSES] = "Unexpected argument after `...`",
|
57
58
|
[PM_ERR_ARGUMENT_BARE_HASH] = "Unexpected bare hash argument",
|
58
59
|
[PM_ERR_ARGUMENT_BLOCK_MULTI] = "Multiple block arguments; only one block is allowed",
|
59
60
|
[PM_ERR_ARGUMENT_FORMAL_CLASS] = "Invalid formal argument; formal argument cannot be a class variable",
|
60
61
|
[PM_ERR_ARGUMENT_FORMAL_CONSTANT] = "Invalid formal argument; formal argument cannot be a constant",
|
61
62
|
[PM_ERR_ARGUMENT_FORMAL_GLOBAL] = "Invalid formal argument; formal argument cannot be a global variable",
|
62
63
|
[PM_ERR_ARGUMENT_FORMAL_IVAR] = "Invalid formal argument; formal argument cannot be an instance variable",
|
64
|
+
[PM_ERR_ARGUMENT_FORWARDING_UNBOUND] = "Unexpected `...` in an non-parenthesized call",
|
63
65
|
[PM_ERR_ARGUMENT_NO_FORWARDING_AMP] = "Unexpected `&` when the parent method is not forwarding",
|
64
66
|
[PM_ERR_ARGUMENT_NO_FORWARDING_ELLIPSES] = "Unexpected `...` when the parent method is not forwarding",
|
65
67
|
[PM_ERR_ARGUMENT_NO_FORWARDING_STAR] = "Unexpected `*` when the parent method is not forwarding",
|
@@ -85,6 +87,7 @@ static const char* const diagnostic_messages[PM_DIAGNOSTIC_ID_LEN] = {
|
|
85
87
|
[PM_ERR_CANNOT_PARSE_STRING_PART] = "Cannot parse the string part",
|
86
88
|
[PM_ERR_CASE_EXPRESSION_AFTER_CASE] = "Expected an expression after `case`",
|
87
89
|
[PM_ERR_CASE_EXPRESSION_AFTER_WHEN] = "Expected an expression after `when`",
|
90
|
+
[PM_ERR_CASE_MATCH_MISSING_PREDICATE] = "Expected a predicate for a case matching statement",
|
88
91
|
[PM_ERR_CASE_MISSING_CONDITIONS] = "Expected a `when` or `in` clause after `case`",
|
89
92
|
[PM_ERR_CASE_TERM] = "Expected an `end` to close the `case` statement",
|
90
93
|
[PM_ERR_CLASS_IN_METHOD] = "Unexpected class definition in a method body",
|
@@ -199,7 +202,7 @@ static const char* const diagnostic_messages[PM_DIAGNOSTIC_ID_LEN] = {
|
|
199
202
|
[PM_ERR_PARAMETER_NAME_REPEAT] = "Repeated parameter name",
|
200
203
|
[PM_ERR_PARAMETER_NO_DEFAULT] = "Expected a default value for the parameter",
|
201
204
|
[PM_ERR_PARAMETER_NO_DEFAULT_KW] = "Expected a default value for the keyword parameter",
|
202
|
-
[PM_ERR_PARAMETER_NUMBERED_RESERVED] = "
|
205
|
+
[PM_ERR_PARAMETER_NUMBERED_RESERVED] = "%.2s is reserved for a numbered parameter",
|
203
206
|
[PM_ERR_PARAMETER_ORDER] = "Unexpected parameter order",
|
204
207
|
[PM_ERR_PARAMETER_SPLAT_MULTI] = "Unexpected multiple `*` splat parameters",
|
205
208
|
[PM_ERR_PARAMETER_STAR] = "Unexpected parameter `*`",
|
@@ -244,6 +247,7 @@ static const char* const diagnostic_messages[PM_DIAGNOSTIC_ID_LEN] = {
|
|
244
247
|
[PM_ERR_UNARY_RECEIVER_PLUS] = "Expected a receiver for unary `+`",
|
245
248
|
[PM_ERR_UNARY_RECEIVER_TILDE] = "Expected a receiver for unary `~`",
|
246
249
|
[PM_ERR_UNTIL_TERM] = "Expected an `end` to close the `until` statement",
|
250
|
+
[PM_ERR_VOID_EXPRESSION] = "Unexpected void value expression",
|
247
251
|
[PM_ERR_WHILE_TERM] = "Expected an `end` to close the `while` statement",
|
248
252
|
[PM_ERR_WRITE_TARGET_READONLY] = "Immutable variable as a write target",
|
249
253
|
[PM_ERR_WRITE_TARGET_UNEXPECTED] = "Unexpected write target",
|
@@ -252,13 +256,16 @@ static const char* const diagnostic_messages[PM_DIAGNOSTIC_ID_LEN] = {
|
|
252
256
|
[PM_WARN_AMBIGUOUS_FIRST_ARGUMENT_PLUS] = "Ambiguous first argument; put parentheses or a space even after `+` operator",
|
253
257
|
[PM_WARN_AMBIGUOUS_PREFIX_STAR] = "Ambiguous `*` has been interpreted as an argument prefix",
|
254
258
|
[PM_WARN_AMBIGUOUS_SLASH] = "Ambiguous `/`; wrap regexp in parentheses or add a space after `/` operator",
|
259
|
+
[PM_WARN_END_IN_METHOD] = "END in method; use at_exit",
|
255
260
|
};
|
256
261
|
|
257
262
|
static const char*
|
258
263
|
pm_diagnostic_message(pm_diagnostic_id_t diag_id) {
|
259
264
|
assert(diag_id < PM_DIAGNOSTIC_ID_LEN);
|
265
|
+
|
260
266
|
const char *message = diagnostic_messages[diag_id];
|
261
267
|
assert(message);
|
268
|
+
|
262
269
|
return message;
|
263
270
|
}
|
264
271
|
|
@@ -270,7 +277,57 @@ pm_diagnostic_list_append(pm_list_t *list, const uint8_t *start, const uint8_t *
|
|
270
277
|
pm_diagnostic_t *diagnostic = (pm_diagnostic_t *) calloc(sizeof(pm_diagnostic_t), 1);
|
271
278
|
if (diagnostic == NULL) return false;
|
272
279
|
|
273
|
-
*diagnostic = (pm_diagnostic_t) {
|
280
|
+
*diagnostic = (pm_diagnostic_t) {
|
281
|
+
.start = start,
|
282
|
+
.end = end,
|
283
|
+
.message = pm_diagnostic_message(diag_id),
|
284
|
+
.owned = false
|
285
|
+
};
|
286
|
+
|
287
|
+
pm_list_append(list, (pm_list_node_t *) diagnostic);
|
288
|
+
return true;
|
289
|
+
}
|
290
|
+
|
291
|
+
/**
|
292
|
+
* Append a diagnostic to the given list of diagnostics that is using a format
|
293
|
+
* string for its message.
|
294
|
+
*/
|
295
|
+
bool
|
296
|
+
pm_diagnostic_list_append_format(pm_list_t *list, const uint8_t *start, const uint8_t *end, pm_diagnostic_id_t diag_id, ...) {
|
297
|
+
va_list arguments;
|
298
|
+
va_start(arguments, diag_id);
|
299
|
+
|
300
|
+
const char *format = pm_diagnostic_message(diag_id);
|
301
|
+
int result = vsnprintf(NULL, 0, format, arguments);
|
302
|
+
va_end(arguments);
|
303
|
+
|
304
|
+
if (result < 0) {
|
305
|
+
return false;
|
306
|
+
}
|
307
|
+
|
308
|
+
pm_diagnostic_t *diagnostic = (pm_diagnostic_t *) calloc(sizeof(pm_diagnostic_t), 1);
|
309
|
+
if (diagnostic == NULL) {
|
310
|
+
return false;
|
311
|
+
}
|
312
|
+
|
313
|
+
size_t length = (size_t) (result + 1);
|
314
|
+
char *message = (char *) malloc(length);
|
315
|
+
if (message == NULL) {
|
316
|
+
free(diagnostic);
|
317
|
+
return false;
|
318
|
+
}
|
319
|
+
|
320
|
+
va_start(arguments, diag_id);
|
321
|
+
vsnprintf(message, length, format, arguments);
|
322
|
+
va_end(arguments);
|
323
|
+
|
324
|
+
*diagnostic = (pm_diagnostic_t) {
|
325
|
+
.start = start,
|
326
|
+
.end = end,
|
327
|
+
.message = message,
|
328
|
+
.owned = true
|
329
|
+
};
|
330
|
+
|
274
331
|
pm_list_append(list, (pm_list_node_t *) diagnostic);
|
275
332
|
return true;
|
276
333
|
}
|
@@ -284,8 +341,9 @@ pm_diagnostic_list_free(pm_list_t *list) {
|
|
284
341
|
|
285
342
|
for (node = list->head; node != NULL; node = next) {
|
286
343
|
next = node->next;
|
287
|
-
|
288
344
|
pm_diagnostic_t *diagnostic = (pm_diagnostic_t *) node;
|
345
|
+
|
346
|
+
if (diagnostic->owned) free((void *) diagnostic->message);
|
289
347
|
free(diagnostic);
|
290
348
|
}
|
291
349
|
}
|
data/src/enc/pm_big5.c
CHANGED
@@ -15,6 +15,22 @@ pm_encoding_big5_char_width(const uint8_t *b, ptrdiff_t n) {
|
|
15
15
|
return 0;
|
16
16
|
}
|
17
17
|
|
18
|
+
static size_t
|
19
|
+
pm_encoding_big5_star_char_width(const uint8_t *b, ptrdiff_t n) {
|
20
|
+
// These are the single byte characters.
|
21
|
+
if (*b < 0x80) {
|
22
|
+
return 1;
|
23
|
+
}
|
24
|
+
|
25
|
+
// These are the double byte characters.
|
26
|
+
if ((n > 1) && (b[0] >= 0x87 && b[0] <= 0xFE) &&
|
27
|
+
((b[1] >= 0x40 && b[1] <= 0x7E) || (b[1] >= 0xA1 && b[1] <= 0xFE))) {
|
28
|
+
return 2;
|
29
|
+
}
|
30
|
+
|
31
|
+
return 0;
|
32
|
+
}
|
33
|
+
|
18
34
|
static size_t
|
19
35
|
pm_encoding_big5_alpha_char(const uint8_t *b, ptrdiff_t n) {
|
20
36
|
if (pm_encoding_big5_char_width(b, n) == 1) {
|
@@ -24,6 +40,15 @@ pm_encoding_big5_alpha_char(const uint8_t *b, ptrdiff_t n) {
|
|
24
40
|
}
|
25
41
|
}
|
26
42
|
|
43
|
+
static size_t
|
44
|
+
pm_encoding_big5_star_alpha_char(const uint8_t *b, ptrdiff_t n) {
|
45
|
+
if (pm_encoding_big5_star_char_width(b, n) == 1) {
|
46
|
+
return pm_encoding_ascii_alpha_char(b, n);
|
47
|
+
} else {
|
48
|
+
return 0;
|
49
|
+
}
|
50
|
+
}
|
51
|
+
|
27
52
|
static size_t
|
28
53
|
pm_encoding_big5_alnum_char(const uint8_t *b, ptrdiff_t n) {
|
29
54
|
if (pm_encoding_big5_char_width(b, n) == 1) {
|
@@ -33,6 +58,15 @@ pm_encoding_big5_alnum_char(const uint8_t *b, ptrdiff_t n) {
|
|
33
58
|
}
|
34
59
|
}
|
35
60
|
|
61
|
+
static size_t
|
62
|
+
pm_encoding_big5_star_alnum_char(const uint8_t *b, ptrdiff_t n) {
|
63
|
+
if (pm_encoding_big5_star_char_width(b, n) == 1) {
|
64
|
+
return pm_encoding_ascii_alnum_char(b, n);
|
65
|
+
} else {
|
66
|
+
return 0;
|
67
|
+
}
|
68
|
+
}
|
69
|
+
|
36
70
|
static bool
|
37
71
|
pm_encoding_big5_isupper_char(const uint8_t *b, ptrdiff_t n) {
|
38
72
|
if (pm_encoding_big5_char_width(b, n) == 1) {
|
@@ -42,6 +76,15 @@ pm_encoding_big5_isupper_char(const uint8_t *b, ptrdiff_t n) {
|
|
42
76
|
}
|
43
77
|
}
|
44
78
|
|
79
|
+
static bool
|
80
|
+
pm_encoding_big5_star_isupper_char(const uint8_t *b, ptrdiff_t n) {
|
81
|
+
if (pm_encoding_big5_star_char_width(b, n) == 1) {
|
82
|
+
return pm_encoding_ascii_isupper_char(b, n);
|
83
|
+
} else {
|
84
|
+
return false;
|
85
|
+
}
|
86
|
+
}
|
87
|
+
|
45
88
|
/** Big5 encoding */
|
46
89
|
pm_encoding_t pm_encoding_big5 = {
|
47
90
|
.name = "big5",
|
@@ -51,3 +94,23 @@ pm_encoding_t pm_encoding_big5 = {
|
|
51
94
|
.isupper_char = pm_encoding_big5_isupper_char,
|
52
95
|
.multibyte = true
|
53
96
|
};
|
97
|
+
|
98
|
+
/** Big5-HKSCS encoding */
|
99
|
+
pm_encoding_t pm_encoding_big5_hkscs = {
|
100
|
+
.name = "big5-hkscs",
|
101
|
+
.char_width = pm_encoding_big5_star_char_width,
|
102
|
+
.alnum_char = pm_encoding_big5_star_alnum_char,
|
103
|
+
.alpha_char = pm_encoding_big5_star_alpha_char,
|
104
|
+
.isupper_char = pm_encoding_big5_star_isupper_char,
|
105
|
+
.multibyte = true
|
106
|
+
};
|
107
|
+
|
108
|
+
/** Big5-UAO encoding */
|
109
|
+
pm_encoding_t pm_encoding_big5_uao = {
|
110
|
+
.name = "big5-uao",
|
111
|
+
.char_width = pm_encoding_big5_star_char_width,
|
112
|
+
.alnum_char = pm_encoding_big5_star_alnum_char,
|
113
|
+
.alpha_char = pm_encoding_big5_star_alpha_char,
|
114
|
+
.isupper_char = pm_encoding_big5_star_isupper_char,
|
115
|
+
.multibyte = true
|
116
|
+
};
|