-----BEGIN PGP SIGNED MESSAGE-----
Moin,
this is a followup with a final, working patch to:
http://groups.google.com/groups?selm=200409242053.07582%40bloodgate.com
Summary:
A lot of modules delay loading Carp.pm until they need on, on the ground that
hard errors are seldom and that loading unnec. cruft is well, unnec. until
the error actually occurs :)
However, it turned out that a popular module, warnings.pm, always loaded Carp.
Unfortunately, warnings.pm was used by vars.pm - leading to a lot of modules
getting always Carp - this includes basically everything, since vars is uses
quite a lot.
Even more unfortunately (or should I say ironic) is that certain modules tried
to delay loading of Carp, but then had code in them that only worked if Carp
was loaded. Exporter and Exporter::Heavy are two examples, but also warnings
fell into that category :)
This patch removes Carp from warnings.pm - saving a bit of memory. It also
adjusts all the places that stumbled over the missing Carp - Exporter and
Encode being the primary examples. Most of the places are actually test
files.
I wish to thank Jim Cromie, he provieded much needed insight into the B tests.
Below is a short overview over the memory savings.
Best wishes,
Tels
Benchmark done by running the equivalent of:
./perl -Ilib -I. -Mvars -le 'for (1..100000){ for (1..100000){$a++;}}'
and then looking at the column "RES" from top's output to determine the mem
used in Kbyte.
module | 5.8.3 blead blead patch Savings
--------------------------------------------------------------
vars 1784 1656 1592 4%
Exporter 1616 1484 1484 0%
warnings 1744 1612 1448 10%
strict 1528 1364 1364 0%
Carp 1668 1532 1532 0%
bignum 2924 3612 3592 0.5%
Interesting to note is that blead already takes less memory than 5.8.3 - but
5.8.3 was compiled by SuSE, so this might have something to do with that.
Also, bignum takes a lot more - maybe because newer BigInt/BigFloat are so
much bigger? That sounds unlikely to me...
- --
Signed on Sat Oct 16 15:41:01 2004 with key 0x93B84C15.
Visit my photo gallery at http://bloodgate.com/photos/
PGP key on http://bloodgate.com/tels.asc or per email.
"Duke Nukem Forever will come out before Doom 3." - George Broussard, 2002
(http://tinyurl.com/6m8nh)
-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.2.4 (GNU/Linux)
iQEVAwUBQXEttHcLPEOTuEwVAQFfBAf9HNi1CMU22QPsbOb7ipa59/FQvO/yTAKd
l0SMEJ0Tn6dOgIxvRlgMxVhNZLO5kE4VUJpA+WIUG890J/ex4t2AXb2GNHAYIPp4
AfDUrYbqUI32pqL0oc6kx9eH7JVaEdWdwU1hmawxo+2XQynrUOX9DsM3pxj9lTU5
6nn9HDP+AkVcN9mQ+8gNLnYfBw21JQZeKwuI8Gl42MnQcmWLjCbMh9sKxpxzn6CZ
Hi3Ix8cWTKWky8AM9r5fKP2E6gX0nxbir/gImx93MKrVsqAKdq5g8hIMgyi5kA7d
vORpO7DApmaJ5DCBTE141I3kGJuD5REihPFZHZ8qBmMADd7wpUv6iQ==
=MZSF
-----END PGP SIGNATURE-----
diff -ruN blead/ext/B/t/optree_specials.t blead.patch/ext/B/t/optree_specials.t
--- blead/ext/B/t/optree_specials.t 2004-06-18 14:00:33.000000000 +0200
+++ blead.patch/ext/B/t/optree_specials.t 2004-10-16 13:32:28.000000000 +0200
@@ -1,5 +1,12 @@
#!./perl
+# This tests the B:: module(s) with CHECK, BEGIN, END and INIT blocks. The
+# text excerpts below marked with "# " in front are the expected output. They
+# are there twice, EOT for threading, and EONT for a non-threading Perl. The
+# output is matched losely. If the match fails even though the "got" and
+# "expected" output look exactly the same, then watch for trailing, invisible
+# spaces.
+
BEGIN {
chdir 't';
@INC = ('../lib', '../ext/B/t');
@@ -29,7 +36,6 @@
my $src = q[our ($beg, $chk, $init, $end) = qq{'foo'}; BEGIN { $beg++ } CHECK {
$chk++ } INIT { $init++ } END { $end++ }];
-
checkOptree ( name => 'BEGIN',
bcopts => 'BEGIN',
prog => $src,
@@ -37,74 +43,46 @@
# BEGIN 1:
# b <1> leavesub[1 ref] K/REFC,1 ->(end)
# - <@> lineseq KP ->b
-# 1 <;> nextstate(B::Concise -242 Concise.pm:304) v/2 ->2
+# 1 <;> nextstate(B::Concise -234 Concise.pm:328) v/2 ->2
# 3 <1> require sK/1 ->4
-# 2 <$> const[PV "strict.pm"] s/BARE ->3
-# 4 <;> nextstate(B::Concise -242 Concise.pm:304) v/2 ->5
+# 2 <$> const(PV "warnings.pm") s/BARE ->3
+# 4 <;> nextstate(B::Concise -234 Concise.pm:328) v/2 ->5
# - <@> lineseq K ->-
-# 5 <;> nextstate(B::Concise -242 Concise.pm:304) /2 ->6
+# 5 <;> nextstate(B::Concise -234 Concise.pm:328) /2 ->6
# a <1> entersub[t1] KS*/TARG,2 ->b
# 6 <0> pushmark s ->7
-# 7 <$> const[PV "strict"] sM ->8
-# 8 <$> const[PV "refs"] sM ->9
-# 9 <$> method_named[PVIV 1520340202] ->a
+# 7 <$> const(PV "warnings") sM ->8
+# 8 <$> const(PV "qw") sM ->9
+# 9 <$> method_named(PVIV 1520340202) ->a
# BEGIN 2:
-# m <1> leavesub[1 ref] K/REFC,1 ->(end)
-# - <@> lineseq KP ->m
-# c <;> nextstate(B::Concise -227 Concise.pm:327) v/2 ->d
-# e <1> require sK/1 ->f
-# d <$> const[PV "warnings.pm"] s/BARE ->e
-# f <;> nextstate(B::Concise -227 Concise.pm:327) v/2 ->g
-# - <@> lineseq K ->-
-# g <;> nextstate(B::Concise -227 Concise.pm:327) /2 ->h
-# l <1> entersub[t1] KS*/TARG,2 ->m
-# h <0> pushmark s ->i
-# i <$> const[PV "warnings"] sM ->j
-# j <$> const[PV "qw"] sM ->k
-# k <$> method_named[PVIV 1520340202] ->l
-# BEGIN 3:
-# q <1> leavesub[1 ref] K/REFC,1 ->(end)
-# - <@> lineseq KP ->q
-# n <;> nextstate(main 2 -e:3) v ->o
-# p <1> postinc[t3] sK/1 ->q
-# - <1> ex-rv2sv sKRM/1 ->p
-# o <#> gvsv[*beg] s ->p
+# f <1> leavesub[1 ref] K/REFC,1 ->(end)
+# - <@> lineseq KP ->f
+# c <;> nextstate(main 2 -e:1) v ->d
+# e <1> postinc[t2] sK/1 ->f
+# - <1> ex-rv2sv sKRM/1 ->e
+# d <$> gvsv(*beg) s ->e
EOT_EOT
# BEGIN 1:
# b <1> leavesub[1 ref] K/REFC,1 ->(end)
# - <@> lineseq KP ->b
-# 1 <;> nextstate(B::Concise -242 Concise.pm:304) v/2 ->2
+# 1 <;> nextstate(B::Concise -234 Concise.pm:328) v/2 ->2
# 3 <1> require sK/1 ->4
-# 2 <$> const(PV "strict.pm") s/BARE ->3
-# 4 <;> nextstate(B::Concise -242 Concise.pm:304) v/2 ->5
+# 2 <$> const(PV "warnings.pm") s/BARE ->3
+# 4 <;> nextstate(B::Concise -234 Concise.pm:328) v/2 ->5
# - <@> lineseq K ->-
-# 5 <;> nextstate(B::Concise -242 Concise.pm:304) /2 ->6
+# 5 <;> nextstate(B::Concise -234 Concise.pm:328) /2 ->6
# a <1> entersub[t1] KS*/TARG,2 ->b
# 6 <0> pushmark s ->7
-# 7 <$> const(PV "strict") sM ->8
-# 8 <$> const(PV "refs") sM ->9
+# 7 <$> const(PV "warnings") sM ->8
+# 8 <$> const(PV "qw") sM ->9
# 9 <$> method_named(PVIV 1520340202) ->a
# BEGIN 2:
-# m <1> leavesub[1 ref] K/REFC,1 ->(end)
-# - <@> lineseq KP ->m
-# c <;> nextstate(B::Concise -227 Concise.pm:327) v/2 ->d
-# e <1> require sK/1 ->f
-# d <$> const(PV "warnings.pm") s/BARE ->e
-# f <;> nextstate(B::Concise -227 Concise.pm:327) v/2 ->g
-# - <@> lineseq K ->-
-# g <;> nextstate(B::Concise -227 Concise.pm:327) /2 ->h
-# l <1> entersub[t1] KS*/TARG,2 ->m
-# h <0> pushmark s ->i
-# i <$> const(PV "warnings") sM ->j
-# j <$> const(PV "qw") sM ->k
-# k <$> method_named(PVIV 1520340202) ->l
-# BEGIN 3:
-# q <1> leavesub[1 ref] K/REFC,1 ->(end)
-# - <@> lineseq KP ->q
-# n <;> nextstate(main 2 -e:3) v ->o
-# p <1> postinc[t2] sK/1 ->q
-# - <1> ex-rv2sv sKRM/1 ->p
-# o <$> gvsv(*beg) s ->p
+# f <1> leavesub[1 ref] K/REFC,1 ->(end)
+# - <@> lineseq KP ->f
+# c <;> nextstate(main 2 -e:1) v ->d
+# e <1> postinc[t2] sK/1 ->f
+# - <1> ex-rv2sv sKRM/1 ->e
+# d <$> gvsv(*beg) s ->e
EONT_EONT
@@ -181,92 +159,68 @@
prog => $src,
expect => <<'EOT_EOT', expect_nt => <<'EONT_EONT');
# BEGIN 1:
-# 1 <;> nextstate(B::Concise -242 Concise.pm:304) v/2
-# 2 <$> const[PV "strict.pm"] s/BARE
+# 1 <;> nextstate(B::Concise -234 Concise.pm:328) v/2
+# 2 <$> const(PV "warnings.pm") s/BARE
# 3 <1> require sK/1
-# 4 <;> nextstate(B::Concise -242 Concise.pm:304) v/2
-# 5 <;> nextstate(B::Concise -242 Concise.pm:304) /2
+# 4 <;> nextstate(B::Concise -234 Concise.pm:328) v/2
+# 5 <;> nextstate(B::Concise -234 Concise.pm:328) /2
# 6 <0> pushmark s
-# 7 <$> const[PV "strict"] sM
-# 8 <$> const[PV "refs"] sM
-# 9 <$> method_named[PVIV 1520340202]
+# 7 <$> const(PV "warnings") sM
+# 8 <$> const(PV "qw") sM
+# 9 <$> method_named(PVIV 1520340202)
# a <1> entersub[t1] KS*/TARG,2
# b <1> leavesub[1 ref] K/REFC,1
# BEGIN 2:
-# c <;> nextstate(B::Concise -227 Concise.pm:327) v/2
-# d <$> const[PV "warnings.pm"] s/BARE
-# e <1> require sK/1
-# f <;> nextstate(B::Concise -227 Concise.pm:327) v/2
-# g <;> nextstate(B::Concise -227 Concise.pm:327) /2
-# h <0> pushmark s
-# i <$> const[PV "warnings"] sM
-# j <$> const[PV "qw"] sM
-# k <$> method_named[PVIV 1520340202]
-# l <1> entersub[t1] KS*/TARG,2
-# m <1> leavesub[1 ref] K/REFC,1
-# BEGIN 3:
-# n <;> nextstate(main 2 -e:3) v
-# o <#> gvsv[*beg] s
-# p <1> postinc[t3] sK/1
-# q <1> leavesub[1 ref] K/REFC,1
+# c <;> nextstate(main 2 -e:1) v
+# d <$> gvsv(*beg) s
+# e <1> postinc[t2] sK/1
+# f <1> leavesub[1 ref] K/REFC,1
# END 1:
-# r <;> nextstate(main 5 -e:6) v
-# s <#> gvsv[*end] s
-# t <1> postinc[t3] sK/1
-# u <1> leavesub[1 ref] K/REFC,1
+# g <;> nextstate(main 5 -e:1) v
+# h <$> gvsv(*end) s
+# i <1> postinc[t2] sK/1
+# j <1> leavesub[1 ref] K/REFC,1
# INIT 1:
-# v <;> nextstate(main 4 -e:5) v
-# w <#> gvsv[*init] s
-# x <1> postinc[t3] sK/1
-# y <1> leavesub[1 ref] K/REFC,1
+# k <;> nextstate(main 4 -e:1) v
+# l <$> gvsv(*init) s
+# m <1> postinc[t2] sK/1
+# n <1> leavesub[1 ref] K/REFC,1
# CHECK 1:
-# z <;> nextstate(main 3 -e:4) v
-# 10 <#> gvsv[*chk] s
-# 11 <1> postinc[t3] sK/1
-# 12 <1> leavesub[1 ref] K/REFC,1
+# o <;> nextstate(main 3 -e:1) v
+# p <$> gvsv(*chk) s
+# q <1> postinc[t2] sK/1
+# r <1> leavesub[1 ref] K/REFC,1
EOT_EOT
# BEGIN 1:
-# 1 <;> nextstate(B::Concise -242 Concise.pm:304) v/2
-# 2 <$> const(PV "strict.pm") s/BARE
+# 1 <;> nextstate(B::Concise -234 Concise.pm:328) v/2
+# 2 <$> const(PV "warnings.pm") s/BARE
# 3 <1> require sK/1
-# 4 <;> nextstate(B::Concise -242 Concise.pm:304) v/2
-# 5 <;> nextstate(B::Concise -242 Concise.pm:304) /2
+# 4 <;> nextstate(B::Concise -234 Concise.pm:328) v/2
+# 5 <;> nextstate(B::Concise -234 Concise.pm:328) /2
# 6 <0> pushmark s
-# 7 <$> const(PV "strict") sM
-# 8 <$> const(PV "refs") sM
+# 7 <$> const(PV "warnings") sM
+# 8 <$> const(PV "qw") sM
# 9 <$> method_named(PVIV 1520340202)
# a <1> entersub[t1] KS*/TARG,2
# b <1> leavesub[1 ref] K/REFC,1
# BEGIN 2:
-# c <;> nextstate(B::Concise -227 Concise.pm:327) v/2
-# d <$> const(PV "warnings.pm") s/BARE
-# e <1> require sK/1
-# f <;> nextstate(B::Concise -227 Concise.pm:327) v/2
-# g <;> nextstate(B::Concise -227 Concise.pm:327) /2
-# h <0> pushmark s
-# i <$> const(PV "warnings") sM
-# j <$> const(PV "qw") sM
-# k <$> method_named(PVIV 1520340202)
-# l <1> entersub[t1] KS*/TARG,2
-# m <1> leavesub[1 ref] K/REFC,1
-# BEGIN 3:
-# n <;> nextstate(main 2 -e:3) v
-# o <$> gvsv(*beg) s
-# p <1> postinc[t2] sK/1
-# q <1> leavesub[1 ref] K/REFC,1
+# c <;> nextstate(main 2 -e:1) v
+# d <$> gvsv(*beg) s
+# e <1> postinc[t2] sK/1
+# f <1> leavesub[1 ref] K/REFC,1
# END 1:
-# r <;> nextstate(main 5 -e:6) v
-# s <$> gvsv(*end) s
-# t <1> postinc[t2] sK/1
-# u <1> leavesub[1 ref] K/REFC,1
+# g <;> nextstate(main 5 -e:1) v
+# h <$> gvsv(*end) s
+# i <1> postinc[t2] sK/1
+# j <1> leavesub[1 ref] K/REFC,1
# INIT 1:
-# v <;> nextstate(main 4 -e:5) v
-# w <$> gvsv(*init) s
-# x <1> postinc[t2] sK/1
-# y <1> leavesub[1 ref] K/REFC,1
+# k <;> nextstate(main 4 -e:1) v
+# l <$> gvsv(*init) s
+# m <1> postinc[t2] sK/1
+# n <1> leavesub[1 ref] K/REFC,1
# CHECK 1:
-# z <;> nextstate(main 3 -e:4) v
-# 10 <$> gvsv(*chk) s
-# 11 <1> postinc[t2] sK/1
-# 12 <1> leavesub[1 ref] K/REFC,1
+# o <;> nextstate(main 3 -e:1) v
+# p <$> gvsv(*chk) s
+# q <1> postinc[t2] sK/1
+# r <1> leavesub[1 ref] K/REFC,1
EONT_EONT
diff -ruN blead/ext/B/t/stash.t blead.patch/ext/B/t/stash.t
--- blead/ext/B/t/stash.t 2004-09-08 19:15:52.000000000 +0200
+++ blead.patch/ext/B/t/stash.t 2004-10-16 13:07:48.000000000 +0200
@@ -71,7 +71,7 @@
$got = "@got";
-my $expected = "attributes Carp Carp::Heavy DB Exporter Exporter::Heavy Internals
main Regexp utf8 version warnings";
+my $expected = "attributes Carp Carp::Heavy DB Internals main Regexp utf8 version
warnings";
$expected =~ s/version // if $] < 5.009;
@@ -83,7 +83,7 @@
if ((($Config{static_ext} eq ' ') || ($Config{static_ext} eq ''))
&& !($^O eq 'os2' and $OS2::is_aout)
) {
- print "# [$got]\n# vs.\n# [$expected]\nnot " if $got ne $expected;
+ print "# got [$got]\n# vs.\n# expected [$expected]\nnot " if $got ne $expected;
ok;
} else {
print "ok $test # skipped: one or more static extensions\n"; $test++;
diff -ruN blead/ext/Encode/lib/Encode/Encoding.pm
blead.patch/ext/Encode/lib/Encode/Encoding.pm
--- blead/ext/Encode/lib/Encode/Encoding.pm 2004-05-20 15:51:06.000000000 +0200
+++ blead.patch/ext/Encode/lib/Encode/Encoding.pm 2004-10-16 13:58:59.000000000
+0200
@@ -39,14 +39,14 @@
require Carp;
my $obj = shift;
my $class = ref($obj) ? ref($obj) : $obj;
- Carp::croak $class, "->encode() not defined!";
+ Carp::croak($class . "->encode() not defined!");
}
sub decode{
require Carp;
my $obj = shift;
my $class = ref($obj) ? ref($obj) : $obj;
- Carp::croak $class, "->encode() not defined!";
+ Carp::croak($class . "->encode() not defined!");
}
sub DESTROY {}
diff -ruN blead/lib/Carp.pm blead.patch/lib/Carp.pm
--- blead/lib/Carp.pm 2004-08-17 10:50:23.000000000 +0200
+++ blead.patch/lib/Carp.pm 2004-10-16 13:07:48.000000000 +0200
@@ -178,9 +178,11 @@
=cut
-
+# disable these by default, so they can live w/o require Carp
$CarpInternal{Carp}++;
$CarpInternal{warnings}++;
+$Internal{Exporter}++;
+$Internal{'Exporter::Heavy'}++;
$CarpLevel = 0; # How many extra package levels to skip on carp.
# How many calls to skip on confess.
# Reconciling these notions is hard, use
diff -ruN blead/lib/English.pm blead.patch/lib/English.pm
--- blead/lib/English.pm 2003-08-14 10:02:53.000000000 +0200
+++ blead.patch/lib/English.pm 2004-10-16 13:07:48.000000000 +0200
@@ -64,7 +64,7 @@
}
|| do {
require Carp ;
- Carp::croak "Can't create English for match leftovers: $@" ;
+ Carp::croak ("Can't create English for match leftovers: $@") ;
}
) ;
}
diff -ruN blead/lib/Exporter/Heavy.pm blead.patch/lib/Exporter/Heavy.pm
--- blead/lib/Exporter/Heavy.pm 2004-01-21 22:33:08.000000000 +0100
+++ blead.patch/lib/Exporter/Heavy.pm 2004-10-16 13:07:48.000000000 +0200
@@ -5,7 +5,8 @@
# On one line so MakeMaker will see it.
require Exporter; our $VERSION = $Exporter::VERSION;
-$Carp::Internal{"Exporter::Heavy"} = 1;
+# Carp does this now for us, so we can finally live w/o Carp
+#$Carp::Internal{"Exporter::Heavy"} = 1;
=head1 NAME
diff -ruN blead/lib/Exporter.pm blead.patch/lib/Exporter.pm
--- blead/lib/Exporter.pm 2004-01-26 23:33:33.000000000 +0100
+++ blead.patch/lib/Exporter.pm 2004-10-16 13:07:48.000000000 +0200
@@ -11,7 +11,8 @@
our $Verbose ||= 0;
our $VERSION = '5.58';
our (%Cache);
-$Carp::Internal{Exporter} = 1;
+# Carp does this now for us, so we can finally live w/o Carp
+#$Carp::Internal{Exporter} = 1;
sub as_heavy {
require Exporter::Heavy;
diff -ruN blead/lib/Exporter.t blead.patch/lib/Exporter.t
--- blead/lib/Exporter.t 2003-11-28 23:02:14.000000000 +0100
+++ blead.patch/lib/Exporter.t 2004-10-16 13:07:48.000000000 +0200
@@ -75,7 +75,7 @@
BEGIN {*is = \&Is};
sub Is { 'Is' };
-Exporter::export_ok_tags;
+Exporter::export_ok_tags();
my %tags = map { $_ => 1 } map { @$_ } values %EXPORT_TAGS;
my %exportok = map { $_ => 1 } @EXPORT_OK;
diff -ruN blead/lib/vars_carp.t blead.patch/lib/vars_carp.t
--- blead/lib/vars_carp.t 1970-01-01 01:00:00.000000000 +0100
+++ blead.patch/lib/vars_carp.t 2004-10-16 13:07:48.000000000 +0200
@@ -0,0 +1,17 @@
+#!./perl
+
+# test that "use vars;" doesn't load Carp
+
+BEGIN {
+ chdir 't' if -d 't';
+ @INC = '../lib';
+ $ENV{PERL5LIB} = '../lib';
+}
+
+$| = 1;
+
+print "1..1\n";
+
+# Carp not loaded yet;
+print defined $Carp::VERSION ? "not ok 1\n" : "ok 1\n";
+
diff -ruN blead/lib/warnings.pm blead.patch/lib/warnings.pm
--- blead/lib/warnings.pm 2004-10-12 18:32:03.000000000 +0200
+++ blead.patch/lib/warnings.pm 2004-10-16 13:07:48.000000000 +0200
@@ -131,8 +131,6 @@
=cut
-use Carp ();
-
our %Offsets = (
# Warnings Categories added in Perl 5.008
@@ -300,6 +298,7 @@
sub Croaker
{
+ require Carp;
delete $Carp::CarpInternal{'warnings'};
Carp::croak(@_);
}
@@ -473,6 +472,7 @@
my $message = pop ;
my ($callers_bitmask, $offset, $i) = __chk(@_) ;
+ require Carp;
Carp::croak($message)
if vec($callers_bitmask, $offset+1, 1) ||
vec($callers_bitmask, $Offsets{'all'}+1, 1) ;
@@ -492,6 +492,7 @@
(vec($callers_bitmask, $offset, 1) ||
vec($callers_bitmask, $Offsets{'all'}, 1)) ;
+ require Carp;
Carp::croak($message)
if vec($callers_bitmask, $offset+1, 1) ||
vec($callers_bitmask, $Offsets{'all'}+1, 1) ;
diff -ruN blead/warnings.pl blead.patch/warnings.pl
--- blead/warnings.pl 2004-10-12 18:32:03.000000000 +0200
+++ blead.patch/warnings.pl 2004-10-16 13:07:48.000000000 +0200
@@ -600,14 +600,13 @@
=cut
-use Carp ();
-
KEYWORDS
$All = "" ; vec($All, $Offsets{'all'}, 2) = 3 ;
sub Croaker
{
+ require Carp;
delete $Carp::CarpInternal{'warnings'};
Carp::croak(@_);
}
@@ -781,6 +780,7 @@
my $message = pop ;
my ($callers_bitmask, $offset, $i) = __chk(@_) ;
+ require Carp;
Carp::croak($message)
if vec($callers_bitmask, $offset+1, 1) ||
vec($callers_bitmask, $Offsets{'all'}+1, 1) ;
@@ -800,6 +800,7 @@
(vec($callers_bitmask, $offset, 1) ||
vec($callers_bitmask, $Offsets{'all'}, 1)) ;
+ require Carp;
Carp::croak($message)
if vec($callers_bitmask, $offset+1, 1) ||
vec($callers_bitmask, $Offsets{'all'}+1, 1) ;