Ruby 4.1.0dev (2026-11-13 revision 1d214cd7786e916cd5b198eb58436a5e10b45cc3)
prism_compile.h (1d214cd7786e916cd5b198eb58436a5e10b45cc3)
1#include "prism/prism.h"
2#include "ruby/encoding.h"
3
12typedef struct pm_local_index_struct {
13 int index, level;
15
16// A declaration for the struct that lives in compile.c.
17struct iseq_link_anchor;
19
29typedef struct {
31 int *values;
32
35
37 bool owned;
39
41#define PM_INDEX_LOOKUP_SPECIALS 4
42
44#define PM_SPECIAL_CONSTANT_FLAG ((pm_constant_id_t) (1 << 31))
45#define PM_INDEX_LOOKUP_SPECIAL_MULT 0
46#define PM_INDEX_LOOKUP_SPECIAL_POW 1
47#define PM_INDEX_LOOKUP_SPECIAL_AND 2
48#define PM_INDEX_LOOKUP_SPECIAL_DOT3 3
49
55#define PM_CONSTANT_MULT ((pm_constant_id_t) (PM_SPECIAL_CONSTANT_FLAG | PM_INDEX_LOOKUP_SPECIAL_MULT))
56#define PM_CONSTANT_POW ((pm_constant_id_t) (PM_SPECIAL_CONSTANT_FLAG | PM_INDEX_LOOKUP_SPECIAL_POW))
57#define PM_CONSTANT_AND ((pm_constant_id_t) (PM_SPECIAL_CONSTANT_FLAG | PM_INDEX_LOOKUP_SPECIAL_AND))
58#define PM_CONSTANT_DOT3 ((pm_constant_id_t) (PM_SPECIAL_CONSTANT_FLAG | PM_INDEX_LOOKUP_SPECIAL_DOT3))
59
60static inline int
61pm_index_lookup_table_index(const pm_index_lookup_table_t *table, pm_constant_id_t key)
62{
63 if (LIKELY(!(key & PM_SPECIAL_CONSTANT_FLAG))) {
64 return (int) pm_constant_id_index(key);
65 }
66 return table->capacity - PM_INDEX_LOOKUP_SPECIALS + (int)(key & ~PM_SPECIAL_CONSTANT_FLAG);
67}
68
69static inline void
70pm_index_lookup_table_insert(pm_index_lookup_table_t *table, pm_constant_id_t key, int value)
71{
72 int idx = pm_index_lookup_table_index(table, key);
73 RUBY_ASSERT(idx >= 0 && idx < table->capacity);
74 table->values[idx] = value;
75}
76
77static inline int
78pm_index_lookup_table_lookup(const pm_index_lookup_table_t *table, pm_constant_id_t key, int *value)
79{
80 int idx = pm_index_lookup_table_index(table, key);
81 RUBY_ASSERT(idx >= 0 && idx < table->capacity);
82 if (table->values[idx] == -1) return 0;
83 *value = table->values[idx];
84 return 1;
85}
86
87static inline void
88pm_index_lookup_table_init_heap(pm_index_lookup_table_t *table, int constants_size)
89{
90 int cap = constants_size + PM_INDEX_LOOKUP_SPECIALS;
91 table->values = (int *) ruby_xmalloc(cap * sizeof(int));
92 memset(table->values, -1, cap * sizeof(int));
93 table->capacity = cap;
94 table->owned = true;
95}
96
97// ScopeNodes are helper nodes, and will never be part of the AST. We manually
98// declare them here to avoid generating them.
99typedef struct pm_scope_node {
100 pm_node_t base;
101 struct pm_scope_node *previous;
102 pm_node_t *ast_node;
103 pm_node_t *parameters;
104 pm_node_t *body;
106
107 const pm_parser_t *parser;
108
110 uint64_t source_hash;
111 const pm_options_t *options;
112 const pm_line_offset_list_t *line_offsets;
113 int32_t start_line;
114 rb_encoding *encoding;
115
125
132
133 // The size of the local table on the iseq which includes locals and hidden
134 // variables.
135 int local_table_for_iseq_size;
136
137 ID *constants;
138
146
147 // The current coverage setting, passed down through the various scopes.
148 int coverage_enabled;
149
155
161 size_t last_line;
163
164void pm_scope_node_init(const pm_node_t *node, pm_scope_node_t *scope, pm_scope_node_t *previous);
165void pm_scope_node_destroy(pm_scope_node_t *scope_node);
166
186
187void pm_parse_result_init(pm_parse_result_t *result);
188VALUE pm_load_file(pm_parse_result_t *result, VALUE filepath, bool load_error);
189VALUE pm_parse_file(pm_parse_result_t *result, VALUE filepath, VALUE *script_lines);
190VALUE pm_load_parse_file(pm_parse_result_t *result, VALUE filepath, VALUE *script_lines);
191VALUE pm_parse_string(pm_parse_result_t *result, VALUE source, VALUE filepath, VALUE *script_lines);
192VALUE pm_parse_stdin(pm_parse_result_t *result);
193void pm_options_version_for_current_ruby_set(pm_options_t *options);
194void pm_parse_result_free(pm_parse_result_t *result);
195bool pm_source_hash_matches(VALUE source, VALUE filepath, uint64_t source_hash);
196bool pm_node_source_location(VALUE source, VALUE filepath, int start_line,
197 int node_id, uint64_t source_hash,
198 struct rb_code_location_struct *location);
199
200rb_iseq_t *pm_iseq_new(pm_scope_node_t *node, VALUE name, VALUE path, VALUE realpath, const rb_iseq_t *parent, enum rb_iseq_type, int *error_state);
201rb_iseq_t *pm_iseq_new_top(pm_scope_node_t *node, VALUE name, VALUE path, VALUE realpath, const rb_iseq_t *parent, int *error_state);
202rb_iseq_t *pm_iseq_new_main(pm_scope_node_t *node, VALUE path, VALUE realpath, const rb_iseq_t *parent, int opt, int *error_state);
203rb_iseq_t *pm_iseq_new_eval(pm_scope_node_t *node, VALUE name, VALUE path, VALUE realpath, int first_lineno, const rb_iseq_t *parent, int isolated_depth, int *error_state);
204rb_iseq_t *pm_iseq_new_with_opt(pm_scope_node_t *node, VALUE name, VALUE path, VALUE realpath, int first_lineno, const rb_iseq_t *parent, int isolated_depth, enum rb_iseq_type, const rb_compile_option_t *option, int *error_state);
205rb_iseq_t *pm_iseq_build(pm_scope_node_t *node, VALUE name, VALUE path, VALUE realpath, int first_lineno, const rb_iseq_t *parent, int isolated_depth, enum rb_iseq_type, const rb_compile_option_t *option);
206
207VALUE pm_iseq_compile_node(rb_iseq_t *iseq, pm_scope_node_t *node);
uint32_t pm_constant_id_t
A constant id is a unique identifier for a constant in the constant pool.
static PRISM_INLINE size_t pm_constant_id_index(pm_constant_id_t constant_id)
Returns the index of the constant with the given id among the constants of the parser that produced i...
#define RUBY_ASSERT(...)
Asserts that the given expression is truthy if and only if RUBY_DEBUG is truthy.
Definition assert.h:219
Encoding relates APIs.
The main header file for the prism parser.
A list of constant IDs.
A direct-indexed lookup table mapping constant IDs to local variable indices.
int capacity
Total number of slots (constants_size + PM_INDEX_LOOKUP_SPECIALS).
bool owned
Whether the values array is heap-allocated and needs explicit free.
int * values
Array of local indices, indexed by pm_index_lookup_table_index.
A list of offsets of the start of lines in a string.
the getlocal and setlocal instructions require two parameters.
This is the base structure that represents a node in the syntax tree.
Definition ast.h:1090
bool parsed
Whether or not this parse result has performed its parsing yet.
pm_parser_t * parser
The parser that will do the actual parsing.
pm_source_t * source
The source backing the parse (file, string, or stream).
pm_scope_node_t node
The resulting scope node that will hold the generated AST.
pm_options_t * options
The options that will be passed to the parser.
pm_arena_t * arena
The arena allocator for AST-lifetime memory.
uint64_t source_hash
The source hash of the parsed source, propagated to every iseq.
rb_encoding * filepath_encoding
This is the encoding of the actual filepath object that will be used when a FILE node is compiled or ...
pm_index_lookup_table_t index_lookup_table
A flat lookup table mapping constant IDs (or special IDs) to local variable indices.
size_t last_line
Cached line hint for line offset list lookups.
struct iseq_link_anchor * pre_execution_anchor
This will only be set on the top-level scope node.
VALUE * script_lines
This is a pointer to the list of script lines for the ISEQs that will be associated with this scope n...
uintptr_t ID
Type that represents a Ruby identifier such as a variable name.
Definition value.h:52
uintptr_t VALUE
Type that represents a Ruby object.
Definition value.h:40