1 # Copyright 1999-2014 Gentoo Foundation
2 # Distributed under the terms of the GNU General Public License v2
5 # @ECLASS: ssl-cert.eclass
8 # Max Kalika <max@gentoo.org>
9 # @BLURB: Eclass for SSL certificates
11 # This eclass implements a standard installation procedure for installing
12 # self-signed SSL certificates.
14 # "install_cert /foo/bar" installs ${ROOT}/foo/bar.{key,csr,crt,pem}
16 # @ECLASS-VARIABLE: SSL_CERT_MANDATORY
18 # Set to non zero if ssl-cert is mandatory for ebuild.
19 : ${SSL_CERT_MANDATORY:=0}
21 # @ECLASS-VARIABLE: SSL_CERT_USE
23 # Use flag to append dependency to.
24 : ${SSL_CERT_USE:=ssl}
26 # @ECLASS-VARIABLE: SSL_DEPS_SKIP
28 # Set to non zero to skip adding to DEPEND and IUSE.
31 if [[ "${SSL_DEPS_SKIP}" == "0" ]]; then
32 if [[ "${SSL_CERT_MANDATORY}" == "0" ]]; then
33 DEPEND="${SSL_CERT_USE}? ( dev-libs/openssl )"
34 IUSE="${SSL_CERT_USE}"
36 DEPEND="dev-libs/openssl"
43 # Initializes variables and generates the needed
44 # OpenSSL configuration file and a CA serial file
48 # Location of the config file
49 SSL_CONF="${T}/${$}ssl.cnf"
50 # Location of the CA serial file
51 SSL_SERIAL="${T}/${$}ca.ser"
52 # Location of some random files OpenSSL can use: don't use
53 # /dev/u?random here -- doesn't work properly on all platforms
54 SSL_RANDOM="${T}/environment:${T}/eclass-debug.log:/etc/resolv.conf"
56 # These can be overridden in the ebuild
57 SSL_DAYS="${SSL_DAYS:-730}"
58 SSL_BITS="${SSL_BITS:-1024}"
59 SSL_COUNTRY="${SSL_COUNTRY:-US}"
60 SSL_STATE="${SSL_STATE:-California}"
61 SSL_LOCALITY="${SSL_LOCALITY:-Santa Barbara}"
62 SSL_ORGANIZATION="${SSL_ORGANIZATION:-SSL Server}"
63 SSL_UNIT="${SSL_UNIT:-For Testing Purposes Only}"
64 SSL_COMMONNAME="${SSL_COMMONNAME:-localhost}"
65 SSL_EMAIL="${SSL_EMAIL:-root@localhost}"
67 # Create the CA serial file
68 echo "01" > "${SSL_SERIAL}"
70 # Create the config file
71 ebegin "Generating OpenSSL configuration${1:+ for CA}"
72 cat <<-EOF > "${SSL_CONF}"
75 default_bits = ${SSL_BITS}
76 distinguished_name = req_dn
81 O = ${SSL_ORGANIZATION}
83 CN = ${SSL_COMMONNAME}${1:+ CA}
84 emailAddress = ${SSL_EMAIL}
93 # @RETURN: <base path>
95 # Simple function to determine whether we're creating
96 # a CA (which should only be done once) or final part
103 echo "${T}/${$}server"
108 # @USAGE: <base path>
110 # Generates an RSA key
114 local base=$(get_base "$1")
115 ebegin "Generating ${SSL_BITS} bit RSA key${1:+ for CA}"
116 openssl genrsa -rand "${SSL_RANDOM}" \
117 -out "${base}.key" "${SSL_BITS}" &> /dev/null
124 # @USAGE: <base path>
126 # Generates a certificate signing request using
127 # the key made by gen_key()
131 local base=$(get_base "$1")
132 ebegin "Generating Certificate Signing Request${1:+ for CA}"
133 openssl req -config "${SSL_CONF}" -new \
134 -key "${base}.key" -out "${base}.csr" &>/dev/null
141 # @USAGE: <base path>
143 # Generates either a self-signed CA certificate using
144 # the csr and key made by gen_csr() and gen_key() or
145 # a signed server certificate using the CA cert previously
146 # created by gen_crt()
150 local base=$(get_base "$1")
152 ebegin "Generating self-signed X.509 Certificate for CA"
153 openssl x509 -extfile "${SSL_CONF}" \
154 -days ${SSL_DAYS} -req -signkey "${base}.key" \
155 -in "${base}.csr" -out "${base}.crt" &>/dev/null
157 local ca=$(get_base 1)
158 ebegin "Generating authority-signed X.509 Certificate"
159 openssl x509 -extfile "${SSL_CONF}" \
160 -days ${SSL_DAYS} -req -CAserial "${SSL_SERIAL}" \
161 -CAkey "${ca}.key" -CA "${ca}.crt" \
162 -in "${base}.csr" -out "${base}.crt" &>/dev/null
170 # @USAGE: <base path>
172 # Generates a PEM file by concatinating the key
173 # and cert file created by gen_key() and gen_cert()
177 local base=$(get_base "$1")
178 ebegin "Generating PEM Certificate"
179 (cat "${base}.key"; echo; cat "${base}.crt") > "${base}.pem"
185 # @FUNCTION: install_cert
186 # @USAGE: <certificates>
188 # Uses all the private functions above to generate and install the
189 # requested certificates.
190 # <certificates> are full pathnames relative to ROOT, without extension.
192 # Example: "install_cert /foo/bar" installs ${ROOT}/foo/bar.{key,csr,crt,pem}
196 if [ $# -lt 1 ] ; then
197 eerror "At least one argument needed"
201 case ${EBUILD_PHASE} in
202 unpack|prepare|configure|compile|test|install)
203 die "install_cert cannot be called in ${EBUILD_PHASE}"
207 # Generate a CA environment #164601
208 gen_cnf 1 || return 1
209 gen_key 1 || return 1
210 gen_csr 1 || return 1
211 gen_crt 1 || return 1
218 for cert in "$@" ; do
219 # Check the requested certificate
220 if [ -z "${cert##*/}" ] ; then
221 ewarn "Invalid certification requested, skipping"
225 # Check for previous existence of generated files
226 for type in key csr crt pem ; do
227 if [ -e "${ROOT}${cert}.${type}" ] ; then
228 ewarn "${ROOT}${cert}.${type}: exists, skipping"
233 # Generate the requested files
240 # Install the generated files and set sane permissions
241 local base=$(get_base)
242 install -d "${ROOT}${cert%/*}"
243 install -m0400 "${base}.key" "${ROOT}${cert}.key"
244 install -m0444 "${base}.csr" "${ROOT}${cert}.csr"
245 install -m0444 "${base}.crt" "${ROOT}${cert}.crt"
246 install -m0400 "${base}.pem" "${ROOT}${cert}.pem"
251 if [ ${count} = 0 ] ; then
252 eerror "No certificates were generated"
254 elif [ ${count} != ${#} ] ; then
255 ewarn "Some requested certificates were not generated"