prism 0.15.1 → 0.17.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +35 -1
- data/Makefile +12 -0
- data/README.md +3 -1
- data/config.yml +66 -50
- data/docs/configuration.md +2 -0
- data/docs/fuzzing.md +1 -1
- data/docs/javascript.md +90 -0
- data/docs/releasing.md +27 -0
- data/docs/ruby_api.md +2 -0
- data/docs/serialization.md +28 -29
- data/ext/prism/api_node.c +856 -826
- data/ext/prism/api_pack.c +20 -9
- data/ext/prism/extension.c +494 -119
- data/ext/prism/extension.h +1 -1
- data/include/prism/ast.h +3157 -747
- data/include/prism/defines.h +40 -8
- data/include/prism/diagnostic.h +36 -3
- data/include/prism/enc/pm_encoding.h +119 -28
- data/include/prism/node.h +38 -30
- data/include/prism/options.h +204 -0
- data/include/prism/pack.h +44 -33
- data/include/prism/parser.h +445 -199
- data/include/prism/prettyprint.h +26 -0
- data/include/prism/regexp.h +16 -2
- data/include/prism/util/pm_buffer.h +102 -18
- data/include/prism/util/pm_char.h +162 -48
- data/include/prism/util/pm_constant_pool.h +128 -34
- data/include/prism/util/pm_list.h +68 -38
- data/include/prism/util/pm_memchr.h +18 -3
- data/include/prism/util/pm_newline_list.h +71 -28
- data/include/prism/util/pm_state_stack.h +25 -7
- data/include/prism/util/pm_string.h +115 -27
- data/include/prism/util/pm_string_list.h +25 -6
- data/include/prism/util/pm_strncasecmp.h +32 -0
- data/include/prism/util/pm_strpbrk.h +31 -17
- data/include/prism/version.h +28 -3
- data/include/prism.h +229 -36
- data/lib/prism/compiler.rb +5 -5
- data/lib/prism/debug.rb +43 -13
- data/lib/prism/desugar_compiler.rb +1 -1
- data/lib/prism/dispatcher.rb +27 -26
- data/lib/prism/dsl.rb +16 -16
- data/lib/prism/ffi.rb +138 -61
- data/lib/prism/lex_compat.rb +26 -16
- data/lib/prism/mutation_compiler.rb +11 -11
- data/lib/prism/node.rb +426 -227
- data/lib/prism/node_ext.rb +23 -16
- data/lib/prism/node_inspector.rb +1 -1
- data/lib/prism/pack.rb +79 -40
- data/lib/prism/parse_result/comments.rb +7 -2
- data/lib/prism/parse_result/newlines.rb +4 -0
- data/lib/prism/parse_result.rb +157 -21
- data/lib/prism/pattern.rb +14 -3
- data/lib/prism/ripper_compat.rb +28 -10
- data/lib/prism/serialize.rb +935 -307
- data/lib/prism/visitor.rb +9 -5
- data/lib/prism.rb +20 -2
- data/prism.gemspec +11 -2
- data/rbi/prism.rbi +7305 -0
- data/rbi/prism_static.rbi +196 -0
- data/sig/prism.rbs +4468 -0
- data/sig/prism_static.rbs +123 -0
- data/src/diagnostic.c +56 -53
- data/src/enc/pm_big5.c +1 -0
- data/src/enc/pm_euc_jp.c +1 -0
- data/src/enc/pm_gbk.c +1 -0
- data/src/enc/pm_shift_jis.c +1 -0
- data/src/enc/pm_tables.c +316 -80
- data/src/enc/pm_unicode.c +54 -9
- data/src/enc/pm_windows_31j.c +1 -0
- data/src/node.c +357 -345
- data/src/options.c +170 -0
- data/src/prettyprint.c +7697 -1643
- data/src/prism.c +1964 -1125
- data/src/regexp.c +153 -95
- data/src/serialize.c +432 -397
- data/src/token_type.c +3 -1
- data/src/util/pm_buffer.c +88 -23
- data/src/util/pm_char.c +103 -57
- data/src/util/pm_constant_pool.c +52 -22
- data/src/util/pm_list.c +12 -4
- data/src/util/pm_memchr.c +5 -3
- data/src/util/pm_newline_list.c +25 -63
- data/src/util/pm_state_stack.c +9 -3
- data/src/util/pm_string.c +95 -85
- data/src/util/pm_string_list.c +14 -15
- data/src/util/pm_strncasecmp.c +10 -3
- data/src/util/pm_strpbrk.c +25 -19
- metadata +12 -3
- data/docs/prism.png +0 -0
    
        data/src/token_type.c
    CHANGED
    
    | @@ -9,7 +9,9 @@ | |
| 9 9 |  | 
| 10 10 | 
             
            #include "prism/ast.h"
         | 
| 11 11 |  | 
| 12 | 
            -
             | 
| 12 | 
            +
            /**
         | 
| 13 | 
            +
             * Returns a string representation of the given token type.
         | 
| 14 | 
            +
             */
         | 
| 13 15 | 
             
            PRISM_EXPORTED_FUNCTION const char *
         | 
| 14 16 | 
             
            pm_token_type_to_str(pm_token_type_t token_type)
         | 
| 15 17 | 
             
            {
         | 
    
        data/src/util/pm_buffer.c
    CHANGED
    
    | @@ -1,12 +1,16 @@ | |
| 1 1 | 
             
            #include "prism/util/pm_buffer.h"
         | 
| 2 2 |  | 
| 3 | 
            -
             | 
| 3 | 
            +
            /**
         | 
| 4 | 
            +
             * Return the size of the pm_buffer_t struct.
         | 
| 5 | 
            +
             */
         | 
| 4 6 | 
             
            size_t
         | 
| 5 7 | 
             
            pm_buffer_sizeof(void) {
         | 
| 6 8 | 
             
                return sizeof(pm_buffer_t);
         | 
| 7 9 | 
             
            }
         | 
| 8 10 |  | 
| 9 | 
            -
             | 
| 11 | 
            +
            /**
         | 
| 12 | 
            +
             * Initialize a pm_buffer_t with the given capacity.
         | 
| 13 | 
            +
             */
         | 
| 10 14 | 
             
            bool
         | 
| 11 15 | 
             
            pm_buffer_init_capacity(pm_buffer_t *buffer, size_t capacity) {
         | 
| 12 16 | 
             
                buffer->length = 0;
         | 
| @@ -16,33 +20,45 @@ pm_buffer_init_capacity(pm_buffer_t *buffer, size_t capacity) { | |
| 16 20 | 
             
                return buffer->value != NULL;
         | 
| 17 21 | 
             
            }
         | 
| 18 22 |  | 
| 19 | 
            -
             | 
| 23 | 
            +
            /**
         | 
| 24 | 
            +
             * Initialize a pm_buffer_t with its default values.
         | 
| 25 | 
            +
             */
         | 
| 20 26 | 
             
            bool
         | 
| 21 27 | 
             
            pm_buffer_init(pm_buffer_t *buffer) {
         | 
| 22 28 | 
             
                return pm_buffer_init_capacity(buffer, 1024);
         | 
| 23 29 | 
             
            }
         | 
| 24 30 |  | 
| 25 | 
            -
             | 
| 31 | 
            +
            /**
         | 
| 32 | 
            +
             * Return the value of the buffer.
         | 
| 33 | 
            +
             */
         | 
| 26 34 | 
             
            char *
         | 
| 27 35 | 
             
            pm_buffer_value(pm_buffer_t *buffer) {
         | 
| 28 36 | 
             
                return buffer->value;
         | 
| 29 37 | 
             
            }
         | 
| 30 38 |  | 
| 31 | 
            -
             | 
| 39 | 
            +
            /**
         | 
| 40 | 
            +
             * Return the length of the buffer.
         | 
| 41 | 
            +
             */
         | 
| 32 42 | 
             
            size_t
         | 
| 33 43 | 
             
            pm_buffer_length(pm_buffer_t *buffer) {
         | 
| 34 44 | 
             
                return buffer->length;
         | 
| 35 45 | 
             
            }
         | 
| 36 46 |  | 
| 37 | 
            -
             | 
| 47 | 
            +
            /**
         | 
| 48 | 
            +
             * Append the given amount of space to the buffer.
         | 
| 49 | 
            +
             */
         | 
| 38 50 | 
             
            static inline void
         | 
| 39 51 | 
             
            pm_buffer_append_length(pm_buffer_t *buffer, size_t length) {
         | 
| 40 52 | 
             
                size_t next_length = buffer->length + length;
         | 
| 41 53 |  | 
| 42 54 | 
             
                if (next_length > buffer->capacity) {
         | 
| 43 | 
            -
                     | 
| 55 | 
            +
                    if (buffer->capacity == 0) {
         | 
| 56 | 
            +
                        buffer->capacity = 1;
         | 
| 57 | 
            +
                    }
         | 
| 58 | 
            +
             | 
| 59 | 
            +
                    while (next_length > buffer->capacity) {
         | 
| 44 60 | 
             
                        buffer->capacity *= 2;
         | 
| 45 | 
            -
                    } | 
| 61 | 
            +
                    }
         | 
| 46 62 |  | 
| 47 63 | 
             
                    buffer->value = realloc(buffer->value, buffer->capacity);
         | 
| 48 64 | 
             
                }
         | 
| @@ -50,55 +66,104 @@ pm_buffer_append_length(pm_buffer_t *buffer, size_t length) { | |
| 50 66 | 
             
                buffer->length = next_length;
         | 
| 51 67 | 
             
            }
         | 
| 52 68 |  | 
| 53 | 
            -
             | 
| 69 | 
            +
            /**
         | 
| 70 | 
            +
             * Append a generic pointer to memory to the buffer.
         | 
| 71 | 
            +
             */
         | 
| 54 72 | 
             
            static inline void
         | 
| 55 73 | 
             
            pm_buffer_append(pm_buffer_t *buffer, const void *source, size_t length) {
         | 
| 74 | 
            +
                size_t cursor = buffer->length;
         | 
| 56 75 | 
             
                pm_buffer_append_length(buffer, length);
         | 
| 57 | 
            -
                memcpy(buffer->value +  | 
| 76 | 
            +
                memcpy(buffer->value + cursor, source, length);
         | 
| 58 77 | 
             
            }
         | 
| 59 78 |  | 
| 60 | 
            -
             | 
| 79 | 
            +
            /**
         | 
| 80 | 
            +
             * Append the given amount of space as zeroes to the buffer.
         | 
| 81 | 
            +
             */
         | 
| 61 82 | 
             
            void
         | 
| 62 83 | 
             
            pm_buffer_append_zeroes(pm_buffer_t *buffer, size_t length) {
         | 
| 84 | 
            +
                size_t cursor = buffer->length;
         | 
| 63 85 | 
             
                pm_buffer_append_length(buffer, length);
         | 
| 64 | 
            -
                memset(buffer->value +  | 
| 86 | 
            +
                memset(buffer->value + cursor, 0, length);
         | 
| 65 87 | 
             
            }
         | 
| 66 88 |  | 
| 67 | 
            -
             | 
| 89 | 
            +
            /**
         | 
| 90 | 
            +
             * Append a formatted string to the buffer.
         | 
| 91 | 
            +
             */
         | 
| 68 92 | 
             
            void
         | 
| 69 | 
            -
             | 
| 93 | 
            +
            pm_buffer_append_format(pm_buffer_t *buffer, const char *format, ...) {
         | 
| 94 | 
            +
                va_list arguments;
         | 
| 95 | 
            +
                va_start(arguments, format);
         | 
| 96 | 
            +
                int result = vsnprintf(NULL, 0, format, arguments);
         | 
| 97 | 
            +
                va_end(arguments);
         | 
| 98 | 
            +
             | 
| 99 | 
            +
                if (result < 0) return;
         | 
| 100 | 
            +
                size_t length = (size_t) (result + 1);
         | 
| 101 | 
            +
             | 
| 102 | 
            +
                size_t cursor = buffer->length;
         | 
| 103 | 
            +
                pm_buffer_append_length(buffer, length);
         | 
| 104 | 
            +
             | 
| 105 | 
            +
                va_start(arguments, format);
         | 
| 106 | 
            +
                vsnprintf(buffer->value + cursor, length, format, arguments);
         | 
| 107 | 
            +
                va_end(arguments);
         | 
| 108 | 
            +
             | 
| 109 | 
            +
                buffer->length--;
         | 
| 110 | 
            +
            }
         | 
| 111 | 
            +
             | 
| 112 | 
            +
            /**
         | 
| 113 | 
            +
             * Append a string to the buffer.
         | 
| 114 | 
            +
             */
         | 
| 115 | 
            +
            void
         | 
| 116 | 
            +
            pm_buffer_append_string(pm_buffer_t *buffer, const char *value, size_t length) {
         | 
| 70 117 | 
             
                pm_buffer_append(buffer, value, length);
         | 
| 71 118 | 
             
            }
         | 
| 72 119 |  | 
| 73 | 
            -
             | 
| 120 | 
            +
            /**
         | 
| 121 | 
            +
             * Append a list of bytes to the buffer.
         | 
| 122 | 
            +
             */
         | 
| 74 123 | 
             
            void
         | 
| 75 124 | 
             
            pm_buffer_append_bytes(pm_buffer_t *buffer, const uint8_t *value, size_t length) {
         | 
| 76 125 | 
             
                pm_buffer_append(buffer, (const char *) value, length);
         | 
| 77 126 | 
             
            }
         | 
| 78 127 |  | 
| 79 | 
            -
             | 
| 128 | 
            +
            /**
         | 
| 129 | 
            +
             * Append a single byte to the buffer.
         | 
| 130 | 
            +
             */
         | 
| 80 131 | 
             
            void
         | 
| 81 | 
            -
             | 
| 132 | 
            +
            pm_buffer_append_byte(pm_buffer_t *buffer, uint8_t value) {
         | 
| 82 133 | 
             
                const void *source = &value;
         | 
| 83 134 | 
             
                pm_buffer_append(buffer, source, sizeof(uint8_t));
         | 
| 84 135 | 
             
            }
         | 
| 85 136 |  | 
| 86 | 
            -
             | 
| 137 | 
            +
            /**
         | 
| 138 | 
            +
             * Append a 32-bit unsigned integer to the buffer as a variable-length integer.
         | 
| 139 | 
            +
             */
         | 
| 87 140 | 
             
            void
         | 
| 88 | 
            -
             | 
| 141 | 
            +
            pm_buffer_append_varint(pm_buffer_t *buffer, uint32_t value) {
         | 
| 89 142 | 
             
                if (value < 128) {
         | 
| 90 | 
            -
                     | 
| 143 | 
            +
                    pm_buffer_append_byte(buffer, (uint8_t) value);
         | 
| 91 144 | 
             
                } else {
         | 
| 92 145 | 
             
                    uint32_t n = value;
         | 
| 93 146 | 
             
                    while (n >= 128) {
         | 
| 94 | 
            -
                         | 
| 147 | 
            +
                        pm_buffer_append_byte(buffer, (uint8_t) (n | 128));
         | 
| 95 148 | 
             
                        n >>= 7;
         | 
| 96 149 | 
             
                    }
         | 
| 97 | 
            -
                     | 
| 150 | 
            +
                    pm_buffer_append_byte(buffer, (uint8_t) n);
         | 
| 151 | 
            +
                }
         | 
| 152 | 
            +
            }
         | 
| 153 | 
            +
             | 
| 154 | 
            +
            /**
         | 
| 155 | 
            +
             * Concatenate one buffer onto another.
         | 
| 156 | 
            +
             */
         | 
| 157 | 
            +
            void
         | 
| 158 | 
            +
            pm_buffer_concat(pm_buffer_t *destination, const pm_buffer_t *source) {
         | 
| 159 | 
            +
                if (source->length > 0) {
         | 
| 160 | 
            +
                    pm_buffer_append(destination, source->value, source->length);
         | 
| 98 161 | 
             
                }
         | 
| 99 162 | 
             
            }
         | 
| 100 163 |  | 
| 101 | 
            -
             | 
| 164 | 
            +
            /**
         | 
| 165 | 
            +
             * Free the memory associated with the buffer.
         | 
| 166 | 
            +
             */
         | 
| 102 167 | 
             
            void
         | 
| 103 168 | 
             
            pm_buffer_free(pm_buffer_t *buffer) {
         | 
| 104 169 | 
             
                free(buffer->value);
         | 
    
        data/src/util/pm_char.c
    CHANGED
    
    | @@ -53,6 +53,10 @@ static const uint8_t pm_number_table[256] = { | |
| 53 53 | 
             
                0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // Fx
         | 
| 54 54 | 
             
            };
         | 
| 55 55 |  | 
| 56 | 
            +
            /**
         | 
| 57 | 
            +
             * Returns the number of characters at the start of the string that match the
         | 
| 58 | 
            +
             * given kind. Disallows searching past the given maximum number of characters.
         | 
| 59 | 
            +
             */
         | 
| 56 60 | 
             
            static inline size_t
         | 
| 57 61 | 
             
            pm_strspn_char_kind(const uint8_t *string, ptrdiff_t length, uint8_t kind) {
         | 
| 58 62 | 
             
                if (length <= 0) return 0;
         | 
| @@ -64,16 +68,20 @@ pm_strspn_char_kind(const uint8_t *string, ptrdiff_t length, uint8_t kind) { | |
| 64 68 | 
             
                return size;
         | 
| 65 69 | 
             
            }
         | 
| 66 70 |  | 
| 67 | 
            -
             | 
| 68 | 
            -
             | 
| 71 | 
            +
            /**
         | 
| 72 | 
            +
             * Returns the number of characters at the start of the string that are
         | 
| 73 | 
            +
             * whitespace. Disallows searching past the given maximum number of characters.
         | 
| 74 | 
            +
             */
         | 
| 69 75 | 
             
            size_t
         | 
| 70 76 | 
             
            pm_strspn_whitespace(const uint8_t *string, ptrdiff_t length) {
         | 
| 71 77 | 
             
                return pm_strspn_char_kind(string, length, PRISM_CHAR_BIT_WHITESPACE);
         | 
| 72 78 | 
             
            }
         | 
| 73 79 |  | 
| 74 | 
            -
             | 
| 75 | 
            -
             | 
| 76 | 
            -
             | 
| 80 | 
            +
            /**
         | 
| 81 | 
            +
             * Returns the number of characters at the start of the string that are
         | 
| 82 | 
            +
             * whitespace while also tracking the location of each newline. Disallows
         | 
| 83 | 
            +
             * searching past the given maximum number of characters.
         | 
| 84 | 
            +
             */
         | 
| 77 85 | 
             
            size_t
         | 
| 78 86 | 
             
            pm_strspn_whitespace_newlines(const uint8_t *string, ptrdiff_t length, pm_newline_list_t *newline_list) {
         | 
| 79 87 | 
             
                if (length <= 0) return 0;
         | 
| @@ -92,40 +100,53 @@ pm_strspn_whitespace_newlines(const uint8_t *string, ptrdiff_t length, pm_newlin | |
| 92 100 | 
             
                return size;
         | 
| 93 101 | 
             
            }
         | 
| 94 102 |  | 
| 95 | 
            -
             | 
| 96 | 
            -
             | 
| 103 | 
            +
            /**
         | 
| 104 | 
            +
             * Returns the number of characters at the start of the string that are inline
         | 
| 105 | 
            +
             * whitespace. Disallows searching past the given maximum number of characters.
         | 
| 106 | 
            +
             */
         | 
| 97 107 | 
             
            size_t
         | 
| 98 108 | 
             
            pm_strspn_inline_whitespace(const uint8_t *string, ptrdiff_t length) {
         | 
| 99 109 | 
             
                return pm_strspn_char_kind(string, length, PRISM_CHAR_BIT_INLINE_WHITESPACE);
         | 
| 100 110 | 
             
            }
         | 
| 101 111 |  | 
| 102 | 
            -
             | 
| 103 | 
            -
             | 
| 112 | 
            +
            /**
         | 
| 113 | 
            +
             * Returns the number of characters at the start of the string that are regexp
         | 
| 114 | 
            +
             * options. Disallows searching past the given maximum number of characters.
         | 
| 115 | 
            +
             */
         | 
| 104 116 | 
             
            size_t
         | 
| 105 117 | 
             
            pm_strspn_regexp_option(const uint8_t *string, ptrdiff_t length) {
         | 
| 106 118 | 
             
                return pm_strspn_char_kind(string, length, PRISM_CHAR_BIT_REGEXP_OPTION);
         | 
| 107 119 | 
             
            }
         | 
| 108 120 |  | 
| 121 | 
            +
            /**
         | 
| 122 | 
            +
             * Returns true if the given character matches the given kind.
         | 
| 123 | 
            +
             */
         | 
| 109 124 | 
             
            static inline bool
         | 
| 110 125 | 
             
            pm_char_is_char_kind(const uint8_t b, uint8_t kind) {
         | 
| 111 126 | 
             
                return (pm_byte_table[b] & kind) != 0;
         | 
| 112 127 | 
             
            }
         | 
| 113 128 |  | 
| 114 | 
            -
             | 
| 129 | 
            +
            /**
         | 
| 130 | 
            +
             * Returns true if the given character is a whitespace character.
         | 
| 131 | 
            +
             */
         | 
| 115 132 | 
             
            bool
         | 
| 116 133 | 
             
            pm_char_is_whitespace(const uint8_t b) {
         | 
| 117 134 | 
             
                return pm_char_is_char_kind(b, PRISM_CHAR_BIT_WHITESPACE);
         | 
| 118 135 | 
             
            }
         | 
| 119 136 |  | 
| 120 | 
            -
             | 
| 137 | 
            +
            /**
         | 
| 138 | 
            +
             * Returns true if the given character is an inline whitespace character.
         | 
| 139 | 
            +
             */
         | 
| 121 140 | 
             
            bool
         | 
| 122 141 | 
             
            pm_char_is_inline_whitespace(const uint8_t b) {
         | 
| 123 142 | 
             
                return pm_char_is_char_kind(b, PRISM_CHAR_BIT_INLINE_WHITESPACE);
         | 
| 124 143 | 
             
            }
         | 
| 125 144 |  | 
| 126 | 
            -
             | 
| 127 | 
            -
             | 
| 128 | 
            -
             | 
| 145 | 
            +
            /**
         | 
| 146 | 
            +
             * Scan through the string and return the number of characters at the start of
         | 
| 147 | 
            +
             * the string that match the given kind. Disallows searching past the given
         | 
| 148 | 
            +
             * maximum number of characters.
         | 
| 149 | 
            +
             */
         | 
| 129 150 | 
             
            static inline size_t
         | 
| 130 151 | 
             
            pm_strspn_number_kind(const uint8_t *string, ptrdiff_t length, uint8_t kind) {
         | 
| 131 152 | 
             
                if (length <= 0) return 0;
         | 
| @@ -137,12 +158,14 @@ pm_strspn_number_kind(const uint8_t *string, ptrdiff_t length, uint8_t kind) { | |
| 137 158 | 
             
                return size;
         | 
| 138 159 | 
             
            }
         | 
| 139 160 |  | 
| 140 | 
            -
             | 
| 141 | 
            -
             | 
| 142 | 
            -
             | 
| 143 | 
            -
             | 
| 144 | 
            -
             | 
| 145 | 
            -
             | 
| 161 | 
            +
            /**
         | 
| 162 | 
            +
             * Scan through the string and return the number of characters at the start of
         | 
| 163 | 
            +
             * the string that match the given kind. Disallows searching past the given
         | 
| 164 | 
            +
             * maximum number of characters.
         | 
| 165 | 
            +
             *
         | 
| 166 | 
            +
             * Additionally, report the location of the last invalid underscore character
         | 
| 167 | 
            +
             * found in the string through the out invalid parameter.
         | 
| 168 | 
            +
             */
         | 
| 146 169 | 
             
            static inline size_t
         | 
| 147 170 | 
             
            pm_strspn_number_kind_underscores(const uint8_t *string, ptrdiff_t length, const uint8_t **invalid, uint8_t kind) {
         | 
| 148 171 | 
             
                if (length <= 0) return 0;
         | 
| @@ -166,93 +189,116 @@ pm_strspn_number_kind_underscores(const uint8_t *string, ptrdiff_t length, const | |
| 166 189 | 
             
                return size;
         | 
| 167 190 | 
             
            }
         | 
| 168 191 |  | 
| 169 | 
            -
             | 
| 170 | 
            -
             | 
| 171 | 
            -
             | 
| 172 | 
            -
             | 
| 173 | 
            -
             | 
| 174 | 
            -
             | 
| 175 | 
            -
             | 
| 192 | 
            +
            /**
         | 
| 193 | 
            +
             * Returns the number of characters at the start of the string that are binary
         | 
| 194 | 
            +
             * digits or underscores. Disallows searching past the given maximum number of
         | 
| 195 | 
            +
             * characters.
         | 
| 196 | 
            +
             *
         | 
| 197 | 
            +
             * If multiple underscores are found in a row or if an underscore is
         | 
| 198 | 
            +
             * found at the end of the number, then the invalid pointer is set to the index
         | 
| 199 | 
            +
             * of the first invalid underscore.
         | 
| 200 | 
            +
             */
         | 
| 176 201 | 
             
            size_t
         | 
| 177 202 | 
             
            pm_strspn_binary_number(const uint8_t *string, ptrdiff_t length, const uint8_t **invalid) {
         | 
| 178 203 | 
             
                return pm_strspn_number_kind_underscores(string, length, invalid, PRISM_NUMBER_BIT_BINARY_NUMBER);
         | 
| 179 204 | 
             
            }
         | 
| 180 205 |  | 
| 181 | 
            -
             | 
| 182 | 
            -
             | 
| 183 | 
            -
             | 
| 184 | 
            -
             | 
| 185 | 
            -
             | 
| 186 | 
            -
             | 
| 187 | 
            -
             | 
| 206 | 
            +
            /**
         | 
| 207 | 
            +
             * Returns the number of characters at the start of the string that are octal
         | 
| 208 | 
            +
             * digits or underscores. Disallows searching past the given maximum number of
         | 
| 209 | 
            +
             * characters.
         | 
| 210 | 
            +
             *
         | 
| 211 | 
            +
             * If multiple underscores are found in a row or if an underscore is
         | 
| 212 | 
            +
             * found at the end of the number, then the invalid pointer is set to the index
         | 
| 213 | 
            +
             * of the first invalid underscore.
         | 
| 214 | 
            +
             */
         | 
| 188 215 | 
             
            size_t
         | 
| 189 216 | 
             
            pm_strspn_octal_number(const uint8_t *string, ptrdiff_t length, const uint8_t **invalid) {
         | 
| 190 217 | 
             
                return pm_strspn_number_kind_underscores(string, length, invalid, PRISM_NUMBER_BIT_OCTAL_NUMBER);
         | 
| 191 218 | 
             
            }
         | 
| 192 219 |  | 
| 193 | 
            -
             | 
| 194 | 
            -
             | 
| 220 | 
            +
            /**
         | 
| 221 | 
            +
             * Returns the number of characters at the start of the string that are decimal
         | 
| 222 | 
            +
             * digits. Disallows searching past the given maximum number of characters.
         | 
| 223 | 
            +
             */
         | 
| 195 224 | 
             
            size_t
         | 
| 196 225 | 
             
            pm_strspn_decimal_digit(const uint8_t *string, ptrdiff_t length) {
         | 
| 197 226 | 
             
                return pm_strspn_number_kind(string, length, PRISM_NUMBER_BIT_DECIMAL_DIGIT);
         | 
| 198 227 | 
             
            }
         | 
| 199 228 |  | 
| 200 | 
            -
             | 
| 201 | 
            -
             | 
| 202 | 
            -
             | 
| 203 | 
            -
             | 
| 204 | 
            -
             | 
| 205 | 
            -
             | 
| 206 | 
            -
             | 
| 229 | 
            +
            /**
         | 
| 230 | 
            +
             * Returns the number of characters at the start of the string that are decimal
         | 
| 231 | 
            +
             * digits or underscores. Disallows searching past the given maximum number of
         | 
| 232 | 
            +
             * characters.
         | 
| 233 | 
            +
             *
         | 
| 234 | 
            +
             * If multiple underscores are found in a row or if an underscore is
         | 
| 235 | 
            +
             * found at the end of the number, then the invalid pointer is set to the index
         | 
| 236 | 
            +
             * of the first invalid underscore
         | 
| 237 | 
            +
             */
         | 
| 207 238 | 
             
            size_t
         | 
| 208 239 | 
             
            pm_strspn_decimal_number(const uint8_t *string, ptrdiff_t length, const uint8_t **invalid) {
         | 
| 209 240 | 
             
                return pm_strspn_number_kind_underscores(string, length, invalid, PRISM_NUMBER_BIT_DECIMAL_NUMBER);
         | 
| 210 241 | 
             
            }
         | 
| 211 242 |  | 
| 212 | 
            -
             | 
| 213 | 
            -
             | 
| 214 | 
            -
             | 
| 243 | 
            +
            /**
         | 
| 244 | 
            +
             * Returns the number of characters at the start of the string that are
         | 
| 245 | 
            +
             * hexadecimal digits. Disallows searching past the given maximum number of
         | 
| 246 | 
            +
             * characters.
         | 
| 247 | 
            +
             */
         | 
| 215 248 | 
             
            size_t
         | 
| 216 249 | 
             
            pm_strspn_hexadecimal_digit(const uint8_t *string, ptrdiff_t length) {
         | 
| 217 250 | 
             
                return pm_strspn_number_kind(string, length, PRISM_NUMBER_BIT_HEXADECIMAL_DIGIT);
         | 
| 218 251 | 
             
            }
         | 
| 219 252 |  | 
| 220 | 
            -
             | 
| 221 | 
            -
             | 
| 222 | 
            -
             | 
| 223 | 
            -
             | 
| 224 | 
            -
             | 
| 225 | 
            -
             | 
| 226 | 
            -
             | 
| 253 | 
            +
            /**
         | 
| 254 | 
            +
             * Returns the number of characters at the start of the string that are
         | 
| 255 | 
            +
             * hexadecimal digits or underscores. Disallows searching past the given maximum
         | 
| 256 | 
            +
             * number of characters.
         | 
| 257 | 
            +
             *
         | 
| 258 | 
            +
             * If multiple underscores are found in a row or if an underscore is
         | 
| 259 | 
            +
             * found at the end of the number, then the invalid pointer is set to the index
         | 
| 260 | 
            +
             * of the first invalid underscore.
         | 
| 261 | 
            +
             */
         | 
| 227 262 | 
             
            size_t
         | 
| 228 263 | 
             
            pm_strspn_hexadecimal_number(const uint8_t *string, ptrdiff_t length, const uint8_t **invalid) {
         | 
| 229 264 | 
             
                return pm_strspn_number_kind_underscores(string, length, invalid, PRISM_NUMBER_BIT_HEXADECIMAL_NUMBER);
         | 
| 230 265 | 
             
            }
         | 
| 231 266 |  | 
| 267 | 
            +
            /**
         | 
| 268 | 
            +
             * Returns true if the given character matches the given kind.
         | 
| 269 | 
            +
             */
         | 
| 232 270 | 
             
            static inline bool
         | 
| 233 271 | 
             
            pm_char_is_number_kind(const uint8_t b, uint8_t kind) {
         | 
| 234 272 | 
             
                return (pm_number_table[b] & kind) != 0;
         | 
| 235 273 | 
             
            }
         | 
| 236 274 |  | 
| 237 | 
            -
             | 
| 275 | 
            +
            /**
         | 
| 276 | 
            +
             * Returns true if the given character is a binary digit.
         | 
| 277 | 
            +
             */
         | 
| 238 278 | 
             
            bool
         | 
| 239 279 | 
             
            pm_char_is_binary_digit(const uint8_t b) {
         | 
| 240 280 | 
             
                return pm_char_is_number_kind(b, PRISM_NUMBER_BIT_BINARY_DIGIT);
         | 
| 241 281 | 
             
            }
         | 
| 242 282 |  | 
| 243 | 
            -
             | 
| 283 | 
            +
            /**
         | 
| 284 | 
            +
             * Returns true if the given character is an octal digit.
         | 
| 285 | 
            +
             */
         | 
| 244 286 | 
             
            bool
         | 
| 245 287 | 
             
            pm_char_is_octal_digit(const uint8_t b) {
         | 
| 246 288 | 
             
                return pm_char_is_number_kind(b, PRISM_NUMBER_BIT_OCTAL_DIGIT);
         | 
| 247 289 | 
             
            }
         | 
| 248 290 |  | 
| 249 | 
            -
             | 
| 291 | 
            +
            /**
         | 
| 292 | 
            +
             * Returns true if the given character is a decimal digit.
         | 
| 293 | 
            +
             */
         | 
| 250 294 | 
             
            bool
         | 
| 251 295 | 
             
            pm_char_is_decimal_digit(const uint8_t b) {
         | 
| 252 296 | 
             
                return pm_char_is_number_kind(b, PRISM_NUMBER_BIT_DECIMAL_DIGIT);
         | 
| 253 297 | 
             
            }
         | 
| 254 298 |  | 
| 255 | 
            -
             | 
| 299 | 
            +
            /**
         | 
| 300 | 
            +
             * Returns true if the given character is a hexadecimal digit.
         | 
| 301 | 
            +
             */
         | 
| 256 302 | 
             
            bool
         | 
| 257 303 | 
             
            pm_char_is_hexadecimal_digit(const uint8_t b) {
         | 
| 258 304 | 
             
                return pm_char_is_number_kind(b, PRISM_NUMBER_BIT_HEXADECIMAL_DIGIT);
         | 
    
        data/src/util/pm_constant_pool.c
    CHANGED
    
    | @@ -1,6 +1,8 @@ | |
| 1 1 | 
             
            #include "prism/util/pm_constant_pool.h"
         | 
| 2 2 |  | 
| 3 | 
            -
             | 
| 3 | 
            +
            /**
         | 
| 4 | 
            +
             * Initialize a list of constant ids.
         | 
| 5 | 
            +
             */
         | 
| 4 6 | 
             
            void
         | 
| 5 7 | 
             
            pm_constant_id_list_init(pm_constant_id_list_t *list) {
         | 
| 6 8 | 
             
                list->ids = NULL;
         | 
| @@ -8,8 +10,10 @@ pm_constant_id_list_init(pm_constant_id_list_t *list) { | |
| 8 10 | 
             
                list->capacity = 0;
         | 
| 9 11 | 
             
            }
         | 
| 10 12 |  | 
| 11 | 
            -
             | 
| 12 | 
            -
             | 
| 13 | 
            +
            /**
         | 
| 14 | 
            +
             * Append a constant id to a list of constant ids. Returns false if any
         | 
| 15 | 
            +
             * potential reallocations fail.
         | 
| 16 | 
            +
             */
         | 
| 13 17 | 
             
            bool
         | 
| 14 18 | 
             
            pm_constant_id_list_append(pm_constant_id_list_t *list, pm_constant_id_t id) {
         | 
| 15 19 | 
             
                if (list->size >= list->capacity) {
         | 
| @@ -22,7 +26,9 @@ pm_constant_id_list_append(pm_constant_id_list_t *list, pm_constant_id_t id) { | |
| 22 26 | 
             
                return true;
         | 
| 23 27 | 
             
            }
         | 
| 24 28 |  | 
| 25 | 
            -
             | 
| 29 | 
            +
            /**
         | 
| 30 | 
            +
             * Checks if the current constant id list includes the given constant id.
         | 
| 31 | 
            +
             */
         | 
| 26 32 | 
             
            bool
         | 
| 27 33 | 
             
            pm_constant_id_list_includes(pm_constant_id_list_t *list, pm_constant_id_t id) {
         | 
| 28 34 | 
             
                for (size_t index = 0; index < list->size; index++) {
         | 
| @@ -31,13 +37,17 @@ pm_constant_id_list_includes(pm_constant_id_list_t *list, pm_constant_id_t id) { | |
| 31 37 | 
             
                return false;
         | 
| 32 38 | 
             
            }
         | 
| 33 39 |  | 
| 34 | 
            -
             | 
| 40 | 
            +
            /**
         | 
| 41 | 
            +
             * Get the memory size of a list of constant ids.
         | 
| 42 | 
            +
             */
         | 
| 35 43 | 
             
            size_t
         | 
| 36 44 | 
             
            pm_constant_id_list_memsize(pm_constant_id_list_t *list) {
         | 
| 37 45 | 
             
                return sizeof(pm_constant_id_list_t) + (list->capacity * sizeof(pm_constant_id_t));
         | 
| 38 46 | 
             
            }
         | 
| 39 47 |  | 
| 40 | 
            -
             | 
| 48 | 
            +
            /**
         | 
| 49 | 
            +
             * Free the memory associated with a list of constant ids.
         | 
| 50 | 
            +
             */
         | 
| 41 51 | 
             
            void
         | 
| 42 52 | 
             
            pm_constant_id_list_free(pm_constant_id_list_t *list) {
         | 
| 43 53 | 
             
                if (list->ids != NULL) {
         | 
| @@ -45,8 +55,10 @@ pm_constant_id_list_free(pm_constant_id_list_t *list) { | |
| 45 55 | 
             
                }
         | 
| 46 56 | 
             
            }
         | 
| 47 57 |  | 
| 48 | 
            -
             | 
| 49 | 
            -
             | 
| 58 | 
            +
            /**
         | 
| 59 | 
            +
             * A relatively simple hash function (djb2) that is used to hash strings. We are
         | 
| 60 | 
            +
             * optimizing here for simplicity and speed.
         | 
| 61 | 
            +
             */
         | 
| 50 62 | 
             
            static inline uint32_t
         | 
| 51 63 | 
             
            pm_constant_pool_hash(const uint8_t *start, size_t length) {
         | 
| 52 64 | 
             
                // This is a prime number used as the initial value for the hash function.
         | 
| @@ -59,7 +71,9 @@ pm_constant_pool_hash(const uint8_t *start, size_t length) { | |
| 59 71 | 
             
                return value;
         | 
| 60 72 | 
             
            }
         | 
| 61 73 |  | 
| 62 | 
            -
             | 
| 74 | 
            +
            /**
         | 
| 75 | 
            +
             * https://graphics.stanford.edu/~seander/bithacks.html#RoundUpPowerOf2
         | 
| 76 | 
            +
             */
         | 
| 63 77 | 
             
            static uint32_t
         | 
| 64 78 | 
             
            next_power_of_two(uint32_t v) {
         | 
| 65 79 | 
             
                // Avoid underflow in subtraction on next line.
         | 
| @@ -84,7 +98,9 @@ is_power_of_two(uint32_t size) { | |
| 84 98 | 
             
            }
         | 
| 85 99 | 
             
            #endif
         | 
| 86 100 |  | 
| 87 | 
            -
             | 
| 101 | 
            +
            /**
         | 
| 102 | 
            +
             * Resize a constant pool to a given capacity.
         | 
| 103 | 
            +
             */
         | 
| 88 104 | 
             
            static inline bool
         | 
| 89 105 | 
             
            pm_constant_pool_resize(pm_constant_pool_t *pool) {
         | 
| 90 106 | 
             
                assert(is_power_of_two(pool->capacity));
         | 
| @@ -136,7 +152,9 @@ pm_constant_pool_resize(pm_constant_pool_t *pool) { | |
| 136 152 | 
             
                return true;
         | 
| 137 153 | 
             
            }
         | 
| 138 154 |  | 
| 139 | 
            -
             | 
| 155 | 
            +
            /**
         | 
| 156 | 
            +
             * Initialize a new constant pool with a given capacity.
         | 
| 157 | 
            +
             */
         | 
| 140 158 | 
             
            bool
         | 
| 141 159 | 
             
            pm_constant_pool_init(pm_constant_pool_t *pool, uint32_t capacity) {
         | 
| 142 160 | 
             
                const uint32_t maximum = (~((uint32_t) 0));
         | 
| @@ -154,14 +172,18 @@ pm_constant_pool_init(pm_constant_pool_t *pool, uint32_t capacity) { | |
| 154 172 | 
             
                return true;
         | 
| 155 173 | 
             
            }
         | 
| 156 174 |  | 
| 157 | 
            -
             | 
| 175 | 
            +
            /**
         | 
| 176 | 
            +
             * Return a pointer to the constant indicated by the given constant id.
         | 
| 177 | 
            +
             */
         | 
| 158 178 | 
             
            pm_constant_t *
         | 
| 159 | 
            -
            pm_constant_pool_id_to_constant(pm_constant_pool_t *pool, pm_constant_id_t constant_id) {
         | 
| 179 | 
            +
            pm_constant_pool_id_to_constant(const pm_constant_pool_t *pool, pm_constant_id_t constant_id) {
         | 
| 160 180 | 
             
                assert(constant_id > 0 && constant_id <= pool->size);
         | 
| 161 181 | 
             
                return &pool->constants[constant_id - 1];
         | 
| 162 182 | 
             
            }
         | 
| 163 183 |  | 
| 164 | 
            -
             | 
| 184 | 
            +
            /**
         | 
| 185 | 
            +
             * Insert a constant into a constant pool and return its index in the pool.
         | 
| 186 | 
            +
             */
         | 
| 165 187 | 
             
            static inline pm_constant_id_t
         | 
| 166 188 | 
             
            pm_constant_pool_insert(pm_constant_pool_t *pool, const uint8_t *start, size_t length, pm_constant_pool_bucket_type_t type) {
         | 
| 167 189 | 
             
                if (pool->size >= (pool->capacity / 4 * 3)) {
         | 
| @@ -225,29 +247,37 @@ pm_constant_pool_insert(pm_constant_pool_t *pool, const uint8_t *start, size_t l | |
| 225 247 | 
             
                return id;
         | 
| 226 248 | 
             
            }
         | 
| 227 249 |  | 
| 228 | 
            -
             | 
| 229 | 
            -
             | 
| 250 | 
            +
            /**
         | 
| 251 | 
            +
             * Insert a constant into a constant pool. Returns the id of the constant, or 0
         | 
| 252 | 
            +
             * if any potential calls to resize fail.
         | 
| 253 | 
            +
             */
         | 
| 230 254 | 
             
            pm_constant_id_t
         | 
| 231 255 | 
             
            pm_constant_pool_insert_shared(pm_constant_pool_t *pool, const uint8_t *start, size_t length) {
         | 
| 232 256 | 
             
                return pm_constant_pool_insert(pool, start, length, PM_CONSTANT_POOL_BUCKET_DEFAULT);
         | 
| 233 257 | 
             
            }
         | 
| 234 258 |  | 
| 235 | 
            -
             | 
| 236 | 
            -
             | 
| 237 | 
            -
             | 
| 259 | 
            +
            /**
         | 
| 260 | 
            +
             * Insert a constant into a constant pool from memory that is now owned by the
         | 
| 261 | 
            +
             * constant pool. Returns the id of the constant, or 0 if any potential calls to
         | 
| 262 | 
            +
             * resize fail.
         | 
| 263 | 
            +
             */
         | 
| 238 264 | 
             
            pm_constant_id_t
         | 
| 239 265 | 
             
            pm_constant_pool_insert_owned(pm_constant_pool_t *pool, const uint8_t *start, size_t length) {
         | 
| 240 266 | 
             
                return pm_constant_pool_insert(pool, start, length, PM_CONSTANT_POOL_BUCKET_OWNED);
         | 
| 241 267 | 
             
            }
         | 
| 242 268 |  | 
| 243 | 
            -
             | 
| 244 | 
            -
             | 
| 269 | 
            +
            /**
         | 
| 270 | 
            +
             * Insert a constant into a constant pool from memory that is constant. Returns
         | 
| 271 | 
            +
             * the id of the constant, or 0 if any potential calls to resize fail.
         | 
| 272 | 
            +
             */
         | 
| 245 273 | 
             
            pm_constant_id_t
         | 
| 246 274 | 
             
            pm_constant_pool_insert_constant(pm_constant_pool_t *pool, const uint8_t *start, size_t length) {
         | 
| 247 275 | 
             
                return pm_constant_pool_insert(pool, start, length, PM_CONSTANT_POOL_BUCKET_CONSTANT);
         | 
| 248 276 | 
             
            }
         | 
| 249 277 |  | 
| 250 | 
            -
             | 
| 278 | 
            +
            /**
         | 
| 279 | 
            +
             * Free the memory associated with a constant pool.
         | 
| 280 | 
            +
             */
         | 
| 251 281 | 
             
            void
         | 
| 252 282 | 
             
            pm_constant_pool_free(pm_constant_pool_t *pool) {
         | 
| 253 283 | 
             
                // For each constant in the current constant pool, free the contents if the
         |