develooper Front page | perl.perl5.porters | Postings from December 2021

Re: "no snails"; or having signatured subs complain about @_

Thread Previous | Thread Next
From:
Paul "LeoNerd" Evans
Date:
December 9, 2021 16:29
Subject:
Re: "no snails"; or having signatured subs complain about @_
Message ID:
20211209162913.2a5d0a79@shy.leonerd.org.uk
On Thu, 9 Dec 2021 15:01:21 +0000
Dave Mitchell <davem@iabyn.com> wrote:

> On Tue, Dec 07, 2021 at 06:02:23PM +0000, Paul "LeoNerd" Evans wrote:
> > I think a lot of that isn't even necessary though. A variant of my
> > no-snails branch which I haven't yet committed or pushed, very
> > slightly relaxes the rules and allows a use of @_ as an rvalue in
> > scalar context, purely to allow the code to determine the argument
> > count.  
> 
> I HATE that suggestion!
> 
> For one thing, @_ is still a real variable, containing the args of the
> sub's (grand**N)parent, and will generally  be a different size than
> the proposed value of scalar(@_).
> 
> E.g. (assuming for the sake of demonstration that @_ is accessible to
> print at run time):
> 
>     sub sig ($a,$b) { print "@_"; print scalar @_ }
>     sub plain       { sig(qw(d e)); }
>     plain(qw(a b c));
> 
> outputs: (a b c 2), i.e. @_ contains 3 values but scalar(@_) returns
> 2.

Ahyes; in my current branch I've replaced @_ with a "broken" array that
won't be accessible. Whereas your intention is to not even touch it and
let it reach through to the first caller that wasn't signatured.

I should perhaps add that my "no-snails" branch isn't intended to be
merged to core; it's a useful test scout to find code in core that
would break if we alter the way @_-in-signatured-subs works so we can
fix that ahead of whatever real code changes we make. We might be able
to rescue small things like the CvSIGNATURE flag, but most of the rest
is throwaway temporary exploration.

It's also something that users can build and check their own code
against, to see if they'd be affected by that in future. As a next step
I'd probably look into seeing what can be detected at compiletime, as
that would obviously be much nicer than the current runtime approach.


> Second, using the arg count as a way of determining whether a default
> arg was passed etc, is awkward, ugly and error-prone for all but the
> simplest subs:
...

Yeah sure; it's not great. But it's something that lots of existing
code on CPAN and elsewhere does, right now, so it would be nice if we
could keep that working.

> PS - my intention is that the args will just be left on the stack,
> @_ / padsv[0] will never be populated, and OP_ARG* get their values
> directly from the stack.

OK, that's a detail I hadn't been aware of before. Keeping the values on
the stack does increase memory usage overall - I could imagine a
heavily signature-based program would have a much larger stack during
runtime than current programs do; in effect much more data would be
stored in a single AV, rather than being distributed over several of
them as they are now. That would have a knock-on effect of needing to
Move() more values around when that stack gets grown, so we'd have to
measure if the performance was still OK. Right now the "arguments stack"
is effectively distributed over many small AVs so that grow-time
problem doesn't come up as much.

-----

Lets take a step back here a second: The intermediate goal was to get
"something" towards having a no-snails change in place for 5.36, so we
can continue to move towards de-experimentalizing signatures overall in
time for 5.38.

This was one attempt at it, but could we try something else? E.g. what
about implementing the smallest bit of the query params, just
sufficient to replace existing uses of  scalar(@_)  in current code?
Based on the existing OP_ARGELEM code I could probably make the simple
?$ and ??$ params work within the next couple of days; perhaps something
sufficient to make this work

   sub f(??$has_x, ?$peek_x, $x) {
     ok($has_x);
     is($peek_x, 123);
     is($x, 123);
   }
   f(123);

Based on your intention of leaving argument values on the stack I could
also have a go at hacking up pp_entersub and the pp_arg* ops to work
with that, though at present I can't quite imagine how they'll find
their values from the stack once the actual body of the function has
begun executing (e.g. during the default expression code). My thoughts
are mostly described as the various part 3 sections of

  https://www.nntp.perl.org/group/perl.perl5.porters/2021/11/msg262052.html

From your suggestion to leave the args on the stack it seems like
option 3a is out, but that still leaves 3b, 3c from that mail, 3d from
the next mail

  https://www.nntp.perl.org/group/perl.perl5.porters/2021/11/msg262056.html

or perhaps some other implementation idea I haven't imagined yet - I'll
let you suggest a 3e. :)

-- 
Paul "LeoNerd" Evans

leonerd@leonerd.org.uk      |  https://metacpan.org/author/PEVANS
http://www.leonerd.org.uk/  |  https://www.tindie.com/stores/leonerd/

Thread Previous | Thread Next


nntp.perl.org: Perl Programming lists via nntp and http.
Comments to Ask Bjørn Hansen at ask@perl.org | Group listing | About