#include <libsec.h>
#include <auth.h>
-int debug, auth;
+int debug, auth, dialfile;
char *keyspec = "";
-char *servername, *file, *filex, *ccert;
+char *servername, *file, *filex, *ccert, *dumpcert;
void
usage(void)
{
- fprint(2, "usage: tlsclient [-D] [-a [-k keyspec] ] [-c lib/tls/clientcert] [-t /sys/lib/tls/xxx] [-x /sys/lib/tls/xxx.exclude] [-n servername] dialstring [cmd [args...]]\n");
+ fprint(2, "usage: tlsclient [-D] [-a [-k keyspec] ] [-c clientcert.pem] [-d servercert] [-t /sys/lib/tls/xxx] [-x /sys/lib/tls/xxx.exclude] [-n servername] [-o] dialstring [cmd [args...]]\n");
exits("usage");
}
void
main(int argc, char **argv)
{
- int fd;
+ int fd, dfd;
char *addr;
TLSconn *conn;
Thumbprint *thumb;
+ AuthInfo *ai = nil;
+ fmtinstall('[', encodefmt);
fmtinstall('H', encodefmt);
ARGBEGIN{
case 'c':
ccert = EARGF(usage());
break;
+ case 'd':
+ dumpcert = EARGF(usage());
+ break;
case 'n':
servername = EARGF(usage());
break;
+ case 'o':
+ dialfile = 1;
+ break;
default:
usage();
}ARGEND
sysfatal("specifying -x without -t is useless");
if(file){
- thumb = initThumbprints(file, filex);
+ thumb = initThumbprints(file, filex, "x509");
if(thumb == nil)
sysfatal("initThumbprints: %r");
} else
thumb = nil;
addr = *argv++;
- if((fd = dial(addr, 0, 0, 0)) < 0)
+ if((fd = dialfile? open(addr, ORDWR): dial(addr, 0, 0, 0)) < 0)
sysfatal("dial %s: %r", addr);
conn = (TLSconn*)mallocz(sizeof *conn, 1);
}
if(auth){
- AuthInfo *ai;
-
ai = auth_proxy(fd, auth_getkey, "proto=p9any role=client %s", keyspec);
if(ai == nil)
sysfatal("auth_proxy: %r");
if(fd < 0)
sysfatal("tlsclient: %r");
- if(thumb){
- uchar digest[20];
+ if(dumpcert){
+ if((dfd = create(dumpcert, OWRITE, 0666)) < 0)
+ sysfatal("create: %r");
+ if(conn->cert != nil)
+ write(dfd, conn->cert, conn->certlen);
+ write(dfd, "", 0);
+ close(dfd);
+ }
- if(conn->cert==nil || conn->certlen<=0)
- sysfatal("server did not provide TLS certificate");
- sha1(conn->cert, conn->certlen, digest, nil);
- if(!okThumbprint(digest, thumb))
- sysfatal("server certificate %.*H not recognized", SHA1dlen, digest);
+ if(thumb){
+ if(!okCertificate(conn->cert, conn->certlen, thumb))
+ sysfatal("cert for %s not recognized: %r", servername ? servername : addr);
+ freeThumbprints(thumb);
}
+ free(conn->cert);
+ free(conn->sessionID);
+ free(conn);
+ if(ai != nil)
+ auth_freeAI(ai);
+
if(*argv){
dup(fd, 0);
dup(fd, 1);