Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
proto auto-generation for methods, so it's now possible to write mult…
…i methods again without having to write an explicit proto. Re-uses generic instantiation get get the invocant type on the auto-gen'd proto right...a cunning use I'd not thought of for it. :-)
  • Loading branch information
jnthn committed Jul 9, 2011
1 parent 734ed25 commit 63f8bd7
Show file tree
Hide file tree
Showing 3 changed files with 28 additions and 4 deletions.
7 changes: 6 additions & 1 deletion src/Perl6/Metamodel/BOOTSTRAP.pm
Expand Up @@ -352,7 +352,12 @@ Code.HOW.add_method(Code, 'name', sub ($self) {
~pir::getattribute__PPPs(pir::perl6_decontainerize__PP($self),
Code, '$!do')
});

Code.HOW.add_method(Code, '!set_name', sub ($self, $name) {
pir::assign__vPS(
pir::getattribute__PPPs(pir::perl6_decontainerize__PP($self), Code, '$!do'),
$name)
});

# Need to actually run the code block. Also need this available before we finish
# up the stub.
Code.HOW.add_parrot_vtable_handler_mapping(Code, 'invoke', '$!do');
Expand Down
17 changes: 14 additions & 3 deletions src/Perl6/Metamodel/MultiMethodContainer.pm
Expand Up @@ -2,6 +2,14 @@ role Perl6::Metamodel::MultiMethodContainer {
# Set of multi-methods to incorporate. Not just the method handles;
# each is a hash containing keys name and body.
has @!multi_methods_to_incorporate;

# The proto we'll clone.
my $autogen_proto;

# Sets the proto we'll auto-gen based on.
method set_autogen_proto($proto) {
$autogen_proto := $proto
}

# We can't incorporate multis right away as we don't know all parents
# yet, maybe, which influences whether we even can have multis, need to
Expand Down Expand Up @@ -80,9 +88,12 @@ role Perl6::Metamodel::MultiMethodContainer {
$j := $j + 1;
}
unless $found {
pir::die("Could not find a proto for multi '" ~ $name ~
"' in package '" ~ self.name($obj) ~
"', and proto generation is not yet implemented");
# No proto found, so we'll generate one here.
my $proto := $autogen_proto.instantiate_generic(
hash( T => $obj ));
$proto."!set_name"($name);
$proto.add_dispatchee($code);
self.add_method($obj, $name, $proto);
}
}
$i := $i + 1;
Expand Down
8 changes: 8 additions & 0 deletions src/core/stubs.pm
Expand Up @@ -23,4 +23,12 @@ sub DYNAMIC(\$name) is rw {
$x
}

# Set up ClassHOW's auto-gen proto (nested scope so it won't
# actually appear in the setting).
{
my class Dummy {
our proto method AUTOGEN(::T $: |$) { * }
}
Dummy.HOW.set_autogen_proto(&Dummy::AUTOGEN);
}

0 comments on commit 63f8bd7

Please sign in to comment.