Aaron Patterson
578ff32611
Move filling in the rest of the locals to the end
2024-01-24 09:40:30 -08:00
Aaron Patterson
7a33a1aee2
Insert all locals in the locals index table
...
Prism provides an index (local_body_index) which is supposed to point at
the start of locals declared in the method body. Prism assumed that
method body locals would only occur _after_ parameter names.
Unfortunately this assumption is not correct, which meant that we would
in some cases not insert all locals in the local table. This commit
iterates over locals a second time, inserting any that didn't get
inserted on the first pass.
Fixes: https://github.com/ruby/prism/issues/2245
Co-Authored-By: Matt Valentine-House <matt@eightbitraptor.com>
2024-01-24 09:40:30 -08:00
Peter Zhu
927928badb
[PRISM] Fix anonymous keyword arguments
...
Fixes ruby/prism#2256 .
2024-01-24 11:41:08 -05:00
Kevin Newton
4220bdba39
[PRISM] Remove dead code from prism_compile.c
...
Previously, we were using the main pm_compile_node switch to compile
target nodes. Eventually we switched to pm_compile_target_node and
updated all the call sites. As such, all of this has become dead
code.
However, the multi target code was reused for both parameters and
multi writes (it was just incorrect for multi writes). So that code
has now been moved into its own function that is more specific to
destructured parameters (and has more assertions to that effect).
Overall now you should not see target nodes when you call into
pm_compile_node, since they are more specialized and require more
special handling.
2024-01-24 11:18:58 -05:00
Kevin Newton
767f5d045f
[PRISM] Use lvar depths for starting
2024-01-24 10:37:08 -05:00
Peter Zhu
529700d314
[PRISM] Nested MultiWriteNode with method calls
...
Fixes ruby/prism#2247 .
2024-01-24 10:08:25 -05:00
Peter Zhu
909a710a69
[PRISM] Fix anonymous splat nodes
...
Fixes ruby/prism#2257 .
2024-01-23 17:45:51 -05:00
Peter Zhu
cecf42601a
[PRISM] Fix block fowarding
2024-01-23 15:23:13 -05:00
Peter Zhu
333f4b4930
[PRISM] Support block parameters with no name
...
Fixes ruby/prism#2249 .
2024-01-23 15:23:13 -05:00
Aaron Patterson
cfa15bb173
Handle trailing commas on blocks
...
We need to set a special flag on block iseqs when there is a trailing
comma.
Fixes: https://github.com/ruby/prism/issues/2244
2024-01-22 16:35:58 -08:00
Aaron Patterson
270a46e392
Check keyword parameters correctly
...
We weren't checking the right offsets when compiling methods with
keyword parameters that had complex code.
Fixes: https://github.com/ruby/prism/issues/2228
2024-01-22 16:02:41 -08:00
Peter Zhu
708fa77404
[PRISM] Fix keyword arguments in IndexOrWriteNode
...
Fixes ruby/prism#2236 .
2024-01-22 15:07:52 -08:00
Peter Zhu
1838dbf6e7
[PRISM] Fix splat and block in aset
2024-01-22 15:07:39 -08:00
Peter Zhu
1847192366
[PRISM] Fix block in aset
...
Fixes ruby/prism#2223 .
2024-01-22 15:07:39 -08:00
Peter Zhu
8065672d99
[PRISM] Force semicolon at the end of PM macros
2024-01-22 15:22:12 -05:00
Peter Zhu
2630941696
[PRISM] Use PM_SWAP macro
2024-01-22 15:21:09 -05:00
Peter Zhu
789de5972b
[PRISM] Use PM_POP macro
2024-01-22 15:16:14 -05:00
Aaron Patterson
7db6832225
Fix compiling rescue + ensure
...
When we're compiling begin / rescue / ensure nodes, we need to "wrap"
the code in the begin statements correctly. The wrapping is like this:
(ensure code (rescue code (begin code)))
This patch pulls the each leg in to its own function, then calls the
appropriate wrapping function depending on whether there are ensure /
rescue legs.
Fixes: https://github.com/ruby/prism/issues/2221
2024-01-22 12:02:03 -08:00
Peter Zhu
dbd76d9101
[PRISM] Fix keyword splat in IndexAndWriteNode and IndexOrWriteNode
...
Fixes ruby/prism#2232 and ruby/prism#2234 .
2024-01-22 12:56:43 -05:00
Kevin Newton
ab99ce910c
[PRISM] Insert concatarray for index targets with splat
2024-01-22 12:55:06 -05:00
Kevin Newton
e5f8585a29
[PRISM] Fix line for leave instructions
2024-01-22 12:54:32 -05:00
Peter Zhu
a7af34fa8b
[PRISM] Fix keywords arguments in IndexAndWriteNode
...
Fixes ruby/prism#2233 .
2024-01-22 11:26:21 -05:00
Kevin Newton
6401f282d2
[PRISM] Fix up source line for 1-indexed line numbers
2024-01-22 11:21:04 -05:00
Kevin Newton
d68aaa6672
[PRISM] Freeze regex literals in iseqs
2024-01-22 11:12:38 -05:00
Peter Zhu
580429d27c
[PRISM] Fix incorrect ordering of MultiTargetNode
...
Fixes ruby/prism#2218 .
2024-01-22 10:51:43 -05:00
Matt Valentine-House
2abf153016
[PRISM] Add TP call/return events to method ISEQs
2024-01-22 09:40:52 -05:00
Kevin Newton
99d6e2f1ee
[PRISM] Revisit target nodes
2024-01-19 20:12:07 -05:00
eileencodes
ed50161bd6
[PRISM] Fix ensure code running twice
...
Fixes : ruby/prism#2212
2024-01-19 13:04:01 -08:00
Aaron Patterson
4778b0eeda
Fix kwarg ordering
...
Required keyword arguments need to come first.
Fixes: https://github.com/ruby/prism/issues/2158
Co-authored-by: Kevin Newton <kddnewton@gmail.com>
2024-01-19 12:32:20 -08:00
Peter Zhu
740f0b52e0
[PRISM] Fix typo with pm_scope_node_destroy
...
We need to run the pm_scope_node_destroy after compiling the iseq.
2024-01-19 14:09:32 -05:00
Aaron Patterson
efe4b8ac0f
Fix ensure code when running break in a while loop
...
We need to run ensure code when breaking from a while loop
Co-authored-by: John Hawthorn <jhawthorn@github.com>
Co-authored-by: Kevin Newton <kddnewton@gmail.com>
2024-01-19 09:35:36 -08:00
Peter Zhu
5a5cf23d02
[PRISM] Fix indentation for PM_SCOPE_NODE [ci skip]
2024-01-19 11:18:47 -05:00
Peter Zhu
c28094d385
[PRISM] Add function to free scope node
...
pm_scope_node_destroy frees the scope node after we're done using it to
make sure that the index_lookup_table is not leaked.
For example:
10.times do
100_000.times do
RubyVM::InstructionSequence.compile_prism("begin; 1; rescue; 2; end")
end
puts `ps -o rss= -p #{$$}`
end
Before:
33056
50304
67776
84544
101520
118448
135712
152352
169136
186656
After:
15264
15296
15408
17040
17152
17152
18320
18352
18400
18608
2024-01-18 16:33:25 -05:00
Peter Zhu
47081c3ee3
[PRISM] Pass pm_scope_node_t by reference
...
We can pass pm_scope_node_t by reference to pm_new_child_iseq rather
than by value.
2024-01-18 16:33:25 -05:00
Matt Valentine-House
60dd731125
[PRISM] Correct checkmatch flags for splat in rescue
2024-01-18 20:25:28 +00:00
Matt Valentine-House
8a3e7f08b8
[PRISM] Fix case splat with no predicate
2024-01-18 20:03:27 +00:00
Peter Zhu
686b1655a0
[PRISM] Fix indentation in switch [ci skip]
2024-01-18 14:59:59 -05:00
Peter Zhu
d8ac96efc5
[PRISM] Fix memory leak in case nodes
...
The temporary array conditions_labels is heap allocated and never freed.
We can use alloca instead to stack allocate it so that we don't need to
manually free it.
For example:
code = "case; #{100.times.map { "when #{it}; " }.join}; end"
10.times do
10_000.times do
RubyVM::InstructionSequence.compile_prism(code)
end
puts `ps -o rss= -p #{$$}`
end
Before:
21376
30304
38800
47184
55456
64192
72288
80400
89040
97104
After:
13088
13632
13760
14016
14688
14992
15120
15232
15744
15744
2024-01-18 13:40:14 -05:00
Peter Zhu
00814fd672
[PRISM] Fix memory leak in iseq
...
rb_iseq_compile_prism_node calls both rb_translate_prism and iseq_setup.
Both of these functions call iseq_set_sequence. This means that the first
iseq_set_sequence will leak because the iseq will be overwritten.
For example:
10.times do
100_000.times do
RubyVM::InstructionSequence.compile_prism("")
end
puts `ps -o rss= -p #{$$}`
end
Before:
20528
27328
33840
40208
46400
52960
59168
65600
71888
78352
After:
13696
13712
13712
13712
13712
14352
14352
14992
14992
14992
2024-01-18 10:35:46 -05:00
eileencodes
db9f5fc916
[Prism] Implement defined? for PM_UNLESS_NODE
...
Ruby code:
```ruby
defined?(unless true; 1; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,16)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,16)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
555af5e599
[Prism] Implement defined? for PM_UNTIL_NODE
...
Ruby code:
```ruby
defined?(until a == 1; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,16)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,16)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
24d02cd485
[Prism] Implement defined? for PM_WHILE_NODE
...
Ruby code:
```ruby
defined?(while a != 1; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,16)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,16)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
b5d3d61130
[Prism] Implement defined? for PM_SINGLETON_CLASS_NODE
...
Ruby code:
```ruby
defined?(class << self; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,16)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,16)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
d2000e0e6c
[Prism] Implement defined? for PM_RATIONAL_NODE
...
Ruby code:
```ruby
defined?(1.2r)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,16)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,16)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
913772a08a
[Prism] Implement defined? for PM_MODULE_NODE
...
Ruby code:
```ruby
defined?(module M; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,16)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,16)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
a9a22b9f2d
[Prism] Implement defined? for PM_MATCH_REQUIRED_NODE
...
Ruby code:
```ruby
defined?(1 => 1)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,16)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,16)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
b40fc4f0a7
[Prism] Implement defined? for PM_MATCH_WRITE_NODE
...
Ruby code:
```ruby
defined?(/(?<foo>bar)/ =~ 'barbar')
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,35)>
local table (size: 1, argc: 0 [opts: 0, rest: -1, post: 0, block: -1, kw: -1@-1, kwrest: -1])
[ 1] foo@0
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,35)>
local table (size: 1, argc: 0 [opts: 0, rest: -1, post: 0, block: -1, kw: -1@-1, kwrest: -1])
[ 1] foo@0
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
a2092ef207
[Prism] Implement defined? for PM_IF_NODE
...
Ruby code:
```ruby
defined?(if true; 1; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,43)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,43)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
fb1eed3f70
[Prism] Implement defined? for PM_FOR_NODE
...
Ruby code:
```ruby
defined?(for i in [1,2] do; i; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,43)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,43)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00
eileencodes
7460820fec
[Prism] Implement defined? for PM_DEF_NODE
...
Ruby code:
```ruby
defined?(def prism_test_def_node; end)
```
Instructions:
```
"********* Ruby *************"
== disasm: #<ISeq:<compiled>@<compiled>:1 (1,0)-(59,43)>
0000 putobject "expression" ( 59)[Li]
0002 leave
"********* PRISM *************"
== disasm: #<ISeq:<compiled>@<compiled>:58 (58,0)-(58,43)>
0000 putobject "expression" ( 58)[Li]
0002 leave
```
Related: ruby/prism#2188
2024-01-17 17:21:29 -05:00