Created
February 21, 2016 06:52
-
-
Save kousu/5c0b7a959885cdade8ea to your computer and use it in GitHub Desktop.
openssl sucks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| #!/bin/sh | |
| # | |
| # generates a self-signed CA and certificates signed by that CA. | |
| # If you install the CA into your certificate stores (in Firefox: Prefs->Advanced->Certs->Import, in Gnome: open the .crt in and whose .crt,.key pair can be used | |
| # worked out with http://www.akadia.com/services/ssh_test_certificate.html and trial and error | |
| # (as usual, with OpenSSL) | |
| # Usage: | |
| # ./mkcert # and follow the prompts, to make a CA | |
| # ./mkcert my.domain.name | |
| # ./mkcert 4chan.tk | |
| # Find CA.crt and import it to your browser/OS cert stores. | |
| # For extra security, once you are done generating certs, *delete* CA.key. Then it cannot sign any more keys, but its signature can still be checked, via the magic of Public Key Crypto | |
| # For each domain, any server you run will need to be given the pair (domain.crt, domain.key). domain.crt is public knowledge, but hold domain.key safe (though the attack surface is faiiiiiirly small, since your self-signed CA won't exist except your own devices) | |
| # e.g. in python: | |
| # ``` | |
| # httpd = http.server(('0.0.0.0',443), http.server.SimpleHTTPRequestHandler) | |
| # import ssl | |
| # ctx = ssl.SSLContext(ssl.PROTOCOL_TLSv1_2); | |
| # ssl.load_cert_chain("domain.crt", "domain.key"); #here you have to pass *both* files | |
| # httpd.socket = ssl.wrap_socket(httpd.socket); | |
| # httpd.serve_forever(); | |
| # ``` | |
| # | |
| # e.g. in apache.conf: | |
| # ``` | |
| # SSLEngine on | |
| # SSLCertificateFile domain.crt | |
| # SSLCertificateKeyFile domain.key | |
| # ``` | |
| TARGET=$1 | |
| case $TARGET in | |
| "") | |
| DAYS=${2:-90} #CAs are good for 3 months by default | |
| echo | |
| echo "Generating self-signed certificate authority (CA)." | |
| echo "--------------------------------------------------" | |
| echo | |
| echo "You will be asked to fill in details which should identify your new certificate authority." | |
| echo "Luckily, no one ever looks at their cert stores so you can type anything you like." | |
| echo "The only field that really matters is common name (CN)." | |
| echo | |
| echo "If you do not wish to lose your previous CA, quit now." | |
| echo | |
| echo "Your CA will be good for $DAYS days." | |
| read -p "[press enter] " | |
| echo | |
| rm CA.key CA.crt 2>/dev/null | |
| openssl genrsa -out CA.key 4096 && #there's also -newkey rsa:4096 as an option to req, but a) it doesn't let us pick the name b) it doesn't let us make an unencrypted key | |
| #openssl req -new -key CA.key -out CA.csr -extensions v3_ca && | |
| #openssl x509 -req -in CA.csr -out CA.crt -signkey CA.key -extensions v3_ca -days "$DAYS" && #NOTE! -signkey, despite its name sounding like giving the key to sign with, actually is how we *cause* self-signed; | |
| # also for some reason in this form -extensions is ignored. motherfucker. | |
| openssl req -new -x509 -days "$DAYS" -key CA.key -out CA.crt -extensions v3_ca && | |
| #fd:4 4< <(read -p "Enter Password: " A; echo $A) && #<-- if openssl fails it doesn't return non-zero. great. | |
| # TODO: give the /option/ of encrypting the key; there's a way to do this with 'openssl rsa' | |
| # I believe if you inline the genrsa command (by using -newkey instead of -key) you are not given the option to skip putting a password on | |
| # | |
| echo 'CA.crt generated. Try `openssl x509 -in CA.crt -text` to see results' | |
| echo 'Under *nix, you may install your CA as an OS-level CA by (as root):' | |
| echo '\# cp CA.crt /etc/ssl/certs/my_new_ca_name.pem && c_rehash' | |
| echo 'You may also install it into Firefox/Chrome using their preferences GUIs' | |
| echo 'or into Windows by using the Control Panel' | |
| # headsup: | |
| # so *this* command works in one go: | |
| # openssl req -new -x509 -days 3650 -extensions v3_ca -keyout cakey.pem -out cacert.pem -batch -passout pass:password | |
| # but it requires a password, which is annoying | |
| # there's also `openssl ca` and `/etc/ssl/misc/CA.sh` but oh god no | |
| ;; | |
| *) | |
| DAYS=${2:-3} # keys are only good for 3 days by default | |
| echo | |
| echo "Generating $1.crt and $1.key, signed by the CA." | |
| echo | |
| echo "If you do not wish to overwrite your previous cert, quit now." | |
| echo | |
| echo "Your cert will be good for $DAYS days." | |
| echo "-----------------------------------------------" | |
| read -p "[press enter] " | |
| echo | |
| rm "$1.key" "$1.crt" 2>/dev/null | |
| openssl genrsa -out "$1".key 4096 && | |
| openssl req -new -key "$1".key -out "$1".csr -subj "/CN=$1" && | |
| # wtf is CA.srl for? why can we only create it when we're signing a sub-certificate?? | |
| openssl x509 -req -in "$1".csr -out "$1".crt -CA CA.crt -CAkey CA.key -CAcreateserial -days "$DAYS" && | |
| rm "$1".csr | |
| echo $1'.crt generated. Try `openssl x509 -in '$1'.crt -text` to see results' | |
| ;; | |
| esac | |
| echo |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment