| 179 |
rodolico |
1 |
#! /usr/bin/env perl
|
|
|
2 |
|
| 182 |
rodolico |
3 |
# Creates a private key, Signing Request, and signed certificate file
|
|
|
4 |
# for a target service. Tested on Apache2
|
|
|
5 |
#
|
|
|
6 |
# Run with the primary domain name as the first parameter, optionally
|
|
|
7 |
# followed by one or more alias names. The certificate will be valid
|
|
|
8 |
# for all names passed on command line
|
|
|
9 |
#
|
|
|
10 |
# CA (key and crt) are in the variables $caCRT and $caKey and new files
|
|
|
11 |
# are placed in $serverCertDir and named based on the first parameter
|
|
|
12 |
#
|
|
|
13 |
# An ext file is created, if it doesn't exist, from $sslConfig and
|
|
|
14 |
# used to set defaults for the actual csr and crt file creation
|
|
|
15 |
|
| 179 |
rodolico |
16 |
use strict;
|
|
|
17 |
use warnings;
|
|
|
18 |
|
| 182 |
rodolico |
19 |
use FindBin;
|
|
|
20 |
use File::Spec;
|
|
|
21 |
use Cwd 'abs_path';
|
|
|
22 |
use File::Basename;
|
| 179 |
rodolico |
23 |
|
| 182 |
rodolico |
24 |
my $binDir = dirname( abs_path( __FILE__ ) ) . '/';
|
|
|
25 |
my $config = $binDir . "makeCert.conf";
|
|
|
26 |
my $sslConfig = $binDir . 'openssl.cnf';
|
|
|
27 |
|
|
|
28 |
die "$config\n";
|
|
|
29 |
|
|
|
30 |
my $configFile; # prototype for the domain specific config file
|
|
|
31 |
my $caCRT; # location of the CA crt file
|
|
|
32 |
my $caKey; # location of the CA Key file
|
|
|
33 |
my $serverCertDir; # where to put the server certs
|
|
|
34 |
my $certDays; # number of days a certificate is valid for
|
|
|
35 |
my $caDays; # number of days a CA is good for (not used in this script)
|
|
|
36 |
|
|
|
37 |
|
|
|
38 |
die "Config File $config not found\n" unless -f $config;
|
|
|
39 |
die "openssl config file $sslConfig not found\n" unless -f $sslConfig;
|
|
|
40 |
|
|
|
41 |
eval `cat $config`;
|
|
|
42 |
|
|
|
43 |
die "Can not find CA Cert $caCRT\n" unless -f $caCRT;
|
|
|
44 |
die "Can not find CA Key $caKey\n" unless -f $caKey;
|
|
|
45 |
|
|
|
46 |
|
| 179 |
rodolico |
47 |
# they must pass in at least a domain. All other cli params taken as aliases
|
|
|
48 |
# this will also be the filename for each file created, ie $DOMAIN.extension
|
|
|
49 |
my $DOMAIN = shift;
|
|
|
50 |
die "Usage: $0 domain [alias alias]\n" unless $DOMAIN;
|
|
|
51 |
|
|
|
52 |
# if the domain doesn't have an ext file, create it
|
|
|
53 |
if ( ! -f "$DOMAIN.ext" ) {
|
| 182 |
rodolico |
54 |
my @newLines;
|
| 179 |
rodolico |
55 |
# read in the default config file
|
|
|
56 |
open CNF, "<$configFile" or die "Could not read $configFile: $!\n";
|
|
|
57 |
my @config = <CNF>;
|
|
|
58 |
close CNF;
|
|
|
59 |
# remove all line endings
|
|
|
60 |
chomp @config;
|
| 182 |
rodolico |
61 |
my $line = 0;
|
|
|
62 |
my $inAltNames = 0;
|
|
|
63 |
for my $line ( @config ) {
|
|
|
64 |
if ( $line =~ m/^\[\s*alt_names\s*\]/ ) {
|
|
|
65 |
$inAltNames = 1;
|
|
|
66 |
next;
|
|
|
67 |
}
|
|
|
68 |
if ( $inAltNames ) {
|
|
|
69 |
next if $line !~ m/^\[/;
|
|
|
70 |
$inAltNames = 0;
|
|
|
71 |
}
|
|
|
72 |
push @newLines, $line;
|
|
|
73 |
}
|
|
|
74 |
# start the alt_names section
|
|
|
75 |
push @newLines, '[ alt_names ]';
|
| 179 |
rodolico |
76 |
# the first DNS entry is the actual domain.
|
| 182 |
rodolico |
77 |
push @newLines, "DNS.1=$DOMAIN";
|
| 179 |
rodolico |
78 |
my $dns = 2;
|
|
|
79 |
# read in all aliases and add them as a separate DNS entry
|
|
|
80 |
while ( my $alias = shift ) {
|
| 182 |
rodolico |
81 |
push @newLines, "DNS.$dns=$alias";
|
| 179 |
rodolico |
82 |
$dns++;
|
|
|
83 |
}
|
|
|
84 |
# print the ext file back out
|
| 182 |
rodolico |
85 |
open CNF, ">$serverCertDir$DOMAIN.ext" or die "Could not write to $serverCertDir$DOMAIN.ext: $!\n";
|
|
|
86 |
print CNF join( "\n", @newLines ) . "\n";
|
| 179 |
rodolico |
87 |
close CNF;
|
|
|
88 |
}
|
|
|
89 |
|
|
|
90 |
# Create an rsa key into $DOMAIN.key
|
| 182 |
rodolico |
91 |
`openssl genpkey -algorithm RSA -out $serverCertDir$DOMAIN.key -pkeyopt rsa_keygen_bits:2048`;
|
| 179 |
rodolico |
92 |
# create a signing request, using $DOMAIN.ext for all the DN stuff saved in $DOMAIN.csr
|
| 182 |
rodolico |
93 |
`openssl req -config openssl.cnf -key $serverCertDir$DOMAIN.key -new -out $serverCertDir$DOMAIN.csr`;
|
| 179 |
rodolico |
94 |
# generate the actual crt file as $DOMAIN.crt, using the csr and ext file
|
| 182 |
rodolico |
95 |
`openssl x509 -req -in $serverCertDir$DOMAIN.csr -CA $caCRT -CAkey $caKey -CAcreateserial -out $serverCertDir$DOMAIN.crt -days $certDays -extensions req_ext -extfile $serverCertDir$DOMAIN.ext`;
|
| 179 |
rodolico |
96 |
|
| 182 |
rodolico |
97 |
print "key and crt created. Use the following command to view the certificate\nopenssl x509 -in $DOMAIN.crt -text -noout\n";
|
| 179 |
rodolico |
98 |
1;
|