Skip Menu |

This queue is for tickets about the Crypt-X509-CRL CPAN distribution.

Report information
The Basics
Id: 129362
Status: new
Priority: 0/
Queue: Crypt-X509-CRL

People
Owner: Nobody in particular
Requestors: public [...] wernig.net
Cc:
AdminCc:

Bug Information
Severity: (no value)
Broken in: (no value)
Fixed in: (no value)



Subject: $parser is cached globally, so $self->{"_error"} is never reset, preventing loops; with patch
Date: Mon, 29 Apr 2019 20:02:36 +0200
To: bug-Crypt-X509-CRL [...] rt.cpan.org
From: Markus Wernig <public [...] wernig.net>
Hi all Using version 0.1 of the module on Gentoo Linux. The module defines (line numbers prepended): 18: my $error = undef; In the constructor it checks if the parser is already set and uses the old one if present: 147: if ( not defined ( $parser ) ) { 148: $parser = _init(); 149: } It appears that the $parser from Convert::ASN1 that is used here does not reset its internal error state when being called a second time. So while this seems a good idea wrt performance, it breaks whenever looping over multiple CRLs, one of which fails to parse. The solution is to not check for a cached $parser, just call _init every time (remove lines 147 and 149 in the constructor quoted above). This is in fact a duplicate of https://rt.cpan.org/Public/Bug/Display.html?id=118487, which has gone unanswered for almost 3 years. Here's some sample code to illustrate the problem: #!/usr/bin/perl use strict; use warnings; use Crypt::X509::CRL; use MIME::Base64; my $crldir = "/path/to/dir/containing/crl/files"; # # Note: # Of the files in $crldir, one is a corrupt CRL that cannot be parsed # if( $crldir && -d "$crldir" && opendir (CRLDIR, "$crldir")) { while(my $file = readdir CRLDIR) { next if($file =~ /^\./); next unless($file =~ /\.(pem|crl|der)$/i); print("Loading CRL from $crldir/$file\n"); if(open FHC, "<$crldir/$file") { my $crl; my $fmt = "DER"; while(<FHC>) { if($_ =~ /(BEGIN|END).*CRL/) { # remove PEM header/trailer $fmt = "PEM"; next; } $crl .= $_; } close FHC; if($fmt eq "PEM") { $crl = decode_base64($crl); } my $crlobj = undef; if($crlobj = Crypt::X509::CRL->new(crl => $crl)) { if($crlobj->error()) { # error() is now always set for each CRL after the corrupt # one, even if the CRL is OK print("Failed to parse CRL from " . $crlobj->issuer_cn() .": " . $crlobj->error()); } else { print("Parsed CRL from " . $crlobj->issuer_cn()); } } else { print("Failed to parse CRL $crldir/$file\n"); } } else { print("Failed to open CRL $crldir/$file\n"); } } } Here's the patch to fix this problem: --- /usr/local/lib64/perl5/5.24.1/Crypt/X509/CRL.pm 2019-04-29 19:59:41.689237937 +0200 +++ CRL.pm 2019-04-29 20:00:14.817439892 +0200 @@ -144,9 +144,7 @@ sub new { my ( $class , %args ) = @_; - if ( not defined ( $parser ) ) { - $parser = _init(); - } + $parser = _init(); my $self = $parser->decode( $args{'crl'} ); Thanks for looking into it.