Getting started using GnuPG encryption - Part 2

In the previous part we covered creating your key pair, in this part we will look at using it to perform encryption and decryption as well as taking a look at the GnuPG trust system.


Using GnuPG for encryption is really very simple, in the first case let's see how you can encrypt a message.

gpg -aer 3A667E8AF50B404D
      -a, --armor (ASCII output)
      -e, --encrypt
      -r, --receipient

In this case the recipient is going to be ourself, normally you would use the public key of the person you intend to communicate with, once you hit enter you can type or paste in your message, pasting will normally complete the message otherwise you need to hit CTRL + D twice when done, the message will then be encrypted and shown, for example:

gpg -aer 3A667E8AF50B404D
Hello, this is a test message.-----BEGIN PGP MESSAGE-----


Copy all of the encrypted message including the begin and end text and the dash symbols, the only change you can make is to remove the blank line in the encrypted message, anything else and it will not decrypt unless the header and footer is correctly restored, for convenience you can have GnuPG output directly to a file like so.

gpg -aer 3A667E8AF50B404D -o message.txt
    -o, --output


In order to decrypt a received message the correct private key must be available, you will also need your passphrase.

gpg -d
    -d, --decrypt

Once you press enter paste the encrypted message, it will automatically look for the key and if found ask you to enter your passphrase, once entered correctly the original message will be displayed, like before you can use the -o flag to redirect the output to a file, you can also specify a text file as the input rather than having to paste it in.

gpg -d message.txt -o output.txt

What about files?

The exact same process can be used for files, although of course you'd not be pasting the file in, typically it's best to archive files using your favourite archive format (I.E .tar.gz, .zip, etc) when dealing with more than one file, this also helps reduce the final size, since files are not typically in ASCII you should omit the armor option, for example:

gpg -r 3A667E8AF50B404D -e test.tar.gz

There are a few things to note about this, first if you do not specify the output file name it will simply make a copy and append .gpg to the end to signify it's GnuPG encrypted, secondly if you omit the recipient it will use your preferred key, this can be specified in the GnuPG options which will be covered later, this applies to messages as well except it will ask you for the intended recipient, finally the order of parameters when calling GnuPG is important, so if it doesn't work check the order.

Decryption is done exactly the same way, make sure you do specify the output file though or it will dump it in your terminal.


Trust is an important consideration when using encryption, if you're going to send sensitive information to someone you need to be reasonably certain that the recipient is indeed who they claim to be.

Let's say the person we wish to communicate with is called Bob, you could meet Bob face to face, verify his identity and exchange keys, in most cases however this isn't practical or possible, another more practical way is to trust that friends of Bob have performed these checks already, so if you trust Bob's friends then you can trust Bob.

Trust is typically given by signing a persons key with your own key, normally this is done right after the key exchange by both parties, signatures remain with the key unless they are removed making it very useful to see who trusts who, signing a key by default makes it fully trusted, if you try to use a key that is not trusted GnuPG will warn you of this, but not stop you from using it.

gpg -u 'test key' --sign-key 'test2'
  -u, --local-user

Running this will allow you to sign the key with the name 'test2' with 'test key', this does require your secret key otherwise anyone could forge your signature, you can then list signatures with:

gpg --list-sigs
  --list-sigs, --list-signatures

If you have a lot of keys you can restrict it to a single key by using the key id, name or email address.

gpg --list-sigs 'test2'
  pub   rsa2048 2017-06-28 [SC] [expires: 2019-06-28]
  uid           [ultimate] test2 <>
  sig 3        E5745EC536971597 2017-06-28  test2 
  sig          3A667E8AF50B404D 2017-06-28  test key <>
  sub   rsa2048 2017-06-28 [E] [expires: 2019-06-28]
  sig          E5745EC536971597 2017-06-28  test2 <>

If you're wondering why the 'test2' key is signed by itself, this is done when the key is created or changes are made, this can be useful to see when a key was last modified.

You may have also noticed that the 'test key' signature does not have a authenticity level specified, this means no claims to the authenticity of the key have been made, this is the default behaviour, normally level 1 means minimal or no verification has been done, 2 means some verification has been done and 3 means extensive verification, in addition a L character means a local signature which cannot be exported with the key, R for a non-revocable signature (the person who signed it can never revoke it), N if the signature contains a notation and X if the signature has expired, you can specify how much checking you have done when signing a key with the --ask-cert-level option, this is generally recommended.

It's important to note that authentication levels are not very well defined, it's up to the user to decide the meaning of them.

GnuPG Trust System

By default GnuPG used the web of trust model keep track of what keys are trusted, whenever you add a new key the signatures will be checked to determine if it can be trusted, this is done by checking against keys that are trusted introducers, this is separate to the key trust so you can trust a key while not trusting it enough to be an introducer.

To set a key as an introducer you need to edit it, by default your own keys are ultimate introducers.

gpg --edit-key 'test2'
gpg> trust
sec  rsa2048/3A667E8AF50B404D
  created: 2017-06-19  expires: 2018-06-19  usage: SC
  trust: undefined     validity: full
ssb  rsa2048/37DEA43755409894
  created: 2017-06-19  expires: 2018-06-19  usage: E
[  full  ] (1). test key <>

Please decide how far you trust this user to correctly verify other users' keys
(by looking at passports, checking fingerprints from different sources, etc.)

1 = I don't know or won't say
2 = I do NOT trust
3 = I trust marginally
4 = I trust fully
5 = I trust ultimately
m = back to the main menu

Your decision? 4
sec  rsa2048/3A667E8AF50B404D
  created: 2017-06-19  expires: 2018-06-19  usage: SC
  trust: full     validity: full
ssb  rsa2048/37DEA43755409894
  created: 2017-06-19  expires: 2018-06-19  usage: E
[  full  ] (1). test key <>
Please note that the shown key validity is not necessarily correct
unless you restart the program.

gpg> save

When looking at other keys GnuPG will check your trusted introducers, in order for a new key to be trusted it needs to be signed by 3 marginal introducers, 1 full or 1 ultimate introducer, this setting is fully adjustable.

In practice however the system isn't really that good, more often than not you will want to make your own decision about trust rather than rely on the system, a different system known as ToFU (Trust on First Use) is available which grants trust the first time you use a key, or your can disable the automatic system entirely.

In many cases it's acceptable to simply to verify the control of the key rather than the actual identity of the user, in such a scenario the most common method is to email the user a message encrypted with their key, if they are able to decrypt it and reply that is reasonable proof they have control of the key.

In the next part we will be looking at how you can use signatures to verify the integrity and authenticity of messages and files as well as how to use key servers.


Comments, ideas and criticism welcome.

No comments at the moment, why not make one ?