Filter::decrypt#
A sample decrypting source filter: the source after use Filter::decrypt is XOR-ed with “Perl” as the compiler reads it.
Synopsis#
use Filter::decrypt;
The rest of the file is the output of the dist’s decrypt/encrypt script: the two bytes 0xff 0x00, then the source, each block of four bytes XOR-ed with “Perl”.
How it works#
import installs a source filter. On its first read it checks the two-byte header (“truncated file”, “bad encryption format”) and that no filter was added on the use line after it (“too many filters”); then it reads four bytes at a time and serves the decrypted text by the line or the block, as the compiler asks. import dies “debugger disabled” under perl -d, and loading the module dies “Aborting, Compiler detected” once the compiler backend (B) is loaded.
The module is a template for a real decryption filter, not a protection: the decrypted source passes through memory, and B::Deparse can print what it compiled to.
This is a native implementation of decrypt.xs of Filter 1.65 as the dist builds it (-DBYPASS: no refusal of a dynamically linked module or of a perl built with -DDEBUGGING); its Filter/decrypt.pm is used unchanged.
Differences from upstream#
One, where perl 5.44 with decrypt.xs crashes (t/81-xs-native/Filter/150-or-better.t):
Filter::decrypt->importwhile nothing is being compiled installs nothing and leaves memory alone. decrypt.xs stores the filter’s state in the slots of a handle the tokenizer never made, past the end of the string it allocated: it overwrites neighbouring variables, and perl5 can segfault.