CA.pl revision 160814
1142425Snectar#!/usr/bin/perl 255714Skris# 355714Skris# CA - wrapper around ca to make it easier to use ... basically ca requires 455714Skris# some setup stuff to be done before you can use it and this makes 555714Skris# things easier between now and when Eric is convinced to fix it :-) 655714Skris# 755714Skris# CA -newca ... will setup the right stuff 8109998Smarkm# CA -newreq[-nodes] ... will generate a certificate request 955714Skris# CA -sign ... will sign the generated request and output 1055714Skris# 1155714Skris# At the end of that grab newreq.pem and newcert.pem (one has the key 1255714Skris# and the other the certificate) and cat them together and that is what 1355714Skris# you want/need ... I'll make even this a little cleaner later. 1455714Skris# 1555714Skris# 1655714Skris# 12-Jan-96 tjh Added more things ... including CA -signcert which 1755714Skris# converts a certificate to a request and then signs it. 1855714Skris# 10-Jan-96 eay Fixed a few more bugs and added the SSLEAY_CONFIG 1955714Skris# environment variable so this can be driven from 2055714Skris# a script. 2155714Skris# 25-Jul-96 eay Cleaned up filenames some more. 2255714Skris# 11-Jun-96 eay Fixed a few filename missmatches. 2355714Skris# 03-May-96 eay Modified to use 'ssleay cmd' instead of 'cmd'. 2455714Skris# 18-Apr-96 tjh Original hacking 2555714Skris# 2655714Skris# Tim Hudson 2755714Skris# tjh@cryptsoft.com 2855714Skris# 2955714Skris 3055714Skris# 27-Apr-98 snh Translation into perl, fix existing CA bug. 3155714Skris# 3255714Skris# 3355714Skris# Steve Henson 3455714Skris# shenson@bigfoot.com 3555714Skris 3655714Skris# default openssl.cnf file has setup as per the following 3755714Skris# demoCA ... where everything is stored 3855714Skris 39160814Ssimonmy $openssl; 40160814Ssimonif(defined $ENV{OPENSSL}) { 41160814Ssimon $openssl = $ENV{OPENSSL}; 42160814Ssimon} else { 43160814Ssimon $openssl = "openssl"; 44160814Ssimon $ENV{OPENSSL} = $openssl; 45160814Ssimon} 46160814Ssimon 4768651Skris$SSLEAY_CONFIG=$ENV{"SSLEAY_CONFIG"}; 48160814Ssimon$DAYS="-days 365"; # 1 year 49160814Ssimon$CADAYS="-days 1095"; # 3 years 50160814Ssimon$REQ="$openssl req $SSLEAY_CONFIG"; 51160814Ssimon$CA="$openssl ca $SSLEAY_CONFIG"; 52160814Ssimon$VERIFY="$openssl verify"; 53160814Ssimon$X509="$openssl x509"; 54160814Ssimon$PKCS12="$openssl pkcs12"; 5555714Skris 5655714Skris$CATOP="./demoCA"; 5755714Skris$CAKEY="cakey.pem"; 58160814Ssimon$CAREQ="careq.pem"; 5955714Skris$CACERT="cacert.pem"; 6055714Skris 6155714Skris$DIRMODE = 0777; 6255714Skris 6355714Skris$RET = 0; 6455714Skris 6555714Skrisforeach (@ARGV) { 6655714Skris if ( /^(-\?|-h|-help)$/ ) { 67109998Smarkm print STDERR "usage: CA -newcert|-newreq|-newreq-nodes|-newca|-sign|-verify\n"; 6855714Skris exit 0; 6955714Skris } elsif (/^-newcert$/) { 7055714Skris # create a certificate 71160814Ssimon system ("$REQ -new -x509 -keyout newkey.pem -out newcert.pem $DAYS"); 7255714Skris $RET=$?; 73160814Ssimon print "Certificate is in newcert.pem, private key is in newkey.pem\n" 7455714Skris } elsif (/^-newreq$/) { 7555714Skris # create a certificate request 76160814Ssimon system ("$REQ -new -keyout newkey.pem -out newreq.pem $DAYS"); 7755714Skris $RET=$?; 78160814Ssimon print "Request is in newreq.pem, private key is in newkey.pem\n"; 79109998Smarkm } elsif (/^-newreq-nodes$/) { 80109998Smarkm # create a certificate request 81160814Ssimon system ("$REQ -new -nodes -keyout newkey.pem -out newreq.pem $DAYS"); 82109998Smarkm $RET=$?; 83160814Ssimon print "Request is in newreq.pem, private key is in newkey.pem\n"; 8455714Skris } elsif (/^-newca$/) { 8559191Skris # if explicitly asked for or it doesn't exist then setup the 8655714Skris # directory structure that Eric likes to manage things 8755714Skris $NEW="1"; 8855714Skris if ( "$NEW" || ! -f "${CATOP}/serial" ) { 8955714Skris # create the directory hierarchy 9055714Skris mkdir $CATOP, $DIRMODE; 9155714Skris mkdir "${CATOP}/certs", $DIRMODE; 9255714Skris mkdir "${CATOP}/crl", $DIRMODE ; 9355714Skris mkdir "${CATOP}/newcerts", $DIRMODE; 9455714Skris mkdir "${CATOP}/private", $DIRMODE; 9555714Skris open OUT, ">${CATOP}/index.txt"; 9655714Skris close OUT; 97160814Ssimon open OUT, ">${CATOP}/crlnumber"; 98160814Ssimon print OUT "01\n"; 99160814Ssimon close OUT; 10055714Skris } 10155714Skris if ( ! -f "${CATOP}/private/$CAKEY" ) { 10255714Skris print "CA certificate filename (or enter to create)\n"; 10355714Skris $FILE = <STDIN>; 10455714Skris 10555714Skris chop $FILE; 10655714Skris 10755714Skris # ask user for existing CA certificate 10855714Skris if ($FILE) { 10955714Skris cp_pem($FILE,"${CATOP}/private/$CAKEY", "PRIVATE"); 11055714Skris cp_pem($FILE,"${CATOP}/$CACERT", "CERTIFICATE"); 11155714Skris $RET=$?; 11255714Skris } else { 11355714Skris print "Making CA certificate ...\n"; 114160814Ssimon system ("$REQ -new -keyout " . 115160814Ssimon "${CATOP}/private/$CAKEY -out ${CATOP}/$CAREQ"); 116160814Ssimon system ("$CA -create_serial " . 117160814Ssimon "-out ${CATOP}/$CACERT $CADAYS -batch " . 118160814Ssimon "-keyfile ${CATOP}/private/$CAKEY -selfsign " . 119160814Ssimon "-extensions v3_ca " . 120160814Ssimon "-infiles ${CATOP}/$CAREQ "); 12155714Skris $RET=$?; 12255714Skris } 12355714Skris } 12459191Skris } elsif (/^-pkcs12$/) { 12559191Skris my $cname = $ARGV[1]; 12659191Skris $cname = "My Certificate" unless defined $cname; 127160814Ssimon system ("$PKCS12 -in newcert.pem -inkey newkey.pem " . 12859191Skris "-certfile ${CATOP}/$CACERT -out newcert.p12 " . 12959191Skris "-export -name \"$cname\""); 13059191Skris $RET=$?; 131160814Ssimon print "PKCS #12 file is in newcert.p12\n"; 13259191Skris exit $RET; 13355714Skris } elsif (/^-xsign$/) { 13455714Skris system ("$CA -policy policy_anything -infiles newreq.pem"); 13555714Skris $RET=$?; 13655714Skris } elsif (/^(-sign|-signreq)$/) { 13755714Skris system ("$CA -policy policy_anything -out newcert.pem " . 13855714Skris "-infiles newreq.pem"); 13955714Skris $RET=$?; 14055714Skris print "Signed certificate is in newcert.pem\n"; 14168651Skris } elsif (/^(-signCA)$/) { 14268651Skris system ("$CA -policy policy_anything -out newcert.pem " . 14368651Skris "-extensions v3_ca -infiles newreq.pem"); 14468651Skris $RET=$?; 14568651Skris print "Signed CA certificate is in newcert.pem\n"; 14655714Skris } elsif (/^-signcert$/) { 14755714Skris system ("$X509 -x509toreq -in newreq.pem -signkey newreq.pem " . 14855714Skris "-out tmp.pem"); 14955714Skris system ("$CA -policy policy_anything -out newcert.pem " . 15055714Skris "-infiles tmp.pem"); 15155714Skris $RET = $?; 15255714Skris print "Signed certificate is in newcert.pem\n"; 15355714Skris } elsif (/^-verify$/) { 15455714Skris if (shift) { 15555714Skris foreach $j (@ARGV) { 15655714Skris system ("$VERIFY -CAfile $CATOP/$CACERT $j"); 15755714Skris $RET=$? if ($? != 0); 15855714Skris } 15955714Skris exit $RET; 16055714Skris } else { 16155714Skris system ("$VERIFY -CAfile $CATOP/$CACERT newcert.pem"); 16255714Skris $RET=$?; 16355714Skris exit 0; 16455714Skris } 16555714Skris } else { 16655714Skris print STDERR "Unknown arg $_\n"; 167109998Smarkm print STDERR "usage: CA -newcert|-newreq|-newreq-nodes|-newca|-sign|-verify\n"; 16855714Skris exit 1; 16955714Skris } 17055714Skris} 17155714Skris 17255714Skrisexit $RET; 17355714Skris 17455714Skrissub cp_pem { 17555714Skrismy ($infile, $outfile, $bound) = @_; 17655714Skrisopen IN, $infile; 17755714Skrisopen OUT, ">$outfile"; 17855714Skrismy $flag = 0; 17955714Skriswhile (<IN>) { 18055714Skris $flag = 1 if (/^-----BEGIN.*$bound/) ; 18155714Skris print OUT $_ if ($flag); 18255714Skris if (/^-----END.*$bound/) { 18355714Skris close IN; 18455714Skris close OUT; 18555714Skris return; 18655714Skris } 18755714Skris} 18855714Skris} 18955714Skris 190