#!/bin/bash
export SCRIPT_PATH=$( cd "$(dirname "${BASH_SOURCE}")" ; pwd -P )
DEFAULT_DOMAIN='reverse.com'
DEFAULT_IP='123.123.123.123'
# create certificates
# $ make tls-server example.com ssl
# $ make tls-server sub.example.com ssl
# creates example.com.ssl.tls-server.crt:
# - request created with example.com.tls-server.cnf
# - signed by example.com.ca-tls.crt using config example.com.ca-tls.cnf
check_result()
{
if [ $1 -ne 0 ]; then
echo -e "\e[91m Error\e[39m $2"
exit $1
fi
echo -e "\e[92m +\e[39m"
}
warn_result()
{
if [ $1 -ne 0 ]; then
echo -e "\e[93m Warning\e[39m $2"
fi
}
check_prompt()
{
if [ $1 -ne 0 ]; then
warn_result "$@"
read -p 'Would you like to continue [y/n]: ' answer
if [ "$answer" != 'y' ] && [ "$answer" != 'Y' ]; then
echo 'Goodbye'
exit 1
fi
fi
}
domainPath()
{
local domain=$1
local lookup="$SCRIPT_PATH/$DEFAULT_DOMAIN/lookup"
local path=$lookup/$domain
if [ -e $path ]; then
echo $(head -n 1 $path)
fi
}
# type: for avail crt-types see crt-*/etc/*.cnf {email|tls-client|tls-server|code-signing}
# domain: a valid domain, stored in /lookup
# fileName: a unique filename. If the file exists, the last version will be revoked as affiliationChanged
#
# files will be stored in ./crt-*/$domain.$filename.$type.ext
# ---
# make tls-server example.com ssl
# ---
make()
{
local type=$1
local domain=$2
local fileName=$3
local path=$(domainPath $domain)
if [ -z $path ]; then
check_result 1 "domain $domain not found in $SCRIPT_PATH/$DEFAULT_DOMAIN"
fi
local baseType
case "$type" in
email)
baseType='email'
echo "create $baseType/$type"
;;
tls-server|tls-client)
baseType='tls'
echo "create $baseType/$type"
;;
code-signing)
baseType='software'
echo "create $baseType/$type"
;;
*)
check_result 1 "invalid request type $type; {email|tls-client|tls-server|code-signing}"
exit 1
esac
local lvl=$(grep -o '/intermediate/' <<< "$path" | wc -l)
case "$lvl" in
0)
export CA_0_SCRIPT_PATH="$path"
;;
1)
export CA_1_SCRIPT_PATH="$path"
;;
2)
export CA_2_SCRIPT_PATH="$path"
;;
esac
local caCrl="$path/ca-$baseType/db/$domain.ca-$baseType.crl"
local caCnf="$path/ca-$baseType/etc/$domain.ca-$baseType.cnf"
local caPwd="$path/ca-$baseType/private/$domain.ca-$baseType.pwd"
local csrCnf="$path/crt-$baseType/etc/$domain.$type.cnf"
local key="$path/crt-$baseType/private/$domain.$fileName.$type.key"
local csr="$path/crt-$baseType/$domain.$fileName.$type.csr"
local crt="$path/crt-$baseType/$domain.$fileName.$type.crt"
local p12="$path/crt-$baseType/$domain.$fileName.$type.p12"
local chain="$path/$domain.ca-$baseType.chain.pem"
if [ -e $crt ]; then
local lastSrl=$(openssl x509 -in $crt -serial -noout)
local lastFnr=$(openssl x509 -in $crt -fingerprint -noout)
check_prompt 1 "certificate $domain.$fileName.$type.crt exists as \n\t$lastSrl\n\t$lastFnr\nRevoke this version and create a new verion."
echo 'Please set the revokation reason, type any other key to continue without setting the CRL reason.'
echo '[1] unspecified'
echo '[2] keyCompromise'
echo '[3] CACompromise'
echo '[4] affiliationChanged'
echo '[5] superseded'
echo '[6] cessationOfOperation'
echo '[7] certificateHold'
echo '[8] removeFromCRL'
read -p 'Please set the revokation reason [1-8]: ' answer
local revokationReason=no
case "$answer" in
1)
revokationReason=unspecified
;;
2)
revokationReason=keyCompromise
;;
3)
revokationReason=CACompromise
;;
4)
revokationReason=affiliationChanged
;;
5)
revokationReason=superseded
;;
6)
revokationReason=cessationOfOperation
;;
7)
revokationReason=certificateHold
;;
8)
revokationReason=removeFromCRL
;;
*)
warn_result 1 'Nothing matched. Continue without setting a reason.'
esac
if [ $revokationReason == 'no' ]; then
openssl ca \
-config $caCnf \
-revoke $crt \
-passin file:$caPwd
else
openssl ca \
-config $caCnf \
-revoke $crt \
-passin file:$caPwd \
-crl_reason $revokationReason
fi
openssl ca -gencrl \
-config $caCnf \
-out $caCrl \
-passin file:$caPwd
fi
# note -subj
# if you want to use multiple values you should remove the -subj and use the prompt.
# /O/ST must match, see CA-configs.
# I prefer to bypass the prompt for ~300 domains with ~2k subdomains.
case "$type" in
tls-server)
export SAN="DNS:$domain,DNS:*.$domain"
openssl req -new \
-config $csrCnf \
-out $csr \
-keyout $key \
-subj "/C=BE/ST=Antwerp/O=### Network $domain/CN=$domain"
openssl ca \
-batch \
-config $caCnf \
-in $csr \
-out $crt \
-passin file:$caPwd \
-extensions server_ext
openssl pkcs12 -export \
-name "$domain (TLS Network Component)" \
-inkey $key \
-passout pass:\
-in $crt \
-certfile $chain \
-out $p12
;;
*)
check_result 1 "invalid request type $type; {email|tls-client|tls-server|code-signing}"
exit 1
esac
}
Comments