Skip to content

Commit 445550b

Browse files
committed
Fix handling of generic method names.
On JVM (and MoarVM, for that matter) the name associated with a code object is stored statically, not in the actual code ref itself like on Parrot. This is generally more efficient (saves a field in closures), but we relied on it. This prevented declaring more than one user defined operator in Rakudo on JVM, which busted various tests. On Parrot, we keep the same approach as today.
1 parent 3fbb512 commit 445550b

File tree

2 files changed

+52
-1
lines changed

2 files changed

+52
-1
lines changed

src/core/NQPRoutine.nqp

Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -345,6 +345,32 @@ my knowhow NQPRoutine {
345345
nqp::setcodename($!do, $name);
346346
}
347347

348+
method !reify_name($name) {
349+
#?if parrot
350+
nqp::setcodename($!do, $name);
351+
self
352+
#?endif
353+
#?if !parrot
354+
# Make a fresh underlying VM code ref.
355+
my $do := nqp::freshcoderef($!do);
356+
357+
# Clone and attach the code object.
358+
my $der := nqp::clone(self);
359+
nqp::bindattr($der, NQPRoutine, '$!do', $do);
360+
nqp::setcodeobj($do, $der);
361+
362+
# If needed, arrange for a fixup of the cloned code-ref.
363+
unless nqp::isnull($!clone_callback) {
364+
$!clone_callback($!do, $do, $der);
365+
}
366+
367+
# Update name.
368+
nqp::setcodename($do, $name);
369+
370+
$der
371+
#?endif
372+
}
373+
348374
method name() {
349375
nqp::getcodename($!do)
350376
}
@@ -458,6 +484,31 @@ my knowhow NQPRegex {
458484
method !set_name($name) {
459485
nqp::setcodename($!do, $name);
460486
}
487+
method !reify_name($name) {
488+
#?if parrot
489+
nqp::setcodename($!do, $name);
490+
self
491+
#?endif
492+
#?if !parrot
493+
# Make a fresh underlying VM code ref.
494+
my $do := nqp::freshcoderef($!do);
495+
496+
# Clone and attach the code object.
497+
my $der := nqp::clone(self);
498+
nqp::bindattr($der, NQPRegex, '$!do', $do);
499+
nqp::setcodeobj($do, $der);
500+
501+
# If needed, arrange for a fixup of the cloned code-ref.
502+
unless nqp::isnull($!clone_callback) {
503+
$!clone_callback($!do, $do, $der);
504+
}
505+
506+
# Update name.
507+
nqp::setcodename($do, $name);
508+
509+
$der
510+
#?endif
511+
}
461512
}
462513
nqp::setinvokespec(NQPRegex, NQPRegex, '$!do', nqp::null);
463514
nqp::setboolspec(NQPRegex, 5, nqp::null());

src/how/NQPParametricRoleHOW.nqp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -143,7 +143,7 @@ knowhow NQPParametricRoleHOW {
143143
!! nqp::iterval($_).clone();
144144
if nqp::substr($name, 0, 12) eq '!!LATENAME!!' {
145145
$name := nqp::atkey($pad, nqp::substr($name, 12));
146-
$meth.'!set_name'($name);
146+
$meth := $meth.'!reify_name'($name);
147147
}
148148
$irole.HOW.add_method($irole, $name, $meth);
149149
}

0 commit comments

Comments
 (0)