B-OPCheck

 view release on metacpan or  search on metacpan

lib/B/OPCheck.pm  view on Meta::CPAN

package B::OPCheck; # git description: v0.31-4-gd081d88
# ABSTRACT: PL_check hacks using Perl callbacks

use 5.008;

use strict;
use warnings;

use Carp;
use XSLoader;
use Scalar::Util;
use Scope::Guard;
use B::Utils 0.08 ();

our $VERSION = '0.32';

XSLoader::load 'B::OPCheck', $VERSION;

sub import {
    my ($class, $opname, $mode, $sub) = @_;

    $^H |= 0x120000; # set HINT_LOCALIZE_HH + an unused bit to work around a %^H bug

    my $by_opname = $^H{OPCHECK_leavescope} ||= {};
    my $guards = $by_opname->{$opname} ||= [];
    push @$guards, Scope::Guard->new(sub {
        leavescope($opname, $mode, $sub);
    });

    enterscope($opname, $mode, $sub);
}

sub unimport {
    my ($class, $opname) = @_;

    if ( defined $opname ) {
        my $by_opname = $^H{OPCHECK_leavescope};
        delete $by_opname->{$opname};
        return if scalar keys %$by_opname; # don't delete other things
    }

    delete $^H{OPCHECK_leavescope};
    $^H &= ~0x120000;
}

1;

__END__

=pod

=encoding UTF-8

=head1 NAME

B::OPCheck - PL_check hacks using Perl callbacks

=head1 VERSION

version 0.32

=head1 SYNOPSIS

    use B::Generate; # to change things

    use B::OPCheck entersub => check => sub {
        my $op = shift; # op has been checked by normal PL_check
        sodomize($op);
    };

    foo(); # this entersub will have the callback triggered

=head1 DESCRIPTION

PL_check is an array indexed by opcode number (op_type) that contains function
pointers invoked as the last stage of optree compilation, per op.

This hook is called in bottom up order, as the code is parsed and the optree is
prepared.

This is how modules like L<autobox> do their magic

This module provides an api for registering PL_check hooks lexically, allowing
you to alter the behavior of certain ops using L<B::Generate> from perl space.



( run in 0.582 second using v1.01-cache-2.11-cpan-ceb78f64989 )