in reply to Re^4: named sub, subref and magic goto speed
in thread named sub, subref and magic goto speed

( ah, I don't know. ) However, you can't say that goto $ref is really goto &$ref. My benchmarks show they are quite different.

Replies are listed 'Best First'.
Re^6: named sub, subref and magic goto speed
by Limbic~Region (Chancellor) on Dec 14, 2006 at 17:01 UTC
    ikegami,
    You have updated your node without noting it as such. The content of your original node to which my reply applies to was:

    My benchmarks show that goto $ref is quite different from goto &$ref.

    First, I want to make it clear that my question has nothing to do with speed or benchmarks. My question is specifically regarding to ysth's implied assertion that goto &$ref; does not have to build a stack frame.

    Of course, this assumes that goto $ref; truly is the same as goto &$ref; which you yourself say:

    The docs say a label is expected, but if a code ref is provided, goto $ref is treated as goto &$ref.

    Since your benchmarks indicate that this isn't the case, perhaps perl is doing something special under the covers and you should revise your statement. My original question was regarding stack frames only, but at this point I am also interested in knowing why goto $ref; is behaving as if it were goto &$ref; but performs much better.

    Cheers - L~R

      Maybe it's having to do a lookup of labels first, to make sure "CODE(0x226298)" isn't actually the name of a label.

      We're building the house of the future together.
        jdporter,
        That would imply goto $ref; should be slower when ikegami's benchmarks show it being much faster. This is interesting and all but I am really hoping ysth can clarify what he meant regarding stack frames.

        Cheers - L~R

      All,
      Since I am currently without perl, ikegami was kind enough to provide the following regarding the optree differences:
      Given the following !.pl: sub goto_scalar { goto $ref; } sub goto_amp { goto &$ref; } >perl -MO=Concise,goto_scalar !.pl main::goto_scalar: 4 <1> leavesub[1 ref] K/REFC,1 ->(end) - <@> lineseq KP ->4 1 <;> nextstate(main 1 !.pl:1) v ->2 3 <1> goto sKS/1 ->4 - <1> ex-rv2sv sK/1 ->3 2 <#> gvsv[*ref] s ->3 !.pl syntax OK >perl -MO=Concise,goto_amp !.pl main::goto_amp: 7 <1> leavesub[1 ref] K/REFC,1 ->(end) - <@> lineseq KP ->7 1 <;> nextstate(main 2 !.pl:2) v ->2 6 <1> goto sKS/1 ->7 5 <1> refgen sK/1 ->6 - <1> ex-list lKRM ->5 2 <0> pushmark sRM ->3 4 <1> rv2cv[t2] lKRM/33 ->5 - <1> ex-list lK ->4 - <0> ex-pushmark s ->3 - <1> ex-rv2cv vKPRM*/1 ->- - <1> ex-rv2sv sK/1 ->- 3 <#> gvsv[*ref] s ->4 !.pl syntax OK
      At a glance, a masked bandit core hacker suspected the rv2cv extra opcode was necessary but that refgen thinking it needed to boil down a list as though it needed to handle \($a, $b, $c) or some such probably wasn't - though I may have misunderstood him.

      Cheers - L~R