| IO::Socket::SSL::Intercept(3) | User Contributed Perl Documentation | IO::Socket::SSL::Intercept(3) |
IO::Socket::SSL::Intercept -- SSL interception (man in the middle)
use IO::Socket::SSL::Intercept;
# create interceptor with proxy certificates
my $mitm = IO::Socket::SSL::Intercept->new(
proxy_cert_file => 'proxy_cert.pem',
proxy_key_file => 'proxy_key.pem',
...
);
my $listen = IO::Socket::INET->new( LocalAddr => .., Listen => .. );
while (1) {
# TCP accept new client
my $client = $listen->accept or next;
# SSL connect to server
my $server = IO::Socket::SSL->new(
PeerAddr => ..,
SSL_verify_mode => ...,
...
) or die "ssl connect failed: $!,$SSL_ERROR";
# clone server certificate
my ($cert,$key) = $mitm->clone_cert( $server->peer_certificate );
# and upgrade client side to SSL with cloned certificate
IO::Socket::SSL->start_SSL($client,
SSL_server => 1,
SSL_cert => $cert,
SSL_key => $key
) or die "upgrade failed: $SSL_ERROR";
# now transfer data between $client and $server and analyze
# the unencrypted data
...
}
This module provides functionality to clone certificates and sign them with a proxy certificate, thus making it easy to intercept SSL connections (man in the middle). It also manages a cache of the generated certificates.
Intercepting SSL connections is useful for analyzing encrypted traffic for security reasons or for testing. It does not break the end-to-end security of SSL, e.g. a properly written client will notice the interception unless you explicitly configure the client to trust your interceptor. Intercepting SSL works the following way:
Using openssl such a proxy CA certificate and private key can be created with:
openssl genrsa -out proxy_key.pem 1024
openssl req -new -x509 -extensions v3_ca -key proxy_key.pem -out proxy_cert.pem
# export as PKCS12 for import into browser
openssl pkcs12 -export -in proxy_cert.pem -inkey proxy_key.pem -out proxy_cert.p12
IO::Socket::SSL::Intercept helps creating the cloned certificate with the following methods:
If the argument is a hash it will store for each generated certificate a hash reference with "cert" and "atime" in the hash, where "atime" is the time of last access (to expire unused entries) and "cert" is the certificate. Please note, that the certificate is in Net::SSLeays internal X509 format and can thus not be simply dumped and restored. The key for the hash is an "ident" either given to "clone_cert" or generated from the original certificate.
If the argument is a subroutine it will be called as "$cache->(ident,sub)". This call should return either an existing (cached) "(cert,key)" or call "sub" without arguments to create a new "(cert,key)", store it and return it. If called with "$cache->('type')" the function should just return 1 to signal that it supports the current type of cache. If it reutrns nothing instead the older cache interface is assumed for compatibility reasons.
Steffen Ullrich
| 2020-02-14 | perl v5.34.0 |