herb 0.11.1 → 0.11.2
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.
- checksums.yaml +4 -4
- data/Rakefile +4 -2
- data/config.yml +6 -0
- data/ext/herb/extconf.rb +8 -31
- data/ext/herb/nodes.c +75 -75
- data/ext/herb/parser_options_helpers.c +26 -0
- data/lib/herb/analysis/partial_index.rb +1 -1
- data/lib/herb/analysis/partial_resolution.rb +27 -0
- data/lib/herb/ast/helpers.rb +1 -1
- data/lib/herb/configuration.rb +11 -1
- data/lib/herb/dev/classifier.rb +1 -1
- data/lib/herb/engine/compiler.rb +5 -8
- data/lib/herb/engine/slots/dynamics_compiler.rb +53 -14
- data/lib/herb/engine/slots/subtree_compiler.rb +1 -1
- data/lib/herb/engine/slots/visitor.rb +32 -4
- data/lib/herb/engine/visitors/instrumentation_visitor.rb +18 -6
- data/lib/herb/parser_options.rb +6 -3
- data/lib/herb/project.rb +19 -8
- data/lib/herb/version.rb +1 -1
- data/lib/herb.rb +1 -1
- data/sig/herb/analysis/partial_resolution.rbs +8 -0
- data/sig/herb/configuration.rbs +3 -0
- data/sig/herb/engine/slots/dynamics_compiler.rbs +24 -7
- data/sig/herb/engine/slots/visitor.rbs +14 -0
- data/sig/herb/engine/visitors/instrumentation_visitor.rbs +5 -1
- data/sig/herb/parser_options.rbs +6 -4
- data/sig/herb.rbs +2 -2
- data/src/analyze/action_view/attribute_extraction_helpers.c +40 -21
- data/src/analyze/action_view/generated_handlers.c +36 -36
- data/src/analyze/action_view/image_tag.c +7 -3
- data/src/analyze/action_view/javascript_include_tag.c +6 -3
- data/src/analyze/action_view/link_to.c +23 -23
- data/src/analyze/action_view/registry.c +7 -3
- data/src/analyze/action_view/tag_helper_node_builders.c +6 -13
- data/src/analyze/action_view/tag_helpers.c +139 -90
- data/src/analyze/action_view/turbo_frame_tag.c +5 -4
- data/src/analyze/analyze.c +35 -19
- data/src/analyze/analyze_helpers.c +161 -188
- data/src/analyze/analyzed_ruby.c +8 -7
- data/src/analyze/control_type.c +29 -22
- data/src/analyze/herb_directives.c +16 -20
- data/src/analyze/iteration_nodes.c +69 -24
- data/src/analyze/parse_errors.c +32 -22
- data/src/analyze/postfix_conditionals.c +23 -13
- data/src/analyze/prism_annotate.c +29 -28
- data/src/analyze/render_nodes.c +51 -41
- data/src/analyze/strict_locals.c +14 -15
- data/src/analyze/ternary_conditionals.c +14 -10
- data/src/herb.c +10 -8
- data/src/include/analyze/action_view/tag_helper_handler.h +1 -1
- data/src/include/analyze/action_view/tag_helper_node_builders.h +1 -0
- data/src/include/analyze/action_view/tag_helpers.h +1 -1
- data/src/include/analyze/analyze.h +3 -2
- data/src/include/analyze/analyzed_ruby.h +4 -2
- data/src/include/analyze/helpers.h +6 -6
- data/src/include/herb.h +3 -2
- data/src/include/parser/parser_options.h +5 -0
- data/src/include/prism/prism_context.h +12 -12
- data/src/include/prism/prism_helpers.h +30 -0
- data/src/include/prism_version.h +11 -0
- data/src/include/version.h +1 -1
- data/src/parser/parser_helpers.c +1 -2
- data/src/parser.c +6 -7
- data/src/parser_options_defaults.c +1 -0
- data/src/prism/prism_helpers.c +84 -50
- data/src/prism/ruby_parser.c +20 -20
- data/templates/ext/herb/nodes.c.erb +5 -5
- data/templates/ext/herb/parser_options_helpers.c.erb +33 -0
- data/templates/java/nodes.c.erb +6 -6
- data/templates/java/parser_options_helpers.c.erb +41 -2
- data/templates/java/parser_options_helpers.h.erb +2 -1
- data/templates/javascript/packages/node/extension/nodes.cpp.erb +5 -5
- data/templates/javascript/packages/node/extension/parser_options_helpers.cpp.erb +34 -2
- data/templates/javascript/packages/node/extension/parser_options_helpers.h.erb +1 -1
- data/templates/lib/herb/parser_options.rb.erb +1 -1
- data/templates/rust/src/prism/generated_deserialize.rs.erb +90 -44
- data/templates/rust/src/prism/generated_prettyprint.rs.erb +18 -27
- data/templates/src/analyze/action_view/generated_handlers.c.erb +23 -22
- data/templates/src/include/parser/parser_options.h.erb +10 -0
- data/templates/src/include/prism_version.h.erb +17 -0
- data/templates/src/parser_options_defaults.c.erb +1 -1
- data/templates/template.rb +17 -2
- data/templates/wasm/nodes.cpp.erb +5 -5
- data/templates/wasm/parser_options_helpers.cpp.erb +24 -0
- data/vendor/prism/Rakefile +76 -7
- data/vendor/prism/config.yml +174 -161
- data/vendor/prism/include/prism/arena.h +45 -0
- data/vendor/prism/include/prism/arena.hpp +42 -0
- data/vendor/prism/include/prism/ast.h +2738 -611
- data/vendor/prism/include/prism/ast.hpp +641 -0
- data/vendor/prism/include/prism/buffer.h +60 -0
- data/vendor/prism/include/prism/buffer.hpp +55 -0
- data/vendor/prism/include/prism/comments.h +72 -0
- data/vendor/prism/include/prism/compiler/accel.h +26 -0
- data/vendor/prism/include/prism/compiler/align.h +36 -0
- data/vendor/prism/include/prism/compiler/assume.h +25 -0
- data/vendor/prism/include/prism/compiler/branch.h +26 -0
- data/vendor/prism/include/prism/compiler/bswap.h +46 -0
- data/vendor/prism/include/prism/compiler/cplusplus.hpp +16 -0
- data/vendor/prism/include/prism/compiler/endianness.h +34 -0
- data/vendor/prism/include/prism/compiler/exceptions.hpp +17 -0
- data/vendor/prism/include/prism/compiler/exported.h +24 -0
- data/vendor/prism/include/prism/compiler/fallthrough.h +22 -0
- data/vendor/prism/include/prism/compiler/filesystem.h +32 -0
- data/vendor/prism/include/prism/compiler/flex_array.h +19 -0
- data/vendor/prism/include/prism/compiler/force_inline.h +21 -0
- data/vendor/prism/include/prism/compiler/format.h +27 -0
- data/vendor/prism/include/prism/compiler/inline.h +17 -0
- data/vendor/prism/include/prism/compiler/lifetimebound.hpp +25 -0
- data/vendor/prism/include/prism/compiler/nodiscard.h +22 -0
- data/vendor/prism/include/prism/compiler/nonnull.h +18 -0
- data/vendor/prism/include/prism/compiler/unused.h +18 -0
- data/vendor/prism/include/prism/constant_pool.h +106 -0
- data/vendor/prism/include/prism/diagnostic.h +55 -402
- data/vendor/prism/include/prism/errors_format.h +61 -0
- data/vendor/prism/include/prism/excludes.h +29 -0
- data/vendor/prism/include/prism/integer.h +41 -0
- data/vendor/prism/include/prism/internal/allocator.h +68 -0
- data/vendor/prism/include/prism/internal/allocator_debug.h +88 -0
- data/vendor/prism/include/prism/internal/arena.h +108 -0
- data/vendor/prism/include/prism/internal/bit.h +42 -0
- data/vendor/prism/include/prism/internal/buffer.h +94 -0
- data/vendor/prism/include/prism/internal/char.h +145 -0
- data/vendor/prism/include/prism/internal/comments.h +54 -0
- data/vendor/prism/include/prism/internal/constant_pool.h +152 -0
- data/vendor/prism/include/prism/internal/diagnostic.h +389 -0
- data/vendor/prism/include/prism/{encoding.h → internal/encoding.h} +27 -68
- data/vendor/prism/include/prism/internal/integer.h +68 -0
- data/vendor/prism/include/prism/internal/isinf.h +16 -0
- data/vendor/prism/include/prism/internal/line_offset_list.h +34 -0
- data/vendor/prism/include/prism/{util/pm_list.h → internal/list.h} +11 -52
- data/vendor/prism/include/prism/internal/magic_comments.h +23 -0
- data/vendor/prism/include/prism/internal/memchr.h +15 -0
- data/vendor/prism/include/prism/internal/node.h +42 -0
- data/vendor/prism/include/prism/internal/options.h +232 -0
- data/vendor/prism/include/prism/internal/parser.h +1015 -0
- data/vendor/prism/include/prism/internal/regexp.h +26 -0
- data/vendor/prism/include/prism/internal/serialize.h +39 -0
- data/vendor/prism/include/prism/internal/source.h +72 -0
- data/vendor/prism/include/prism/internal/static_literals.h +60 -0
- data/vendor/prism/include/prism/internal/stringy.h +30 -0
- data/vendor/prism/include/prism/{util/pm_strncasecmp.h → internal/strncasecmp.h} +3 -17
- data/vendor/prism/include/prism/{util/pm_strpbrk.h → internal/strpbrk.h} +7 -20
- data/vendor/prism/include/prism/internal/tokens.h +11 -0
- data/vendor/prism/include/prism/internal/xxh3.h +16 -0
- data/vendor/prism/include/prism/json.h +40 -0
- data/vendor/prism/include/prism/line_offset_list.h +69 -0
- data/vendor/prism/include/prism/magic_comments.h +53 -0
- data/vendor/prism/include/prism/node.h +59 -49
- data/vendor/prism/include/prism/node.hpp +272 -0
- data/vendor/prism/include/prism/node_type.hpp +38 -0
- data/vendor/prism/include/prism/options.h +154 -279
- data/vendor/prism/include/prism/options.hpp +43 -0
- data/vendor/prism/include/prism/parser.h +367 -870
- data/vendor/prism/include/prism/parser.hpp +274 -0
- data/vendor/prism/include/prism/prettyprint.h +14 -9
- data/vendor/prism/include/prism/serialize.h +123 -0
- data/vendor/prism/include/prism/source.h +163 -0
- data/vendor/prism/include/prism/stream.h +36 -0
- data/vendor/prism/include/prism/string_query.h +82 -0
- data/vendor/prism/include/prism/stringy.h +61 -0
- data/vendor/prism/include/prism/stringy.hpp +31 -0
- data/vendor/prism/include/prism/version.h +20 -3
- data/vendor/prism/include/prism.h +35 -320
- data/vendor/prism/include/prism.hpp +24 -0
- data/vendor/prism/src/arena.c +122 -0
- data/vendor/prism/src/{util/pm_buffer.c → buffer.c} +53 -21
- data/vendor/prism/src/{util/pm_char.c → char.c} +28 -57
- data/vendor/prism/src/comments.c +455 -0
- data/vendor/prism/src/constant_pool.c +406 -0
- data/vendor/prism/src/diagnostic.c +120 -68
- data/vendor/prism/src/encoding.c +8 -3
- data/vendor/prism/src/errors_format.c +519 -0
- data/vendor/prism/src/{util/pm_integer.c → integer.c} +38 -22
- data/vendor/prism/src/json.c +5733 -0
- data/vendor/prism/src/line_offset_list.c +100 -0
- data/vendor/prism/src/list.c +24 -0
- data/vendor/prism/src/{util/pm_memchr.c → memchr.c} +8 -6
- data/vendor/prism/src/node.c +3465 -7787
- data/vendor/prism/src/options.c +161 -54
- data/vendor/prism/src/parser.c +371 -0
- data/vendor/prism/src/prettyprint.c +421 -354
- data/vendor/prism/src/prism.c +8522 -7280
- data/vendor/prism/src/regexp.c +960 -45
- data/vendor/prism/src/serialize.c +2434 -2048
- data/vendor/prism/src/source.c +524 -0
- data/vendor/prism/src/static_literals.c +303 -360
- data/vendor/prism/src/string_query.c +180 -0
- data/vendor/prism/src/stringy.c +61 -0
- data/vendor/prism/src/{util/pm_strncasecmp.c → strncasecmp.c} +5 -4
- data/vendor/prism/src/strpbrk.c +447 -0
- data/vendor/prism/src/{token_type.c → tokens.c} +39 -18
- data/vendor/prism/src/xxh3.c +292 -0
- data/vendor/prism/templates/ext/prism/api_node.c.erb +58 -44
- data/vendor/prism/templates/include/prism/ast.h.erb +67 -17
- data/vendor/prism/templates/include/prism/ast.hpp.erb +31 -0
- data/vendor/prism/templates/include/prism/internal/diagnostic.h.erb +60 -0
- data/vendor/prism/templates/java/{org → api/src/main/java-templates/org/ruby_lang}/prism/AbstractNodeVisitor.java.erb +1 -1
- data/vendor/prism/templates/java/{org → api/src/main/java-templates/org/ruby_lang}/prism/Loader.java.erb +232 -133
- data/vendor/prism/templates/java/{org → api/src/main/java-templates/org/ruby_lang}/prism/Nodes.java.erb +62 -23
- data/vendor/prism/templates/javascript/src/deserialize.js.erb +153 -146
- data/vendor/prism/templates/javascript/src/nodes.js.erb +4 -9
- data/vendor/prism/templates/lib/prism/compiler.rb.erb +14 -5
- data/vendor/prism/templates/lib/prism/dispatcher.rb.erb +20 -12
- data/vendor/prism/templates/lib/prism/dot_visitor.rb.erb +37 -11
- data/vendor/prism/templates/lib/prism/dsl.rb.erb +43 -4
- data/vendor/prism/templates/lib/prism/inspect_visitor.rb.erb +26 -10
- data/vendor/prism/templates/lib/prism/mutation_compiler.rb.erb +5 -2
- data/vendor/prism/templates/lib/prism/node.rb.erb +283 -105
- data/vendor/prism/templates/lib/prism/reflection.rb.erb +11 -2
- data/vendor/prism/templates/lib/prism/serialize.rb.erb +291 -134
- data/vendor/prism/templates/lib/prism/visitor.rb.erb +18 -0
- data/vendor/prism/templates/src/diagnostic.c.erb +114 -63
- data/vendor/prism/templates/src/json.c.erb +130 -0
- data/vendor/prism/templates/src/node.c.erb +79 -236
- data/vendor/prism/templates/src/prettyprint.c.erb +24 -13
- data/vendor/prism/templates/src/serialize.c.erb +369 -183
- data/vendor/prism/templates/src/{token_type.c.erb → tokens.c.erb} +22 -11
- data/vendor/prism/templates/template.rb +193 -91
- metadata +100 -42
- data/vendor/prism/include/prism/defines.h +0 -260
- data/vendor/prism/include/prism/pack.h +0 -163
- data/vendor/prism/include/prism/regexp.h +0 -43
- data/vendor/prism/include/prism/static_literals.h +0 -121
- data/vendor/prism/include/prism/util/pm_buffer.h +0 -236
- data/vendor/prism/include/prism/util/pm_char.h +0 -204
- data/vendor/prism/include/prism/util/pm_constant_pool.h +0 -218
- data/vendor/prism/include/prism/util/pm_integer.h +0 -130
- data/vendor/prism/include/prism/util/pm_memchr.h +0 -29
- data/vendor/prism/include/prism/util/pm_newline_list.h +0 -113
- data/vendor/prism/include/prism/util/pm_string.h +0 -200
- data/vendor/prism/src/pack.c +0 -509
- data/vendor/prism/src/util/pm_constant_pool.c +0 -342
- data/vendor/prism/src/util/pm_list.c +0 -49
- data/vendor/prism/src/util/pm_newline_list.c +0 -125
- data/vendor/prism/src/util/pm_string.c +0 -381
- data/vendor/prism/src/util/pm_strpbrk.c +0 -206
- data/vendor/prism/templates/include/prism/diagnostic.h.erb +0 -130
- data/vendor/prism/templates/rbi/prism/dsl.rbi.erb +0 -68
- data/vendor/prism/templates/rbi/prism/node.rbi.erb +0 -167
- data/vendor/prism/templates/rbi/prism/visitor.rbi.erb +0 -18
- data/vendor/prism/templates/sig/prism/_private/dot_visitor.rbs.erb +0 -45
- data/vendor/prism/templates/sig/prism/dsl.rbs.erb +0 -31
- data/vendor/prism/templates/sig/prism/mutation_compiler.rbs.erb +0 -7
- data/vendor/prism/templates/sig/prism/node.rbs.erb +0 -136
- data/vendor/prism/templates/sig/prism/visitor.rbs.erb +0 -17
- data/vendor/prism/templates/sig/prism.rbs.erb +0 -92
data/src/analyze/analyzed_ruby.c
CHANGED
|
@@ -1,18 +1,20 @@
|
|
|
1
1
|
#include "../include/analyze/analyzed_ruby.h"
|
|
2
2
|
#include "../include/lib/hb_string.h"
|
|
3
|
+
#include "../include/prism/prism_helpers.h"
|
|
3
4
|
|
|
4
5
|
#include <prism.h>
|
|
5
6
|
#include <string.h>
|
|
6
7
|
|
|
7
|
-
analyzed_ruby_T* init_analyzed_ruby(hb_string_T source) {
|
|
8
|
+
analyzed_ruby_T* init_analyzed_ruby(hb_string_T source, const parser_options_T* options) {
|
|
8
9
|
analyzed_ruby_T* analyzed = malloc(sizeof(analyzed_ruby_T));
|
|
9
10
|
|
|
10
11
|
if (!analyzed) { return NULL; }
|
|
11
12
|
|
|
12
|
-
|
|
13
|
+
analyzed->arena = pm_arena_new();
|
|
14
|
+
analyzed->parser = herb_prism_parser_new(analyzed->arena, (const uint8_t*) source.data, source.length, options);
|
|
13
15
|
|
|
14
|
-
analyzed->root = pm_parse(
|
|
15
|
-
analyzed->valid = (analyzed->parser
|
|
16
|
+
analyzed->root = pm_parse(analyzed->parser);
|
|
17
|
+
analyzed->valid = (pm_parser_errors_size(analyzed->parser) == 0);
|
|
16
18
|
analyzed->parsed = true;
|
|
17
19
|
analyzed->if_node_count = 0;
|
|
18
20
|
analyzed->elsif_node_count = 0;
|
|
@@ -43,9 +45,8 @@ analyzed_ruby_T* init_analyzed_ruby(hb_string_T source) {
|
|
|
43
45
|
void free_analyzed_ruby(analyzed_ruby_T* analyzed) {
|
|
44
46
|
if (!analyzed) { return; }
|
|
45
47
|
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
pm_parser_free(&analyzed->parser);
|
|
48
|
+
pm_parser_free(analyzed->parser);
|
|
49
|
+
pm_arena_free(analyzed->arena);
|
|
49
50
|
|
|
50
51
|
free(analyzed);
|
|
51
52
|
}
|
data/src/analyze/control_type.c
CHANGED
|
@@ -6,6 +6,8 @@
|
|
|
6
6
|
#include "../include/errors.h"
|
|
7
7
|
#include "../include/lib/hb_array.h"
|
|
8
8
|
|
|
9
|
+
#include "../include/prism/prism_helpers.h"
|
|
10
|
+
|
|
9
11
|
#include <prism.h>
|
|
10
12
|
#include <stdbool.h>
|
|
11
13
|
#include <stdint.h>
|
|
@@ -29,8 +31,8 @@ static bool control_type_is_yield(control_type_t type) {
|
|
|
29
31
|
return type == CONTROL_TYPE_YIELD;
|
|
30
32
|
}
|
|
31
33
|
|
|
32
|
-
static
|
|
33
|
-
if (!node) { return
|
|
34
|
+
static pm_visit_result_t find_earliest_control_keyword_walker(const pm_node_t* node, void* data) {
|
|
35
|
+
if (!node) { return PM_VISIT_DESCEND; }
|
|
34
36
|
|
|
35
37
|
location_walker_context_T* context = (location_walker_context_T*) data;
|
|
36
38
|
earliest_control_keyword_T* result = context->result;
|
|
@@ -41,50 +43,52 @@ static bool find_earliest_control_keyword_walker(const pm_node_t* node, void* da
|
|
|
41
43
|
switch (node->type) {
|
|
42
44
|
case PM_IF_NODE: {
|
|
43
45
|
pm_if_node_t* if_node = (pm_if_node_t*) node;
|
|
46
|
+
if (!herb_prism_location_assigned(if_node->if_keyword_loc)) { break; }
|
|
47
|
+
|
|
44
48
|
current_type = CONTROL_TYPE_IF;
|
|
45
|
-
keyword_offset =
|
|
49
|
+
keyword_offset = if_node->if_keyword_loc.start;
|
|
46
50
|
break;
|
|
47
51
|
}
|
|
48
52
|
|
|
49
53
|
case PM_UNLESS_NODE: {
|
|
50
54
|
pm_unless_node_t* unless_node = (pm_unless_node_t*) node;
|
|
51
55
|
current_type = CONTROL_TYPE_UNLESS;
|
|
52
|
-
keyword_offset =
|
|
56
|
+
keyword_offset = unless_node->unless_keyword_loc.start;
|
|
53
57
|
break;
|
|
54
58
|
}
|
|
55
59
|
|
|
56
60
|
case PM_CASE_NODE: {
|
|
57
61
|
pm_case_node_t* case_node = (pm_case_node_t*) node;
|
|
58
62
|
current_type = CONTROL_TYPE_CASE;
|
|
59
|
-
keyword_offset =
|
|
63
|
+
keyword_offset = case_node->case_keyword_loc.start;
|
|
60
64
|
break;
|
|
61
65
|
}
|
|
62
66
|
|
|
63
67
|
case PM_CASE_MATCH_NODE: {
|
|
64
68
|
pm_case_match_node_t* case_match_node = (pm_case_match_node_t*) node;
|
|
65
69
|
current_type = CONTROL_TYPE_CASE_MATCH;
|
|
66
|
-
keyword_offset =
|
|
70
|
+
keyword_offset = case_match_node->case_keyword_loc.start;
|
|
67
71
|
break;
|
|
68
72
|
}
|
|
69
73
|
|
|
70
74
|
case PM_WHILE_NODE: {
|
|
71
75
|
pm_while_node_t* while_node = (pm_while_node_t*) node;
|
|
72
76
|
current_type = CONTROL_TYPE_WHILE;
|
|
73
|
-
keyword_offset =
|
|
77
|
+
keyword_offset = while_node->while_keyword_loc.start;
|
|
74
78
|
break;
|
|
75
79
|
}
|
|
76
80
|
|
|
77
81
|
case PM_UNTIL_NODE: {
|
|
78
82
|
pm_until_node_t* until_node = (pm_until_node_t*) node;
|
|
79
83
|
current_type = CONTROL_TYPE_UNTIL;
|
|
80
|
-
keyword_offset =
|
|
84
|
+
keyword_offset = until_node->until_keyword_loc.start;
|
|
81
85
|
break;
|
|
82
86
|
}
|
|
83
87
|
|
|
84
88
|
case PM_FOR_NODE: {
|
|
85
89
|
pm_for_node_t* for_node = (pm_for_node_t*) node;
|
|
86
90
|
current_type = CONTROL_TYPE_FOR;
|
|
87
|
-
keyword_offset =
|
|
91
|
+
keyword_offset = for_node->for_keyword_loc.start;
|
|
88
92
|
break;
|
|
89
93
|
}
|
|
90
94
|
|
|
@@ -92,17 +96,17 @@ static bool find_earliest_control_keyword_walker(const pm_node_t* node, void* da
|
|
|
92
96
|
pm_begin_node_t* begin_node = (pm_begin_node_t*) node;
|
|
93
97
|
current_type = CONTROL_TYPE_BEGIN;
|
|
94
98
|
|
|
95
|
-
if (begin_node->begin_keyword_loc
|
|
96
|
-
keyword_offset =
|
|
99
|
+
if (herb_prism_location_assigned(begin_node->begin_keyword_loc)) {
|
|
100
|
+
keyword_offset = begin_node->begin_keyword_loc.start;
|
|
97
101
|
} else {
|
|
98
|
-
keyword_offset =
|
|
102
|
+
keyword_offset = node->location.start;
|
|
99
103
|
}
|
|
100
104
|
break;
|
|
101
105
|
}
|
|
102
106
|
|
|
103
107
|
case PM_YIELD_NODE: {
|
|
104
108
|
current_type = CONTROL_TYPE_YIELD;
|
|
105
|
-
keyword_offset =
|
|
109
|
+
keyword_offset = node->location.start;
|
|
106
110
|
break;
|
|
107
111
|
}
|
|
108
112
|
|
|
@@ -112,12 +116,14 @@ static bool find_earliest_control_keyword_walker(const pm_node_t* node, void* da
|
|
|
112
116
|
if (call->block != NULL && call->block->type == PM_BLOCK_NODE) {
|
|
113
117
|
pm_block_node_t* block_node = (pm_block_node_t*) call->block;
|
|
114
118
|
|
|
115
|
-
bool has_opening = is_do_block(
|
|
116
|
-
|
|
119
|
+
bool has_opening = is_do_block(context->source_start, block_node->opening_loc)
|
|
120
|
+
|| is_brace_block(context->source_start, block_node->opening_loc);
|
|
121
|
+
bool is_unclosed =
|
|
122
|
+
!has_valid_block_closing(context->source_start, block_node->opening_loc, block_node->closing_loc);
|
|
117
123
|
|
|
118
124
|
if (has_opening && is_unclosed) {
|
|
119
125
|
current_type = CONTROL_TYPE_BLOCK;
|
|
120
|
-
keyword_offset =
|
|
126
|
+
keyword_offset = node->location.start;
|
|
121
127
|
}
|
|
122
128
|
}
|
|
123
129
|
break;
|
|
@@ -126,12 +132,13 @@ static bool find_earliest_control_keyword_walker(const pm_node_t* node, void* da
|
|
|
126
132
|
case PM_LAMBDA_NODE: {
|
|
127
133
|
pm_lambda_node_t* lambda = (pm_lambda_node_t*) node;
|
|
128
134
|
|
|
129
|
-
bool has_opening = is_do_block(
|
|
130
|
-
|
|
135
|
+
bool has_opening = is_do_block(context->source_start, lambda->opening_loc)
|
|
136
|
+
|| is_brace_block(context->source_start, lambda->opening_loc);
|
|
137
|
+
bool is_unclosed = !has_valid_block_closing(context->source_start, lambda->opening_loc, lambda->closing_loc);
|
|
131
138
|
|
|
132
139
|
if (has_opening && is_unclosed) {
|
|
133
140
|
current_type = CONTROL_TYPE_BLOCK;
|
|
134
|
-
keyword_offset =
|
|
141
|
+
keyword_offset = node->location.start;
|
|
135
142
|
}
|
|
136
143
|
|
|
137
144
|
break;
|
|
@@ -141,7 +148,7 @@ static bool find_earliest_control_keyword_walker(const pm_node_t* node, void* da
|
|
|
141
148
|
case PM_BREAK_NODE:
|
|
142
149
|
case PM_RETURN_NODE: {
|
|
143
150
|
current_type = CONTROL_TYPE_UNKNOWN;
|
|
144
|
-
keyword_offset =
|
|
151
|
+
keyword_offset = node->location.start;
|
|
145
152
|
break;
|
|
146
153
|
}
|
|
147
154
|
|
|
@@ -166,7 +173,7 @@ static bool find_earliest_control_keyword_walker(const pm_node_t* node, void* da
|
|
|
166
173
|
}
|
|
167
174
|
}
|
|
168
175
|
|
|
169
|
-
return
|
|
176
|
+
return PM_VISIT_DESCEND;
|
|
170
177
|
}
|
|
171
178
|
|
|
172
179
|
static control_type_t find_earliest_control_keyword(pm_node_t* root, const uint8_t* source_start) {
|
|
@@ -210,7 +217,7 @@ static control_type_t detect_analyzed_control_type(analyzed_ruby_T* ruby) {
|
|
|
210
217
|
|
|
211
218
|
if (ruby->unclosed_control_flow_count == 0 && !has_yield_node(ruby)) { return CONTROL_TYPE_UNKNOWN; }
|
|
212
219
|
|
|
213
|
-
return find_earliest_control_keyword(root, ruby->parser
|
|
220
|
+
return find_earliest_control_keyword(root, pm_parser_start(ruby->parser));
|
|
214
221
|
}
|
|
215
222
|
|
|
216
223
|
control_type_t detect_control_type(AST_ERB_CONTENT_NODE_T* erb_node) {
|
|
@@ -17,6 +17,7 @@
|
|
|
17
17
|
#include "../include/prism/prism_helpers.h"
|
|
18
18
|
|
|
19
19
|
#include <prism.h>
|
|
20
|
+
#include <prism/internal/diagnostic.h>
|
|
20
21
|
#include <stdbool.h>
|
|
21
22
|
#include <string.h>
|
|
22
23
|
|
|
@@ -152,14 +153,11 @@ hb_string_T herb_directive_kind_for_prism_node(const pm_node_t* node) {
|
|
|
152
153
|
}
|
|
153
154
|
|
|
154
155
|
typedef struct {
|
|
155
|
-
const uint8_t* synthetic_start;
|
|
156
156
|
size_t signature_start;
|
|
157
157
|
size_t prefix_length;
|
|
158
158
|
} synthetic_mapping_T;
|
|
159
159
|
|
|
160
|
-
static size_t synthetic_to_content_offset(const synthetic_mapping_T* mapping,
|
|
161
|
-
size_t offset = (size_t) (pointer - mapping->synthetic_start);
|
|
162
|
-
|
|
160
|
+
static size_t synthetic_to_content_offset(const synthetic_mapping_T* mapping, uint32_t offset) {
|
|
163
161
|
if (offset < mapping->prefix_length) { return mapping->signature_start; }
|
|
164
162
|
|
|
165
163
|
return mapping->signature_start + offset - mapping->prefix_length;
|
|
@@ -172,7 +170,7 @@ static AST_RUBY_LITERAL_NODE_T* create_default_value_node(
|
|
|
172
170
|
hb_allocator_T* allocator
|
|
173
171
|
) {
|
|
174
172
|
size_t start = synthetic_to_content_offset(mapping, value->location.start);
|
|
175
|
-
size_t end = synthetic_to_content_offset(mapping, value->location
|
|
173
|
+
size_t end = synthetic_to_content_offset(mapping, herb_prism_location_end(value->location));
|
|
176
174
|
|
|
177
175
|
char* source = hb_allocator_strndup(allocator, content->bytes + start, end - start);
|
|
178
176
|
|
|
@@ -212,12 +210,12 @@ static void append_state_declaration(
|
|
|
212
210
|
}
|
|
213
211
|
|
|
214
212
|
size_t name_start = synthetic_to_content_offset(mapping, name_location.start);
|
|
215
|
-
size_t name_end = synthetic_to_content_offset(mapping, name_location
|
|
213
|
+
size_t name_end = synthetic_to_content_offset(mapping, herb_prism_location_end(name_location));
|
|
216
214
|
|
|
217
215
|
if (name_end > name_start && content->bytes[name_end - 1] == ':') { name_end--; }
|
|
218
216
|
|
|
219
217
|
size_t declaration_start = synthetic_to_content_offset(mapping, keyword->location.start);
|
|
220
|
-
size_t declaration_end = synthetic_to_content_offset(mapping, keyword->location
|
|
218
|
+
size_t declaration_end = synthetic_to_content_offset(mapping, herb_prism_location_end(keyword->location));
|
|
221
219
|
|
|
222
220
|
if (!value) {
|
|
223
221
|
append_herb_state_invalid_parameter_error(
|
|
@@ -257,7 +255,7 @@ static void append_invalid_parameter_error(
|
|
|
257
255
|
if (!parameter) { return; }
|
|
258
256
|
|
|
259
257
|
size_t start = synthetic_to_content_offset(mapping, parameter->location.start);
|
|
260
|
-
size_t end = synthetic_to_content_offset(mapping, parameter->location
|
|
258
|
+
size_t end = synthetic_to_content_offset(mapping, herb_prism_location_end(parameter->location));
|
|
261
259
|
|
|
262
260
|
append_herb_state_invalid_parameter_error(
|
|
263
261
|
content_slice(content, start, end),
|
|
@@ -560,29 +558,28 @@ static AST_NODE_T* create_herb_state_directive_node(
|
|
|
560
558
|
hb_buffer_append_with_length(&synthetic, content->bytes + signature_start, signature_length);
|
|
561
559
|
hb_buffer_append(&synthetic, SYNTHETIC_SUFFIX);
|
|
562
560
|
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
566
|
-
pm_parser_init(&parser, (const uint8_t*) hb_buffer_value(&synthetic), hb_buffer_length(&synthetic), &prism_options);
|
|
561
|
+
pm_arena_t* arena = pm_arena_new();
|
|
562
|
+
pm_parser_t* parser =
|
|
563
|
+
herb_prism_parser_new(arena, (const uint8_t*) hb_buffer_value(&synthetic), hb_buffer_length(&synthetic), options);
|
|
567
564
|
|
|
568
|
-
pm_node_t* root = pm_parse(
|
|
565
|
+
pm_node_t* root = pm_parse(parser);
|
|
569
566
|
|
|
570
567
|
synthetic_mapping_T mapping = {
|
|
571
|
-
.synthetic_start = parser.start,
|
|
572
568
|
.signature_start = signature_start,
|
|
573
569
|
.prefix_length = strlen(SYNTHETIC_PREFIX),
|
|
574
570
|
};
|
|
575
571
|
|
|
576
572
|
bool parsed = true;
|
|
577
573
|
|
|
578
|
-
for (const pm_diagnostic_t* error = (
|
|
579
|
-
error = (
|
|
574
|
+
for (const pm_diagnostic_t* error = pm_parser_errors_first(parser); error != NULL;
|
|
575
|
+
error = pm_diagnostic_next(error)) {
|
|
580
576
|
if (error->diag_id == PM_ERR_DEF_TERM) { continue; }
|
|
581
577
|
|
|
582
578
|
parsed = false;
|
|
583
579
|
|
|
584
580
|
position_T error_start = content_position(content, synthetic_to_content_offset(&mapping, error->location.start));
|
|
585
|
-
position_T error_end =
|
|
581
|
+
position_T error_end =
|
|
582
|
+
content_position(content, synthetic_to_content_offset(&mapping, herb_prism_location_end(error->location)));
|
|
586
583
|
|
|
587
584
|
hb_array_append(errors, ruby_parse_error_from_prism_error_with_positions(error, error_start, error_end, allocator));
|
|
588
585
|
}
|
|
@@ -591,9 +588,8 @@ static AST_NODE_T* create_herb_state_directive_node(
|
|
|
591
588
|
parsed ? extract_state_declarations(find_parameters_node(root), content, &mapping, &errors, allocator, options)
|
|
592
589
|
: hb_array_init(0, allocator);
|
|
593
590
|
|
|
594
|
-
|
|
595
|
-
|
|
596
|
-
pm_options_free(&prism_options);
|
|
591
|
+
pm_parser_free(parser);
|
|
592
|
+
pm_arena_free(arena);
|
|
597
593
|
hb_buffer_free(&synthetic);
|
|
598
594
|
|
|
599
595
|
return (AST_NODE_T*) ast_herb_state_directive_node_init(
|
|
@@ -6,6 +6,7 @@
|
|
|
6
6
|
#include "../include/lib/hb_allocator.h"
|
|
7
7
|
#include "../include/lib/hb_array.h"
|
|
8
8
|
#include "../include/lib/hb_string.h"
|
|
9
|
+
#include "../include/prism/prism_helpers.h"
|
|
9
10
|
#include "../include/visitor.h"
|
|
10
11
|
|
|
11
12
|
#include <prism.h>
|
|
@@ -20,14 +21,13 @@ static token_T* create_token_from_prism_location(
|
|
|
20
21
|
const uint8_t* erb_content_source,
|
|
21
22
|
hb_allocator_T* allocator
|
|
22
23
|
) {
|
|
23
|
-
if (location
|
|
24
|
+
if (!herb_prism_location_assigned(location)) { return NULL; }
|
|
24
25
|
if (!source || !erb_content_source) { return NULL; }
|
|
25
26
|
|
|
26
|
-
|
|
27
|
-
char* value = hb_allocator_strndup(allocator, (const char*) location.start, length);
|
|
27
|
+
char* value = hb_allocator_strndup(allocator, (const char*) (erb_content_source + location.start), location.length);
|
|
28
28
|
|
|
29
|
-
size_t total_start = erb_content_offset +
|
|
30
|
-
size_t total_end = erb_content_offset + (
|
|
29
|
+
size_t total_start = erb_content_offset + location.start;
|
|
30
|
+
size_t total_end = erb_content_offset + herb_prism_location_end(location);
|
|
31
31
|
|
|
32
32
|
position_T start = byte_offset_to_position(source, total_start);
|
|
33
33
|
position_T end = byte_offset_to_position(source, total_end);
|
|
@@ -59,15 +59,18 @@ static hb_array_T* extract_call_arguments(
|
|
|
59
59
|
const pm_node_t* argument = call->arguments->arguments.nodes[index];
|
|
60
60
|
if (!argument) { continue; }
|
|
61
61
|
|
|
62
|
-
|
|
63
|
-
|
|
62
|
+
char* value = hb_allocator_strndup(
|
|
63
|
+
allocator,
|
|
64
|
+
(const char*) (erb_content_source + argument->location.start),
|
|
65
|
+
argument->location.length
|
|
66
|
+
);
|
|
64
67
|
|
|
65
68
|
position_T start = { .line = 1, .column = 1 };
|
|
66
69
|
position_T end = { .line = 1, .column = 1 };
|
|
67
70
|
|
|
68
71
|
if (source && erb_content_source) {
|
|
69
|
-
size_t total_start = erb_content_offset +
|
|
70
|
-
size_t total_end = erb_content_offset + (
|
|
72
|
+
size_t total_start = erb_content_offset + argument->location.start;
|
|
73
|
+
size_t total_end = erb_content_offset + herb_prism_location_end(argument->location);
|
|
71
74
|
|
|
72
75
|
start = byte_offset_to_position(source, total_start);
|
|
73
76
|
end = byte_offset_to_position(source, total_end);
|
|
@@ -106,30 +109,72 @@ static const char* ITERATION_METHODS[] = {
|
|
|
106
109
|
"cycle",
|
|
107
110
|
};
|
|
108
111
|
|
|
109
|
-
static
|
|
110
|
-
|
|
112
|
+
static const char* ARGUMENTLESS_ITERATION_METHODS[] = {
|
|
113
|
+
"times", "each_pair", "map", "flat_map", "select", "filter", "reject", "filter_map",
|
|
114
|
+
};
|
|
111
115
|
|
|
116
|
+
static const char* TAG_BUILDER_ELEMENTS[] = {
|
|
117
|
+
"map",
|
|
118
|
+
"select",
|
|
119
|
+
"filter",
|
|
120
|
+
};
|
|
121
|
+
|
|
122
|
+
static bool constant_matches_any(const pm_constant_t* constant, const char** names, size_t count) {
|
|
112
123
|
for (size_t index = 0; index < count; index++) {
|
|
113
|
-
const char* name =
|
|
124
|
+
const char* name = names[index];
|
|
114
125
|
size_t length = strlen(name);
|
|
115
126
|
|
|
116
|
-
if (constant
|
|
127
|
+
if (pm_constant_length(constant) == length && memcmp(pm_constant_start(constant), name, length) == 0) {
|
|
128
|
+
return true;
|
|
129
|
+
}
|
|
117
130
|
}
|
|
118
131
|
|
|
119
132
|
return false;
|
|
120
133
|
}
|
|
121
134
|
|
|
135
|
+
static bool is_iteration_method(const pm_constant_t* constant) {
|
|
136
|
+
return constant_matches_any(constant, ITERATION_METHODS, sizeof(ITERATION_METHODS) / sizeof(ITERATION_METHODS[0]));
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
static bool rejects_call_arguments(const pm_constant_t* constant) {
|
|
140
|
+
return constant_matches_any(
|
|
141
|
+
constant,
|
|
142
|
+
ARGUMENTLESS_ITERATION_METHODS,
|
|
143
|
+
sizeof(ARGUMENTLESS_ITERATION_METHODS) / sizeof(ARGUMENTLESS_ITERATION_METHODS[0])
|
|
144
|
+
);
|
|
145
|
+
}
|
|
146
|
+
|
|
147
|
+
static bool is_tag_builder_element(const pm_constant_t* constant) {
|
|
148
|
+
return constant_matches_any(
|
|
149
|
+
constant,
|
|
150
|
+
TAG_BUILDER_ELEMENTS,
|
|
151
|
+
sizeof(TAG_BUILDER_ELEMENTS) / sizeof(TAG_BUILDER_ELEMENTS[0])
|
|
152
|
+
);
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
static bool has_tag_builder_receiver(const pm_call_node_t* call, const pm_parser_t* parser) {
|
|
156
|
+
if (call->receiver->type != PM_CALL_NODE) { return false; }
|
|
157
|
+
|
|
158
|
+
const pm_call_node_t* receiver = (const pm_call_node_t*) call->receiver;
|
|
159
|
+
const pm_constant_t* constant = pm_parser_constant(parser, receiver->name);
|
|
160
|
+
|
|
161
|
+
return constant && pm_constant_length(constant) == 3 && memcmp(pm_constant_start(constant), "tag", 3) == 0;
|
|
162
|
+
}
|
|
163
|
+
|
|
122
164
|
static bool is_iteration_call(const pm_call_node_t* call, const pm_parser_t* parser) {
|
|
123
165
|
if (!call) { return false; }
|
|
124
166
|
if (call->receiver == NULL) { return false; }
|
|
125
167
|
if (call->block == NULL || call->block->type != PM_BLOCK_NODE) { return false; }
|
|
126
168
|
|
|
127
169
|
pm_constant_id_t name_id = call->name;
|
|
128
|
-
const pm_constant_t* constant =
|
|
170
|
+
const pm_constant_t* constant = pm_parser_constant(parser, name_id);
|
|
129
171
|
|
|
130
172
|
if (!constant) { return false; }
|
|
173
|
+
if (!is_iteration_method(constant)) { return false; }
|
|
174
|
+
if (call->arguments != NULL && rejects_call_arguments(constant)) { return false; }
|
|
175
|
+
if (is_tag_builder_element(constant) && has_tag_builder_receiver(call, parser)) { return false; }
|
|
131
176
|
|
|
132
|
-
return
|
|
177
|
+
return true;
|
|
133
178
|
}
|
|
134
179
|
|
|
135
180
|
static pm_call_node_t* find_iteration_call(pm_node_t* node, const pm_parser_t* parser) {
|
|
@@ -173,15 +218,15 @@ static AST_ERB_ITERATION_BLOCK_NODE_T* try_transform_block_node(
|
|
|
173
218
|
const char* ruby_source = block_node->content->value.data;
|
|
174
219
|
size_t ruby_length = block_node->content->value.length;
|
|
175
220
|
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
pm_node_t* root = pm_parse(
|
|
221
|
+
pm_arena_t* arena = pm_arena_new();
|
|
222
|
+
pm_parser_t* parser = herb_prism_parser_new(arena, (const uint8_t*) ruby_source, ruby_length, context->options);
|
|
223
|
+
pm_node_t* root = pm_parse(parser);
|
|
179
224
|
|
|
180
|
-
pm_call_node_t* iteration_call = find_iteration_call(root,
|
|
225
|
+
pm_call_node_t* iteration_call = find_iteration_call(root, parser);
|
|
181
226
|
|
|
182
227
|
if (!iteration_call) {
|
|
183
|
-
|
|
184
|
-
|
|
228
|
+
pm_parser_free(parser);
|
|
229
|
+
pm_arena_free(arena);
|
|
185
230
|
|
|
186
231
|
return NULL;
|
|
187
232
|
}
|
|
@@ -192,7 +237,7 @@ static AST_ERB_ITERATION_BLOCK_NODE_T* try_transform_block_node(
|
|
|
192
237
|
erb_content_offset = calculate_byte_offset_from_position(context->source, block_node->content->location.start);
|
|
193
238
|
}
|
|
194
239
|
|
|
195
|
-
const uint8_t* erb_content_source = (
|
|
240
|
+
const uint8_t* erb_content_source = pm_parser_start(parser);
|
|
196
241
|
|
|
197
242
|
token_T* receiver = create_token_from_prism_location(
|
|
198
243
|
iteration_call->receiver->location,
|
|
@@ -260,8 +305,8 @@ static AST_ERB_ITERATION_BLOCK_NODE_T* try_transform_block_node(
|
|
|
260
305
|
allocator
|
|
261
306
|
);
|
|
262
307
|
|
|
263
|
-
|
|
264
|
-
|
|
308
|
+
pm_parser_free(parser);
|
|
309
|
+
pm_arena_free(arena);
|
|
265
310
|
|
|
266
311
|
return iteration_block_node;
|
|
267
312
|
}
|
data/src/analyze/parse_errors.c
CHANGED
|
@@ -9,6 +9,7 @@
|
|
|
9
9
|
#include "../include/prism/prism_helpers.h"
|
|
10
10
|
|
|
11
11
|
#include <prism.h>
|
|
12
|
+
#include <prism/internal/diagnostic.h>
|
|
12
13
|
#include <stdlib.h>
|
|
13
14
|
#include <string.h>
|
|
14
15
|
|
|
@@ -43,7 +44,12 @@ static bool should_skip_forwarding_error(
|
|
|
43
44
|
return has_anonymous_keyword_rest;
|
|
44
45
|
}
|
|
45
46
|
|
|
46
|
-
static void parse_erb_content_errors(
|
|
47
|
+
static void parse_erb_content_errors(
|
|
48
|
+
AST_NODE_T* erb_node,
|
|
49
|
+
const char* source,
|
|
50
|
+
const parser_options_T* parser_options,
|
|
51
|
+
hb_allocator_T* allocator
|
|
52
|
+
) {
|
|
47
53
|
if (!erb_node || erb_node->type != AST_ERB_CONTENT_NODE) { return; }
|
|
48
54
|
AST_ERB_CONTENT_NODE_T* content_node = (AST_ERB_CONTENT_NODE_T*) erb_node;
|
|
49
55
|
|
|
@@ -52,13 +58,15 @@ static void parse_erb_content_errors(AST_NODE_T* erb_node, const char* source, h
|
|
|
52
58
|
char* content = hb_string_to_c_string_using_malloc(content_node->content->value);
|
|
53
59
|
if (!content) { return; }
|
|
54
60
|
|
|
55
|
-
|
|
56
|
-
pm_options_t options =
|
|
57
|
-
|
|
61
|
+
pm_arena_t* arena = pm_arena_new();
|
|
62
|
+
pm_options_t* options = pm_options_new();
|
|
63
|
+
pm_options_partial_script_set(options, true);
|
|
64
|
+
herb_prism_options_set_ruby_version(options, parser_options);
|
|
65
|
+
pm_parser_t* parser = pm_parser_new(arena, (const uint8_t*) content, strlen(content), options);
|
|
58
66
|
|
|
59
|
-
|
|
67
|
+
pm_parse(parser);
|
|
60
68
|
|
|
61
|
-
const pm_diagnostic_t* error = (
|
|
69
|
+
const pm_diagnostic_t* error = pm_parser_errors_first(parser);
|
|
62
70
|
|
|
63
71
|
if (error != NULL) {
|
|
64
72
|
RUBY_PARSE_ERROR_T* parse_error = ruby_parse_error_from_prism_error_with_positions(
|
|
@@ -71,9 +79,9 @@ static void parse_erb_content_errors(AST_NODE_T* erb_node, const char* source, h
|
|
|
71
79
|
hb_array_append_lazy(&erb_node->errors, parse_error, allocator);
|
|
72
80
|
}
|
|
73
81
|
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
pm_options_free(
|
|
82
|
+
pm_parser_free(parser);
|
|
83
|
+
pm_arena_free(arena);
|
|
84
|
+
pm_options_free(options);
|
|
77
85
|
free(content);
|
|
78
86
|
}
|
|
79
87
|
|
|
@@ -95,24 +103,26 @@ void herb_analyze_parse_errors(
|
|
|
95
103
|
bool strict_locals_enabled = parser_options && parser_options->strict_locals;
|
|
96
104
|
bool has_anonymous_keyword_rest = strict_locals_enabled && document_has_anonymous_keyword_rest(document);
|
|
97
105
|
|
|
98
|
-
|
|
99
|
-
pm_options_t options =
|
|
100
|
-
|
|
106
|
+
pm_arena_t* arena = pm_arena_new();
|
|
107
|
+
pm_options_t* options = pm_options_new();
|
|
108
|
+
pm_options_partial_script_set(options, true);
|
|
109
|
+
herb_prism_options_set_ruby_version(options, parser_options);
|
|
110
|
+
pm_parser_t* parser = pm_parser_new(arena, (const uint8_t*) extracted_ruby, strlen(extracted_ruby), options);
|
|
101
111
|
|
|
102
|
-
|
|
112
|
+
pm_parse(parser);
|
|
103
113
|
|
|
104
|
-
for (const pm_diagnostic_t* error = (
|
|
105
|
-
error = (
|
|
114
|
+
for (const pm_diagnostic_t* error = pm_parser_errors_first(parser); error != NULL;
|
|
115
|
+
error = pm_diagnostic_next(error)) {
|
|
106
116
|
if (should_skip_forwarding_error(error, strict_locals_enabled, has_anonymous_keyword_rest)) { continue; }
|
|
107
117
|
|
|
108
|
-
size_t error_offset =
|
|
118
|
+
size_t error_offset = error->location.start;
|
|
109
119
|
|
|
110
|
-
if (strstr(error
|
|
120
|
+
if (strstr(pm_diagnostic_message(error), "unexpected ';'") != NULL) {
|
|
111
121
|
if (error_offset < strlen(extracted_ruby) && extracted_ruby[error_offset] == ';') {
|
|
112
122
|
if (error_offset >= strlen(source) || source[error_offset] != ';') {
|
|
113
123
|
AST_NODE_T* erb_node = find_erb_content_at_offset(document, source, error_offset);
|
|
114
124
|
|
|
115
|
-
if (erb_node) { parse_erb_content_errors(erb_node, source, allocator); }
|
|
125
|
+
if (erb_node) { parse_erb_content_errors(erb_node, source, parser_options, allocator); }
|
|
116
126
|
|
|
117
127
|
continue;
|
|
118
128
|
}
|
|
@@ -120,12 +130,12 @@ void herb_analyze_parse_errors(
|
|
|
120
130
|
}
|
|
121
131
|
|
|
122
132
|
RUBY_PARSE_ERROR_T* parse_error =
|
|
123
|
-
ruby_parse_error_from_prism_error(error, (AST_NODE_T*) document, source,
|
|
133
|
+
ruby_parse_error_from_prism_error(error, (AST_NODE_T*) document, source, parser, allocator);
|
|
124
134
|
hb_array_append_lazy(&document->base.errors, parse_error, allocator);
|
|
125
135
|
}
|
|
126
136
|
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
pm_options_free(
|
|
137
|
+
pm_parser_free(parser);
|
|
138
|
+
pm_arena_free(arena);
|
|
139
|
+
pm_options_free(options);
|
|
130
140
|
hb_allocator_dealloc(allocator, extracted_ruby);
|
|
131
141
|
}
|