Monday, June 16, 2014

Make Tomcat Startup by default in Fedora 20

So today I got tired of starting up tomcat manually, and decided to make it start by default at boot. After doing a bit of digging on the intertubes I found that if you create a script in /etc/rc.d called rc.local that is executable fedora will run it on boot. So I created the file and added the following lines:


#!/bin/sh
cd /home/sean/Public/apache-tomcat-8.0.8/bin
su sean ./catalina.sh start

Since root will be the user at startup I wrapped the catalina.sh command in a switch user command to my user. Thus it is started in a sandbox for my user.

Saturday, June 14, 2014

Getting set up on PGP with GPG

PGP, or Pretty Good Privacy is a standard in personal cryptography. It can encrypt your emails, sign documents with a cryptographic signature, encrypt files on your harddrive, and (my new favorite) sign git commits. One of the problems with cryptography is that getting things encrypted and decrypted only gets you half there. The harder part of the equation, at least for us users, is making sure that you are talking to the right person. This means that someone has to vet people, their ids, their domains, emails, and their cryptographic credentials. PGP takes this away from corporations and moves it to a more p2p model called the web of trust, where any user is given the power to vet and approve other users.

GPG, or GNU privacy Gaurd is an implementation of PGP and can easily be found on linux systems. There is gpg and gpg2, the first being a monolithic binary, and the latter a more modularized library allowing gpg to tie into gnome, guis, and other libraries. This blog will cover the command line tools only.

To get started the first thing that you'll want to do is get yourself a public/private key combination. Before diving into the commands, let me take a minute to talk about the weaknesses of the system. Once you've generated your keys, you'll be set for uber secure communication, without some futuristic computing power, it would take even the most powerful modern computers thousands of years to break your messages using brute force methods. Therefore most people won't even attempt to do so, they will try and use alternate means to get ahold of the private messages. The easiest way is to try to get ahold of your private key and use that to break the messages. While setting up your PGP key you'll have a chance to password protect it. Typically password attacks on the private key will be much more successful especially if you use a weak password. So moral of the story is to try to pick a password that will be hard to guess, and that's long enough that it makes it hard to brute force as well.

Alright, let's get started.

gpg2 --gen-key

Ok, now come the quesitons

  1. First up, it will ask you what sort of key that you want, if you want to do all the things mentioned above you'll want a dual RSA key, or option 1 on my machine.
  2. You'll than have a chance to decide the size of your keys, 2048 being standard as of the writing of this post, 4096 if you want to make all the things secure.
  3. Next you'll tell it how long your key should be valid for, most people will opt for an infinite option (0) and then utilize key invalidation to revoke a key that has been compromised, expired or for whatever other reason. I've read that if you are using the key for some short term, less personal reason, like a campaign, or some event, you can utilize the expiration mechanism to express your interest in a short term communication means
  4. Now you get to identify yourself, keep in mind that if you are going to try to build the web of trust, you'll be proving who you are through id cards, and it'll make things easier if everything matches up.
  5. The final step is to specify the password that will guard your private key
gpg: key A6BAE9BD marked as ultimately trusted
public and secret key created and signed.

gpg: checking the trustdb
gpg: 3 marginal(s) needed, 1 complete(s) needed, PGP trust model
gpg: depth: 0  valid:   1  signed:   0  trust: 0-, 0q, 0n, 0m, 0f, 1u
pub   2048R/A6BAE9BD 2014-06-15
      Key fingerprint = E0E6 3484 5581 0B28 8EB8  2B68 EB65 E9D5 A6BA E9BD
uid                  admin account 
sub   2048R/144081B9 2014-06-15

Let's examine some of the parts here. So basically you have a public key, this is the one that you'll be sharing with all your cohorts, putting up on your webpage, broadcasting to the world, and reading off as a fellow pgper examines your id cards. Essentially your public key is hashed into a fingerprint, which is much shorter than reading off the actual key. The full fingerprint is 40 hex digits, which is often shorted to the last 16 or 8 to make things more convenient. You'll then notice your userid down below that, uid's or uat's are considered components of a public key. In fact when people certify you, they certify a uid in combination with a public key. You can have multiple uid's on your public key, and even pictures. Finally you have a sub key, this is a binding to your private key, so people can author messages to your private key through your public key. Remeber the first RSA and RSA step, you have both of them here, however only one will ever be fully specified to other users, as your private key is just for you.

Alright, at this point it would be wise to back up your private key. You can export it to a file, which is well suited for some offline storage format like a cd/dvd. You could burn it, and then tuck it away somewhere safe. That way if you ever lose your key, you can still get back the secret key. Remember however that the password that you set on your private key will remain. So if you forget your password, you are still very much out of luck. I suppose if you are forgetful enough you could remove the password (ie. set it to empty) on the private key before you export it. Or even make the password a part of the file, or as a readme in a different file.

gpg2 --export-secret-key --armor --outfile private-key.asc

The command above will export your private key to the file private-key.asc in a base64 encoded format which is safe to view in a text editor. Since your private and public are so bound together it also includes your public key. The private key is still password protected at this point.

The other thing that you should do strait away is set up a revoke certificate on your public key, and keep this somewhere safe. This will help you in the case that you forget your password, you can revoke your key, which will let everyone know that it is invalid.

gpg2 --armor --output revoke.asc --gen-revoke <keyid>

Alright, now all the details are sorted out and you are ready to go. Let's first address how to distribute your public key to your cohorts

gpg2 --keyserver pgp.mit.edu --send-key <keyid>

The above will send a key up to a keyserver, in this case the mit pgp server. Once you put a key up to a keyserver there is no going back, those keys are up there forever. So make sure that you are really sure you want to do it. Once they are up there, it makes life much easier for those wanting to obtain your key.

gpg2 --keyserver pgp.mit.edu --recv-key <keyid>

For example, someone could grab your key from the keyserver using the above command and the short fingerprint of your key.

gpg2 --armor --output public-key.asc --export <keyid>

So if you don't want to make your key public quite yet, you can export it in the ascii armored format. You can then send this file to your friends via email, you can put it up on your website, or expose it to those that you want to communicate with in a plethora of ways.

gpg2 --import someones-public-key.asc

And you can also pull in someones public key this way as well.

As mentioned before, you are an agent of trust for pgp keys, so once you obtain someones public key, and before you start using it, it's often good to sign their public key to 'certify' it. In fact gpg will warn you when you try to send messages to people keys that you haven't signed, or otherwise obtained trust in. In gpg land this signing is yours and yours alone to shoulder. You could sign anyone and everyone's key if you wanted, and make your web of trust huge. This might be bad though, you might inadvertently sign a pretenders key, and mislead people to believe that the pretender is a person they wished to securely communicate with. So usually it's better to meet the person face to face, and verify through state issued ids that they are who they say they are and that they own the key that they profess to own. Occasionally groups of people will get together and sign each others keys. These parties of nerdiness are called key signing parties, and help the web of trust grow and expand.

gpg2 --ask-cert-level --sign <key or uid>

And this is a way that you sign someones key. This specific way will allow you certify the key to a certain level. 0-3. This is where you can start being a little more relaxed in how you sign someones key. If you meet someone in passing and they show you a fingerprint, and you hear someone call them bob, then maybe you can sign to a level 0 or 1. If you communicate via email or phone, maybe a 2. And if you do all the above, and also see a state issued id and passport, a 3 would be reasonable. In the end though it is up to you.

Now let's say you want to encrypt a message to someone.

echo abcdefghijklmnopqrstuvwxyz > message1.txt gpg2 --armor --recipient <keyid> --encrypt message1.txt

This will create a new file called message1.txt.asc, which will be ascii encoded encrypted version of message1.txt.

rm message1.txt gpg2 --decrypt message1.txt.asc --output message1.txt

This will remove the original text file, and then decrypt the encrypted file and output that back into message1.txt

gpg2 --armor --sign --recipient <keyid> --encrypt message1.txt gpg2 --decrypt message1.txt.asc

In this last step we added on a signature, which basically hashes the original message, and then uses your private key to sign the hash. Basically in all the previous examples we have shown how anyone with your public key can send you an encrypted message. However, even though you may recieve it from their email, it does not necessarily mean that it came from that person. A signature crytographically ensures that the person (or in an unfortunate scenario people) that holds the private key saw the message exactly as you verified it.

You can also send messages to multiple recipients, and because the file or message is really encrypted with a symmetric cipher like AES, only the key to the symmetric cipher needs to be encrypted for each recipient. Therefore the overhead is quite small

OpenSSL Certificates to Tomcat Keystores

So being through this process a few times, and having to relearn it every time has not been fun. But before we get all technical let's do a little review. SSL/TLS allows clients/webbrowsers to securely communicate with servers. It utilizes public key cryptography (RSA or Elliptic Curve) to allow the server to hand out a key to the client. The client can then use that key to encrypt a message that only the server will be able to read (By decrypting it with a private key). This is great and all but unfortunately being able to securely communicate doesn't prevent the problem of communicating to the wrong person. This is where Certificate Authorities (CA) come into play. They verify that the person is who they say they are, and that they own the domain that the key is tied to. Once they have verified all that they "sign" the public key of the server with their private key. Now clients can obtain the public key (signed by the ca) from the server, and then use the ca's public key to verify that the signature was indeed from the ca, and then build trust that not only can they securely communicate with the server, but that they are communicating with the right server.
So in order to get started you have to create your private/public key pair. The public key will be the one that is handed out to everyone, and also the one that will be signed by CA's, while the private one will be kept only by you, and likely your server in order to decrypt all the traffic coming in, and also encrypt the traffic going back out.

openssl genrsa -out <yourdomain>-private-key.pem <key size in bits>

This command will generate a RSA keypair and save it with no password protection. Some common keysizes (from least secure to better secured) 1024, 2048, 4096.


openssl pkey -text -in <yourdomain>-private-key.pem
openssl pkey -in <yourdomain>-private-key.pem -pubout -text

These commands will pour out the different components of the key to the console. The first one generating the base64 encoded private key part, and the second one the base64 encoded public key part.

Ok, so now you have the keys that allow you to set up secure communication, the next step is to get your public key signed by a CA. CA's generally accept a certificate signing request (.csr), this consists of your public key, and a bunch of information about that key, most importantly is the "common name" or CN, which should resolve to your domain name. Mine being murphysean.com, or www.murphysean.com, and if your CA allows you could do *.murphysean.com to allow the certificate to work on all subdomains.

openssl req -out <yourdomain>.csr -key <yourdomain>-private-key.pem -new -sha256

The next command takes in the public/private key combo, a bunch of information from you on the command line, and pumps out a request that the CA can accept and sign to produce your final certificate. The -sha256 will request that the authority sign a sha256 hash of your public key combined with all the information gathered from you, you can leave it off to let it default to something more common. The more you pay the more the CA will be willing to certify. For most of your certificate authorities cheaper signing request options, they are only signing the CN. So don't be suprised when your final certificate has nulls for all the values you filled in.

cat <yourdomain>.csr

This will dump the csr text file to the console for easy copy and paste into your ca's web site form. At this point you should have the certificate from your CA. Save this file as <yourdomain>.crt

They will often also give you their root certificate, and sometimes their intermediate certificates as well. You'll want to nab those up at this time and save them. At this point you have all the pieces you need. I'll include some instructions for nginx at this point.
To get set up in java/tomcat you still have a bit of work to do. Tomcat uses a java keystore that should contain the server certificate. The first step in getting a keystore set up is to get your certificate into a a PKCS12 file. OpenSSL can do this for us.

openssl pkcs12 -export -in <yourdomain>.crt -inkey <yourdomain>-private-key.pem -out <yourdomain>.p12 -name <yourdomain> -CAfile <yourca>.pem -caname <yourcaname> -chain

This will merge all the different certificates into a chained pkcs12 file. You'll want to password protect the private key, with a password that is ok for your server application to know. Also as a side note here, if you were signed by an intermediate certificate, you'll want to obtain all the certificates that fall between you and the root certificate. Open the intermediate file in a text editor, and then just start appending all the certificates in order up to the root certificate. In many cases this is just the one root certificate as there is only one intermediate inbetween you and the root.

keytool -importkeystore -srckeystore <yourdomain>.p12 -srcstoretype PKCS12 -alias <yourdomain> -destkeystore <yourdomain>.keystore

So now you've got everything in order the last step is to just get your tomcat server pointed at your keystore for https/ssl/tls traffic. Open up your server.xml file, and uncomment the SSL Connector. I added two properties to mine, the keystoreFile property which I pointed at my .keystore file, and the keystorePass which unlocked the keystore, and also the private key in that keystore.

<Connector port="8443" protocol="org.apache.coyote.http11.Http11NioProtocol"
maxThreads="150" SSLEnabled="true" scheme="https" secure="true"
clientAuth="false" sslProtocol="TLS"
keystoreFile="<pathtokeystore>.keystore"
keystorePass="<ubersecurepassword in plaintext>"/>

In tomcat 8 the final working Connector looked like the above.