Server IP : 85.214.239.14 / Your IP : 3.23.101.241 Web Server : Apache/2.4.62 (Debian) System : Linux h2886529.stratoserver.net 4.9.0 #1 SMP Tue Jan 9 19:45:01 MSK 2024 x86_64 User : www-data ( 33) PHP Version : 7.4.18 Disable Function : pcntl_alarm,pcntl_fork,pcntl_waitpid,pcntl_wait,pcntl_wifexited,pcntl_wifstopped,pcntl_wifsignaled,pcntl_wifcontinued,pcntl_wexitstatus,pcntl_wtermsig,pcntl_wstopsig,pcntl_signal,pcntl_signal_get_handler,pcntl_signal_dispatch,pcntl_get_last_error,pcntl_strerror,pcntl_sigprocmask,pcntl_sigwaitinfo,pcntl_sigtimedwait,pcntl_exec,pcntl_getpriority,pcntl_setpriority,pcntl_async_signals,pcntl_unshare, MySQL : OFF | cURL : OFF | WGET : ON | Perl : ON | Python : ON | Sudo : ON | Pkexec : OFF Directory : /usr/share/perl5/LWP/Protocol/ |
Upload File : |
package LWP::Protocol::https; use strict; our $VERSION = '6.10'; use base qw(LWP::Protocol::http); require Net::HTTPS; sub socket_type { return "https"; } sub _extra_sock_opts { my $self = shift; my %ssl_opts = %{$self->{ua}{ssl_opts} || {}}; if (delete $ssl_opts{verify_hostname}) { $ssl_opts{SSL_verify_mode} ||= 1; $ssl_opts{SSL_verifycn_scheme} = 'www'; } else { if ( $Net::HTTPS::SSL_SOCKET_CLASS eq 'Net::SSL' ) { $ssl_opts{SSL_verifycn_scheme} = ''; } else { $ssl_opts{SSL_verifycn_scheme} = 'none'; } } if ($ssl_opts{SSL_verify_mode}) { unless (exists $ssl_opts{SSL_ca_file} || exists $ssl_opts{SSL_ca_path}) { $ssl_opts{SSL_ca_file} = '/etc/ssl/certs/ca-certificates.crt'; } } $self->{ssl_opts} = \%ssl_opts; return (%ssl_opts, $self->SUPER::_extra_sock_opts); } #------------------------------------------------------------ # _cn_match($common_name, $san_name) # common_name: an IA5String # san_name: subjectAltName # initially we were only concerned with the dNSName # and the 'left-most' only wildcard as noted in # https://tools.ietf.org/html/rfc6125#section-6.4.3 # this method does not match any wildcarding in the # domain name as listed in section-6.4.3.3 # sub _cn_match { my( $me, $common_name, $san_name ) = @_; # /CN has a '*.' prefix # MUST be an FQDN -- fishing? return 0 if( $common_name =~ /^\*\./ ); my $re = q{}; # empty string # turn a leading "*." into a regex if( $san_name =~ /^\*\./ ) { $san_name =~ s/\*//; $re = "[^.]+"; } # quotemeta the rest and match anchored if( $common_name =~ /^$re\Q$san_name\E$/ ) { return 1; } return 0; } #------------------------------------------------------- # _in_san( cn, cert ) # 'cn' of the form /CN=host_to_check ( "Common Name" form ) # 'cert' any object that implements a peer_certificate('subjectAltNames') method # which will return an array of ( type-id, value ) pairings per # http://tools.ietf.org/html/rfc5280#section-4.2.1.6 # if there is no subjectAltNames there is nothing more to do. # currently we have a _cn_match() that will allow for simple compare. sub _in_san { my($me, $cn, $cert) = @_; # we can return early if there are no SAN options. my @sans = $cert->peer_certificate('subjectAltNames'); return unless scalar @sans; (my $common_name = $cn) =~ s/.*=//; # strip off the prefix. # get the ( type-id, value ) pairwise # currently only the basic CN to san_name check while( my ( $type_id, $value ) = splice( @sans, 0, 2 ) ) { return 'ok' if $me->_cn_match($common_name,$value); } return; } sub _check_sock { my($self, $req, $sock) = @_; my $check = $req->header("If-SSL-Cert-Subject"); if (defined $check) { my $cert = $sock->get_peer_certificate || die "Missing SSL certificate"; my $subject = $cert->subject_name; unless ( defined $subject && ( $subject =~ /$check/ ) ) { my $ok = $self->_in_san( $check, $cert); die "Bad SSL certificate subject: '$subject' !~ /$check/" unless $ok; } $req->remove_header("If-SSL-Cert-Subject"); # don't pass it on } } sub _get_sock_info { my $self = shift; $self->SUPER::_get_sock_info(@_); my($res, $sock) = @_; if ($sock->can('get_sslversion') and my $sslversion = $sock->get_sslversion) { $res->header("Client-SSL-Version" => $sslversion); } $res->header("Client-SSL-Cipher" => $sock->get_cipher); my $cert = $sock->get_peer_certificate; if ($cert) { $res->header("Client-SSL-Cert-Subject" => $cert->subject_name); $res->header("Client-SSL-Cert-Issuer" => $cert->issuer_name); } if (!$self->{ssl_opts}{SSL_verify_mode}) { $res->push_header("Client-SSL-Warning" => "Peer certificate not verified"); } elsif (!$self->{ssl_opts}{SSL_verifycn_scheme}) { $res->push_header("Client-SSL-Warning" => "Peer hostname match with certificate not verified"); } $res->header("Client-SSL-Socket-Class" => $Net::HTTPS::SSL_SOCKET_CLASS); } # upgrade plain socket to SSL, used for CONNECT tunnel when proxying https # will only work if the underlying socket class of Net::HTTPS is # IO::Socket::SSL, but code will only be called in this case if ( $Net::HTTPS::SSL_SOCKET_CLASS->can('start_SSL')) { *_upgrade_sock = sub { my ($self,$sock,$url) = @_; $sock = LWP::Protocol::https::Socket->start_SSL( $sock, SSL_verifycn_name => $url->host, SSL_hostname => $url->host, $self->_extra_sock_opts, ); $@ = LWP::Protocol::https::Socket->errstr if ! $sock; return $sock; } } #----------------------------------------------------------- package LWP::Protocol::https::Socket; use base qw(Net::HTTPS LWP::Protocol::http::SocketMethods); 1; __END__ =head1 NAME LWP::Protocol::https - Provide https support for LWP::UserAgent =head1 SYNOPSIS use LWP::UserAgent; $ua = LWP::UserAgent->new(ssl_opts => { verify_hostname => 1 }); $res = $ua->get("https://www.example.com"); # specify a CA path $ua = LWP::UserAgent->new( ssl_opts => { SSL_ca_path => '/etc/ssl/certs', verify_hostname => 1, } ); =head1 DESCRIPTION The LWP::Protocol::https module provides support for using https schemed URLs with LWP. This module is a plug-in to the LWP protocol handling, so you don't use it directly. Once the module is installed LWP is able to access sites using HTTP over SSL/TLS. If hostname verification is requested by LWP::UserAgent's C<ssl_opts>, and neither C<SSL_ca_file> nor C<SSL_ca_path> is set, then C<SSL_ca_file> is implied to be the one provided by L<Mozilla::CA>. If the Mozilla::CA module isn't available SSL requests will fail. Either install this module, set up an alternative C<SSL_ca_file> or disable hostname verification. This module used to be bundled with the libwww-perl, but it was unbundled in v6.02 in order to be able to declare its dependencies properly for the CPAN tool-chain. Applications that need https support can just declare their dependency on LWP::Protocol::https and will no longer need to know what underlying modules to install. =head1 SEE ALSO L<IO::Socket::SSL>, L<Crypt::SSLeay>, L<Mozilla::CA> =head1 COPYRIGHT & LICENSE Copyright (c) 1997-2011 Gisle Aas. This library is free software; you can redistribute it and/or modify it under the same terms as Perl itself. =cut