Add GnuPG keys export to Nitrokey
This commit is contained in:
parent
8e625fff00
commit
d055d1ee97
1 changed files with 413 additions and 0 deletions
|
@ -0,0 +1,413 @@
|
|||
Title: Importer des clefs GnuPG dans sa Nitrockey Pro
|
||||
Category: sécurité
|
||||
Tags: GPG, open source, open hardware, Nitrokey, pl-fr
|
||||
Date: 2019-07-28 23:10
|
||||
|
||||
Dans un [précédent article]({filename}../decouverte-de-la-nitrokey/index.md)
|
||||
j'ai présenté la *Nitrockey Pro* et fait un bref tour du propriétaire. Cette
|
||||
fois si je vais expliquer comment y importer des clefs PGP déjà existante.
|
||||
|
||||
Bien entendu je part sur un système déjà installée et configurée et part du
|
||||
principe que la Nitrokey est paramétrée (PIN utilisateur et administrateur, nom
|
||||
du propriétaire etc.)
|
||||
|
||||
## Avant de commencer
|
||||
|
||||
Mes clefs sont un peu particulières J'ai :
|
||||
|
||||
- une *clé principale servant* a **créer des sous clefs, de les révoquer et
|
||||
de signer celles des copains**.
|
||||
- une *sous clé* **permettant de chiffrer**
|
||||
- enfin une *sous clé* **permettant de signer**
|
||||
|
||||
A partir de là nous allons **mettre mes deux sous clefs sur la Nitrokey** et
|
||||
garder la clé principale dans un endroit sûr.
|
||||
|
||||
L'importation n'est pas très difficile et prendra qu'une minute. Par contre il
|
||||
est important de réaliser quelques opérations en plus :
|
||||
|
||||
- créer un certificat de révocations.
|
||||
- Sauvegarder comme il se doit la clé maître et ses sous clefs, le certificat
|
||||
de révocation. En effet l'opération d'importation de vous sous clefs
|
||||
supprimera celles-ci du dossier `~/.GnuPG/`
|
||||
- Mettre à l'abri la *Master Key* et la sortir du trousseau *GnuPG* pour la
|
||||
mettre en sécurité. Elle sera utile pour révoquer des sous clefs, en
|
||||
générer d'autres et certifier.
|
||||
|
||||
## Réaliser une sauvegarde
|
||||
|
||||
Avant tout, il est important de garder une copie de sauvegarde de sa clé maître
|
||||
et de ses sous clefs au cas ou une manipulations ne se passe pas comme prévue.
|
||||
Pour bien faire les choses, exportons les clefs privées, publiques et le
|
||||
certificat de révocation dans un fichier compressé et chiffré.
|
||||
|
||||
Commençons par créer un dossier dans le répertoire `/tmp` afin de recevoir le
|
||||
certificat de révocation et les sauvegardes de clefs :
|
||||
|
||||
```shell
|
||||
mkdir /tmp/gpg_backup
|
||||
chmod 700 /tmp/gpg_backup
|
||||
```
|
||||
|
||||
### Certificat de révocation
|
||||
|
||||
Voici la commande utile pour créer un certificat de révocation pour notre clé
|
||||
maître :
|
||||
|
||||
```shell
|
||||
gpg --gen-revoke --output /tmp/gpg_backup/revoke.asc <id>
|
||||
```
|
||||
|
||||
Où `<id>` représente l'identifiant de la clé. Une boite de dialogue apparaît
|
||||
ensuite demandant la phrase de passe permettant de débloquer la clé privée.
|
||||
|
||||
### Exporter les clefs
|
||||
|
||||
Commençons par la clé privée :
|
||||
|
||||
```shell
|
||||
gpg --export-secret-keys --armor --output /tmp/gpg_backup/ephase_private.asc <id>
|
||||
```
|
||||
|
||||
Bien entendu la phrase de passe de la clé sera demandée
|
||||
|
||||
Puis la clé publique, qui ne nécessite pas de phrase de passe pour être
|
||||
débloquée :
|
||||
|
||||
```shell
|
||||
gpg --export --armor --output /tmp/gpg_backup/ephase_public.asc <id>
|
||||
```
|
||||
|
||||
### Créer une archive sécurisée
|
||||
|
||||
Bien entendu il ne faut pas que ces données (du moins le certificat de
|
||||
révocation et la clé privée) tombent entre de mauvaise main, il suffit
|
||||
simplement de créer une archive chiffrée du dossier `/tmp/gpg_backup` :
|
||||
|
||||
```shell
|
||||
tar cz -C '/tmp/' gpg_backup | gpg --symmetric --output ephase_key.gpg && rm -rf /tmp/gpg_backup
|
||||
```
|
||||
|
||||
Après avoir rentré un mot de passe de chiffrement fort pour protéger notre
|
||||
sauvegarde, nous sommes fin prêt pour la suite des opérations. Pour restaurer le
|
||||
dossier il suffira d'utiliser la commande suivante :
|
||||
|
||||
```shell
|
||||
gpg --decrypt ephase_key.gpg | tar xz
|
||||
```
|
||||
|
||||
### Mettre ce fichier à l'abri
|
||||
|
||||
Le fichier `ephase_key.gpg` sera mis à l'abri sur un espace de stockage hors
|
||||
ligne (voire même plusieurs).
|
||||
|
||||
## Importer la paire de clefs
|
||||
|
||||
La manipulation se fait depuis la gestion de clefs `gpg`, nous y accédons avec
|
||||
la commande :
|
||||
|
||||
```shell
|
||||
gpg --expert --edit-key <id>
|
||||
|
||||
gpg (GnuPG) 2.2.17; Copyright (C) 2019 Free Software Foundation, Inc.
|
||||
This is free software: you are free to change and redistribute it.
|
||||
There is NO WARRANTY, to the extent permitted by law.
|
||||
|
||||
La clef secrète est disponible.
|
||||
|
||||
sec rsa4096/XXXXXXXXXXXXXXXX
|
||||
créé : 2016-07-07 expire : 2020-07-12 utilisation : SC
|
||||
confiance : ultime validité : ultime
|
||||
ssb rsa4096/YYYYYYYYYYYYYYYY
|
||||
créé : 2016-07-07 expire : 2020-07-12 utilisation : E
|
||||
ssb rsa4096/ZZZZZZZZZZZZZZZZ
|
||||
créé : 2016-07-07 expire : 2020-07-12 utilisation : S
|
||||
[ ultime ] (1). Yorick Barbanneau <ephase@example.com>
|
||||
|
||||
gpg>
|
||||
```
|
||||
|
||||
À partir de là nous allons procéder par étape :
|
||||
|
||||
1. choisir la sous clé pour 1 (le chiffrement) et l'exporter dans le slot
|
||||
*chiffrement* sur la Nitrokey
|
||||
2. choisir la sous clé 2 (signature) et l'exporter dans le slot *signature*
|
||||
|
||||
La clé maitre sera sortie du trousseau et mise à l'abri.
|
||||
|
||||
### Exporter la clé ¨Chiffrement¨
|
||||
|
||||
Voici les commandes à entrer pour exporter la première clé sur la Nitrokey :
|
||||
|
||||
```shell
|
||||
gpg> key 1
|
||||
|
||||
[...]
|
||||
|
||||
gpg> keytocard
|
||||
```
|
||||
|
||||
`key 1` permet de dire à `gpg` que l'on travaille sur la première sous clé, et
|
||||
`keytocard` envoi celle-ci sur notre *smartcard*
|
||||
|
||||
`gpg` nous demande de déverrouiller par en entrant la phrase
|
||||
de passe et le code *PIN* administrateur de la Nitrokey.
|
||||
|
||||
|
||||
### Exporter la clé ¨Signature¨
|
||||
|
||||
Il faut maintenant dé-sélectionner la sous clé 1 :
|
||||
|
||||
```shell
|
||||
gpg> key 1
|
||||
```
|
||||
|
||||
Pour copier la clé 2:
|
||||
|
||||
```shell
|
||||
gpg> key 2
|
||||
|
||||
[...]
|
||||
|
||||
gpg> keytocard
|
||||
```
|
||||
|
||||
Comme précédemment, `gpg` nous demande de déverrouiller par en entrant la phrase
|
||||
de passe et le code *PIN* administrateur de la Nitrokey.
|
||||
|
||||
### Sauvegarder les changements.
|
||||
|
||||
Il ne reste plus qu'à sauvegarder nos changement sur les clefs et quitter `gpg`
|
||||
|
||||
```shell
|
||||
gpg> save
|
||||
```
|
||||
|
||||
Les deux sous clefs seront alors supprimées de notre trousseau et disponible
|
||||
uniquement via la *smartcard*., d'ailleurs
|
||||
|
||||
## Mettre sa clé maître à l'abri
|
||||
|
||||
La clé maître est la plus importante des clefs, elle permet de créer d'autre
|
||||
sous clefs, d'émettre des certificats de révocation pour celles-ci ou encore de
|
||||
signer les clefs publique des amis.
|
||||
|
||||
Il est tout à fait possible de la sortir du trousseau pour la mettre à l'abri
|
||||
et de la remettre lorsque l'on en a besoin.
|
||||
|
||||
Pour ma part j'ai choisi de mettre la clé sur un support externe chiffré, et
|
||||
avec l'aide d'un script de monter le support lorsque j'en ai besoin et de créer
|
||||
un lien symbolique de la clé depuis le répertoire de `GnuPG`.
|
||||
|
||||
Les outils utilisés sont en général installés de base : `LUKS` et `udisk`
|
||||
|
||||
### Créer le conteneur chiffré
|
||||
|
||||
Toutes les opérations suivantes se font en **super utilisateur** ou avec `sudo`.
|
||||
|
||||
Dans un premier temps partitionnons la clé USB (ici `sdb`):
|
||||
|
||||
```shell
|
||||
parted -s /dev/sdb mklabel msdos mkpart primary ext4 1MiB 100%
|
||||
```
|
||||
|
||||
Il nous faut ensuite créer le conteneur chiffré :
|
||||
|
||||
```shell
|
||||
cryptsetup luksFormat /dev/sdb1
|
||||
WARNING!
|
||||
========
|
||||
Cette action écrasera définitivement les données sur /dev/sdb1.
|
||||
|
||||
Are you sure? (Type uppercase yes): YES
|
||||
Saisissez la phrase secrète pour /dev/sdb1 :
|
||||
Vérifiez la phrase secrète :
|
||||
```
|
||||
|
||||
Le déverrouiller :
|
||||
|
||||
```shell
|
||||
cryptsetup luksOpen /dev/sdb1 gpg_master
|
||||
Saisissez la phrase secrète pour /dev/sdb1 :
|
||||
```
|
||||
|
||||
Pour le formater :
|
||||
|
||||
```shell
|
||||
mkfs.ext4 -E root_owner=1000:1000 -m 0 /dev/mapper/gpg_master
|
||||
```
|
||||
Il faut bien entendu adapter le paramètre `root_owner` en fonction de votre
|
||||
`UID` et de votre `GID`.
|
||||
|
||||
Et enfin monter la partition avec :
|
||||
|
||||
```shell
|
||||
mkdir -p /mnt/usb
|
||||
mount /dev/mapper/gpg_master /mnt/usb
|
||||
```
|
||||
|
||||
Puis s'assurer que la clé USB ne peut être lue seulement par notre utilisateur :
|
||||
|
||||
```shell
|
||||
chmod 700 /mnt/usb
|
||||
```
|
||||
|
||||
### Déplacer la clé maitre GnuPG sur votre clé USB
|
||||
|
||||
Les commandes suivante sont à faire dans la foulée mais en tant utilisateur
|
||||
courant.
|
||||
|
||||
Nous allons utilisé une fonctionnalité de `GnuPG 2` : les clefs privées sont
|
||||
stockée dans le répertoire `~/.gnupg/private-keys-v1.d/` ou chaque fichier
|
||||
correspond à une clé et le nom est repris dans le champs `keygrip` :
|
||||
|
||||
```shell
|
||||
gpg -K --with-keygrip
|
||||
/home/ephase/.gnupg/pubring.kbx
|
||||
-------------------------------
|
||||
sec rsa4096 2016-07-07 [SC] [expire : 2020-07-12]
|
||||
3526F4565D76C5674AA56690936CDF3783293949
|
||||
Keygrip = ABCDEF1234567890ABCDEF1234567890ABCDEF12
|
||||
uid [ ultime ] Yorick Barbanneau <ephase@example.com>
|
||||
ssb> rsa4096 2016-07-07 [E] [expire : 2020-07-12]
|
||||
Keygrip = FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF
|
||||
ssb> rsa4096 2016-07-07 [S] [expire : 2020-07-12]
|
||||
Keygrip = BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB
|
||||
```
|
||||
|
||||
Je doit donc chercher la clé `3526F4565D76C5674AA56690936CDF3783293949.key` et
|
||||
la copier sur notre clé :
|
||||
|
||||
```shell
|
||||
mkdir -p /mnt/usb/.gpg_master
|
||||
chown 700 /mnt/usb/.gpg_master
|
||||
mv ~/.gnupg/private-keys-v1.d/3526F4565D76C5674AA56690936CDF3783293949.key /mnt/usb/.usbmaster
|
||||
```
|
||||
|
||||
Afin de bien vérifier que la clé n'est plus disponible, il suffit de faire :
|
||||
|
||||
```shell
|
||||
gpg -K
|
||||
/home/ephase/.gnupg/pubring.kbx
|
||||
-------------------------------
|
||||
sec# rsa4096 2016-07-07 [SC] [expire : 2020-07-12]
|
||||
3526F4565D76C5674AA56690936CDF3783293949
|
||||
uid [ ultime ] Yorick Barbanneau <ephase@example.com>
|
||||
ssb> rsa4096 2016-07-07 [E] [expire : 2020-07-12]
|
||||
ssb> rsa4096 2016-07-07 [S] [expire : 2020-07-12]
|
||||
```
|
||||
|
||||
Le `#` à côté de `sec` indique que la clé maître n'est plus disponible dans le
|
||||
trousseau `GnuPG`.
|
||||
|
||||
### Automatiser le montage de la clé
|
||||
|
||||
Afin de faciliter les opération de montage et démontage de la clé USB
|
||||
contenant notre clé maître, on va s'aider d'un script.
|
||||
|
||||
L'utilisation est simple, une fois mis dans un endroit accessible via le `$PATH`
|
||||
il suffit de faire `gpgmount.sh m` pour monter la clé USB ou `gpgmount.sh u`
|
||||
pour la démonter.
|
||||
|
||||
```bash
|
||||
#!/bin/bash
|
||||
|
||||
UUID=""
|
||||
mountpoint=""
|
||||
|
||||
usage () {
|
||||
cat <<EOF
|
||||
$0 m | u
|
||||
$0 mount | unmount
|
||||
|
||||
mount or unmount encrypted device based on UUID and attach private keys
|
||||
EOF
|
||||
}
|
||||
|
||||
if [ -L "/dev/disk/by-uuid/${UUID}" ]
|
||||
then
|
||||
case "$@" in
|
||||
"m"|"mount")
|
||||
|
||||
echo "Mount encryted key"
|
||||
action=$(udisksctl unlock -b /dev/disk/by-uuid/${UUID})
|
||||
|
||||
if [ ! $? -eq 0 ]
|
||||
then
|
||||
echo $action
|
||||
exit 10
|
||||
fi
|
||||
mountpoint=$(udisksctl mount -b /dev/mapper/luks-${UUID} | \
|
||||
awk '{print $4}')
|
||||
|
||||
while read -r f
|
||||
do
|
||||
base=$(basename $f)
|
||||
|
||||
#create symlink to key file if not exist
|
||||
if [ ! -e "~/.gnupg/private-keys-v1.d/$base" ]
|
||||
then
|
||||
ln -s $f ~/.gnupg/private-keys-v1.d/$base
|
||||
fi
|
||||
done < <(find ${mountpoint%.}/.gpg_master/ -type f -name "*.key")
|
||||
;;
|
||||
"u"|"unmount")
|
||||
echo "unmount encrypted key"
|
||||
while read -r f
|
||||
do
|
||||
rm $f
|
||||
done < <(find ~/.gnupg/private-keys-v1.d -type l -name "*.key")
|
||||
|
||||
udisksctl unmount -b /dev/mapper/luks-${UUID} 2&> /dev/null || \
|
||||
echo "Volume is already unmounted"
|
||||
udisksctl lock -b /dev/disk/by-uuid/${UUID} 2&> /dev/null || \
|
||||
echo "Encrypted container is not unlocked"
|
||||
;;
|
||||
*)
|
||||
echo "parameter not understood, what do you want :"
|
||||
usage
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
else
|
||||
echo "USB device $UUID is not connected"
|
||||
exit 5
|
||||
fi
|
||||
|
||||
exit 0
|
||||
```
|
||||
|
||||
Il faut bien entendu mettre l'uuid de la partition contenant notre clé maître
|
||||
dans la variable `UUID`.
|
||||
|
||||
Pour le récupérer il suffit de lancer la commande `blkid` en tant que `root`
|
||||
avec en paramètre la partition en question:
|
||||
|
||||
```shell
|
||||
blkid /dev/sdb1
|
||||
/dev/sdb1: UUID="<uuid>" TYPE="crypto_LUKS" PARTUUID="<partuuid>"
|
||||
```
|
||||
|
||||
## En conlusion
|
||||
|
||||
J'ai essayé ici de créer un environnement équilibré entre sécurité et facilité.
|
||||
La Mitrokey permet donc de sécuriser mes sous clefs utilisées tous les jours
|
||||
tout en les rendant disponibles sur mes deux machines principales.
|
||||
|
||||
Bien sûr il serait plus sécurisé de n'utiliser la clé maître sur une machine
|
||||
totalement hors ligne démarrée par une distribution live. Mais avouez que pour
|
||||
signer les clé des amis (lors de [chiffro-fête][l_w_cparty] par exemple), ce
|
||||
n'est pas l'idéal.
|
||||
|
||||
[l_w_cparty]:https://fr.wikipedia.org/wiki/CryptoParty
|
||||
|
||||
## Bibliographie
|
||||
|
||||
*Kernel Maintainer PGP guide — The Linux Kernel documentation* par Konstantin
|
||||
Ryabitsev - [lien][b_pgpkernmaint]
|
||||
|
||||
*Using an offline GnuPG master key* (2015) par Damien Goutte-Gattat
|
||||
- [lien][b_offlinegpgk]
|
||||
|
||||
[b_pgpkernmaint]:https://www.kernel.org/doc/html/v5.1/process/maintainer-pgp-guide.html
|
||||
[b_offlinegpgk]:https://incenp.org/notes/2015/using-an-offline-gnupg-master-key.html
|
Loading…
Add table
Add a link
Reference in a new issue