Prism Ruby parser
Loading...
Searching...
No Matches
Prism Ruby parser

Prism is a parser for the Ruby programming language. It is designed to be portable, error tolerant, and maintainable. It is written in C99 and has no dependencies. It is currently being integrated into CRuby, JRuby, TruffleRuby, Sorbet, and Syntax Tree.

Getting started

If you're vendoring this project and compiling it statically then as long as you have a C99 compiler you will be fine. If you're linking against it as shared library, then you should compile with -fvisibility=hidden and -DPRISM_EXPORT_SYMBOLS to tell prism to make only its public interface visible.

Parsing

In order to parse Ruby code, the functions that you are going to want to use and be aware of are:

Putting all of this together would look something like:

void parse(const uint8_t *source, size_t length) {
pm_parser_t *parser = pm_parser_new(arena, source, length, NULL);
pm_node_t *root = pm_parse(parser);
printf("PARSED!\n");
pm_parser_free(parser);
pm_arena_free(arena);
}
struct pm_arena_t pm_arena_t
An opaque pointer to an arena that is used for allocations.
Definition arena.h:18
PRISM_EXPORTED_FUNCTION PRISM_NODISCARD pm_arena_t * pm_arena_new(void)
Returns a newly allocated and initialized arena.
PRISM_EXPORTED_FUNCTION void pm_arena_free(pm_arena_t *arena) PRISM_NONNULL(1)
Frees both the held memory and the arena itself.
struct pm_parser_t pm_parser_t
The parser used to parse Ruby source.
Definition parser.h:22
PRISM_EXPORTED_FUNCTION PRISM_NODISCARD pm_parser_t * pm_parser_new(pm_arena_t *arena, const uint8_t *source, size_t size, const pm_options_t *options) PRISM_NONNULL(1)
Allocate and initialize a parser with the given start and end pointers.
PRISM_EXPORTED_FUNCTION void pm_parser_free(pm_parser_t *parser) PRISM_NONNULL(1)
Free both the memory held by the given parser and the parser itself.
PRISM_EXPORTED_FUNCTION pm_node_t * pm_parse(pm_parser_t *parser) PRISM_NONNULL(1)
Initiate the parser with the given parser.
This is the base structure that represents a node in the syntax tree.
Definition ast.h:1070

All of the nodes "inherit" from pm_node_t by embedding those structures as their first member. This means you can downcast and upcast any node in the tree to a pm_node_t.

Serializing

Prism provides the ability to serialize the AST and its related metadata into a binary format. This format is designed to be portable to different languages and runtimes so that you only need to make one FFI call in order to parse Ruby code. The functions that you are going to want to use and be aware of are:

Putting all of this together would look something like:

void serialize(const uint8_t *source, size_t length) {
pm_serialize_parse(buffer, source, length, NULL);
printf("SERIALIZED!\n");
pm_buffer_free(buffer);
}
struct pm_buffer_t pm_buffer_t
A wrapper around a contiguous block of allocated memory.
Definition buffer.h:18
PRISM_EXPORTED_FUNCTION PRISM_NODISCARD pm_buffer_t * pm_buffer_new(void)
Allocate and initialize a new buffer.
PRISM_EXPORTED_FUNCTION void pm_buffer_free(pm_buffer_t *buffer) PRISM_NONNULL(1)
Free both the memory held by the buffer and the buffer itself.
PRISM_EXPORTED_FUNCTION void PRISM_EXPORTED_FUNCTION void pm_serialize_parse(pm_buffer_t *buffer, const uint8_t *source, size_t size, const char *data) PRISM_NONNULL(1
Parse the given source to the AST and dump the AST to the given buffer.

Inspecting

Prism provides the ability to inspect the AST by pretty-printing nodes. You can do this with the pm_prettyprint() function, which you would use like:

void prettyprint(const uint8_t *source, size_t length) {
pm_parser_t *parser = pm_parser_new(arena, source, length, NULL);
pm_node_t *root = pm_parse(parser);
pm_prettyprint(buffer, parser, root);
printf("%*.s\n", (int) pm_buffer_length(buffer), pm_buffer_value(buffer));
pm_buffer_free(buffer);
pm_parser_free(parser);
pm_arena_free(arena);
}
PRISM_EXPORTED_FUNCTION size_t pm_buffer_length(const pm_buffer_t *buffer) PRISM_NONNULL(1)
Return the length of the buffer.
PRISM_EXPORTED_FUNCTION char * pm_buffer_value(const pm_buffer_t *buffer) PRISM_NONNULL(1)
Return the value of the buffer.
PRISM_EXPORTED_FUNCTION void pm_prettyprint(pm_buffer_t *output_buffer, const pm_parser_t *parser, const pm_node_t *node) PRISM_NONNULL(1
Pretty-prints the AST represented by the given node to the given buffer.