Skip site navigation (1)Skip section navigation (2)

FreeBSD Manual Pages


home | help
Lexical::SealRequireHiUser3Contributed Perl DocumeLexical::SealRequireHints(3)

       Lexical::SealRequireHints - prevent leakage of lexical hints

	       use Lexical::SealRequireHints;

       This module works around	two historical bugs in Perl's handling of the
       "%^H" (lexical hints) variable.	One bug	causes lexical state in	one
       file to leak into another that is "require"d/"use"d from	it.  This bug,
       [perl #68590], was present from Perl 5.6	up to Perl 5.10, fixed in Perl
       5.11.0.	The second bug causes lexical state (normally a	blank "%^H"
       once the	first bug is fixed) to leak outwards from "", if	it is
       automatically loaded during Unicode regular expression matching,	into
       whatever	source is compiling at the time	of the regexp match.  This
       bug, [perl #73174], was present from Perl 5.8.7 up to Perl 5.11.5,
       fixed in	Perl 5.12.0.

       Both of these bugs seriously damage the usability of any	module relying
       on "%^H"	for lexical scoping, on	the affected Perl versions.  It	is in
       practice	essential to work around these bugs when using such modules.
       On versions of Perl that	require	such a workaround, this	module
       globally	changes	the behaviour of "require", including "use" and	the
       implicit	"require" performed in Unicode regular expression matching, so
       that it no longer exhibits these	bugs.

       The workaround supplied by this module takes effect the first time its
       "import"	method is called.  Typically this will be done by means	of a
       "use" statement.	 This should be	done as	early as possible, because it
       only affects "require"/"use" statements that are	compiled after the
       workaround goes into effect.  For "use" statements, and "require"
       statements that are executed immediately	and only once, it suffices to
       invoke the workaround when loading the first module that	will set up
       vulnerable lexical state.  Delayed-action "require" statements,
       however,	are more troublesome, and can require the workaround to	be
       loaded much earlier.  Ultimately, an affected Perl program may need to
       load the	workaround as very nearly its first action.  Invoking this
       module multiple times, from multiple modules, is	not a problem: the
       workaround is only applied once,	and applies to everything subsequently

       This module is implemented in XS, with a	pure Perl backup version for
       systems that can't handle XS modules.  The XS version has a better
       chance of playing nicely	with other modules that	modify "require"
       handling.  The pure Perl	version	can't work at all on some Perl
       versions; users of those	versions must use the XS.  On all Perl
       versions	suffering the underlying hint leakage bug, pure	Perl hooking
       of "require" breaks the use of "require"	without	an explicit parameter
       (implicitly using $_).

       The history of the "%^H"	bugs is	complex.  Here is a chronological
       statement of the	relevant changes.

       Perl 5.6.0
	   "%^H" introduced.  It exists	only as	a hash at compile time.	 It is
	   not localised by "require", so lexical hints	leak into every	module
	   loaded, which is bug	[perl #68590].

	   The "CORE::GLOBAL" mechanism	doesn't	work cleanly for "require",
	   because overriding "require"	loses the necessary special parsing of
	   bareword arguments to it.  As a result, pure	Perl code can't
	   properly globally affect the	behaviour of "require".	 Pure Perl
	   code	can localise "%^H" itself for any particular "require"
	   invocation, but a global fix	is only	possible through XS.

       Perl 5.7.2
	   The "CORE::GLOBAL" mechanism	now works cleanly for "require", so
	   pure	Perl code can globally affect the behaviour of "require" to
	   achieve a global fix	for the	bug.

       Perl 5.8.7
	   When	"" is automatically loaded during Unicode regular
	   expression matching,	"%^H" now leaks	outward	from it	into whatever
	   source is compiling at the time of the regexp match,	which is bug
	   [perl #73174].  It often goes unnoticed, because [perl #68590]
	   makes "%^H" leak into "" which then doesn't modify it, so
	   what	leaks out tends	to be identical	to what	leaked in.  If [perl
	   #68590] is worked around, however, "%^H" tends to be	(correctly)
	   blank inside	"", and this bug	therefore blanks it for	the
	   outer module.

       Perl 5.9.4
	   "%^H" now exists in two forms.  In addition to the relatively
	   ordinary hash that is modified during compilation, the value	that
	   it had at each point	in compilation is recorded in the compiled op
	   tree, for later examination at runtime.  It is in a special
	   representation-sharing format, and writes to	"%^H" are meant	to be
	   performed on	both forms.  "require" does not	localise the runtime
	   form	of "%^H" (and still doesn't localise the compile-time form).

	   A couple of special "%^H" entries are erroneously written only to
	   the runtime form.

	   Pure	Perl code, although it can localise the	compile-time "%^H" by
	   normal means, can't adequately localise the runtime "%^H", except
	   by using a string eval stack	frame.	This makes a satisfactory
	   global fix for the leakage bug impossible in	pure Perl.

       Perl 5.10.1
	   "require" now properly localises the	runtime	form of	"%^H", but
	   still not the compile-time form.

	   A global fix	is once	again possible in pure Perl, because the fix
	   only	needs to localise the compile-time form.

       Perl 5.11.0
	   "require" now properly localises both forms of "%^H", fixing	[perl
	   #68590].  This makes	[perl #73174] apparent without any workaround
	   for [perl #68590].

	   The special "%^H" entries are now correctly written to both forms
	   of the hash.

       Perl 5.12.0
	   The automatic loading of "" during Unicode regular
	   expression matching now properly restores "%^H", fixing [perl

       The operation of	this module depends on influencing the compilation of
       "require".  As a	result,	it cannot prevent lexical state	leakage
       through a "require" statement that was compiled before this module was
       invoked.	 Where problems	occur, this module must	be invoked earlier.

       On all Perl versions that need a	fix for	the lexical hint leakage bug,
       the pure	Perl implementation of this module unavoidably breaks the use
       of "require" without an explicit	parameter (implicitly using $_).  This
       is due to another bug in	the Perl core, fixed in	Perl 5.15.5, and is
       inherent	to the mechanism by which pure Perl code can hook "require".
       The use of implicit $_ with "require" is	rare, so although this state
       of affairs is faulty it will actually work for most programs.  Perl
       versions	5.12.0 and greater, despite having the "require" hooking bug,
       don't actually exhibit a	problem	with the pure Perl version of this
       module, because with the	lexical	hint leakage bug fixed there is	no
       need for	this module to hook "require".


       Andrew Main (Zefram) <>

       Copyright (C) 2009, 2010, 2011, 2012, 2015, 2016, 2017 Andrew Main
       (Zefram)	<>

       This module is free software; you can redistribute it and/or modify it
       under the same terms as Perl itself.

perl v5.32.1			  2022-03-26	  Lexical::SealRequireHints(3)


Want to link to this manual page? Use this URL:

home | help