Reputation: 31
I have a POP3 login test script which uses IO::Socket::INET
to read and write to the opened socket on TCP:110. This is what I'm used to: -
my $sock = IO::Socket::INET->new(
PeerAddr => "$h:$port",
Proto => "tcp",
) or die "$!\n";
However, I also need to test the same POP3 conversation through SSL-secured POP3S (TCP:995).
I've found that I can use the following on the command-line, which gets me a similar state as "telnet hostname 110", but encrypted: -
openssl s_client -crlf -connect hostname:995
I am hoping to find a way that I can set up some sort of read/write FileHandle or socket on the openssl command, which I can read til it's empty, then write in the required POP3 commands into, then read the responses, and so on...
I feel like because I can see it on screen, it's close enough to grab, but I don't quite know my way around perl well enough, to "get it" and move on!
Unfortunately, the server this script will be run on, is not able to have more perl modules installed, which might have been an obvious solution.
UPDATE
Thanks to @ventatsu for the inspiration, I am now using IPC::Open2
like this: -
my ($sslread,$sslwrite);
my $ssl_fh = open2(
$sslread,
$sslwrite,
"openssl s_client -crlf -connect mail.example.com:995"
) or die "$!\n";
while (<$sslread>) {
print;
if (/^\+OK.*$/) {
## Try to log in
print $sslwrite "USER $u\r\n";
print "USER $u\n";
while (<$sslread>) {
print;
if (/^\+OK.*$/) {
## Keep going
print $sslwrite "PASS $p\r\n";
print "PASS $p\n";
while (<$sslread>) {
print;
}
}
}
print $sslwrite "QUIT";
print "QUIT\n";
}
}
waitpid( $ssl_fh, 0 );
my $child_exit_status = $? >> 8;
My non-SSL test scrip works thusly: -
Testing pop3 on mail.example.com:110
+OK The Microsoft Exchange POP3 service is ready.
USER [email protected]
+OK
PASS Abcd3fGh
+OK User successfully logged on.
The credentials work OK when I run the POP3 commands in an interactive SSL session on the CLI like this: -
openssl s_client -crlf -connect mail.example.com:995
<snip out the SSL bumph />
+OK The Microsoft Exchange POP3 service is ready.
USER [email protected]
+OK
PASS Abcd3fGh
+OK User successfully logged on.
But my SSL test script only almost works thusly: -
Testing pop3s on mail.example.com:995
<snip out the SSL bumph />
+OK The Microsoft Exchange POP3 service is ready.
USER [email protected]
+OK
PASS Abcd3fGh
-ERR Logon failure: unknown user name or bad password.
What am I doing wrong?
Upvotes: 3
Views: 203
Reputation: 3635
You can use IPC::Open2
to attache two file handles, one to the input and one to the output of a program. It may be closer to what you really want to use IO::Socket::SSL
, which functions like IO::Socket::INET
but encrypted.
Update:
My best guess is that your doubling up \r
characters. According to the man page for s_client
-crlf
converts line feeds into carriage return + line feed. An when you print to the $sslwrite
handle you are sending "\r\n"
. I think the result would be that the server would receive "\r\r\n" at the end of each command. You probably want to drop the -crlf
from the openssl
command in your program.
Upvotes: 1