NOPE LinkedIn

Catégories:
Security
Crowdsec

Crodwsec en environnement multi server avec HTTPS

Installation de Crowdsec en environnement multi-server avec HTTPS

Cet article fait suite a celui mettant en oeuvre la solution sans HTTPS

But

Pour résoudre les problèmes de sécurité posés par une communication http en claire dans notre précédente installation multi-serveurs crowdsec , il est possible d’établir une communication entre les agents Crowdsec sur des canaux cryptés via HTTPS

1. Utilisation d’un certificat auto-signé

Génération d’une clef non encryptée:

openssl req -x509 -newkey rsa:4096 -keyout unencrypted-key.pem -out cert.pem -days 365 -nodes -addext "subjectAltName = IP:192.168.xx.xx"
Generating a RSA private key
....................++++
..............................................++++
writing new private key to 'unencrypted-key.pem'
-----
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [AU]:FR
State or Province Name (full name) [Some-State]:Bretagne
Locality Name (eg, city) []:Lorient
Organization Name (eg, company) [Internet Widgits Pty Ltd]:Breizhland
Organizational Unit Name (eg, section) []:IT service
Common Name (e.g. server FQDN or YOUR name) []:brzl001
Email Address []:

Cette clef commence et finie comme suit:

-----BEGIN PRIVATE KEY-----

-----END PRIVATE KEY-----

Génération d’une clef encryptée:

Cette opération va vous demander une passphrase et cette derniére sera nécessaire à chaque utilisation de cette clefs. Donc dans notre cas de figure au lancement de Crowdsec

# openssl req -x509 -newkey rsa:4096 -keyout encrypted-key.pem -out cert.pem -days 365 -addext "subjectAltName = IP:192.168.50.23"
Generating a RSA private key
...............................................++++
.....................................................................................................................................................++++
writing new private key to 'encrypted-key.pem'
Enter PEM pass phrase:
Verifying - Enter PEM pass phrase:
-----
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [AU]:FR
State or Province Name (full name) [Some-State]:Bretagne
Locality Name (eg, city) []:Lorient
Organization Name (eg, company) [Internet Widgits Pty Ltd]:Breizhland
Organizational Unit Name (eg, section) []:IT Service
Common Name (e.g. server FQDN or YOUR name) []:brzl001
Email Address []:

Cette clef doit commencer et finir comme suit:

-----BEGIN ENCRYPTED PRIVATE KEY-----

-----END ENCRYPTED PRIVATE KEY-----

Pour l’instant crowdsec n’est pas en mesure de demander la phrase secrète de la clé privée au démarrage. Nous avons le choix de déchiffrer à la main la clé privée à chaque démarrage ou rechargement de crowdsec ou de stocker la clé non chiffrée. De quelque manière que ce soit pour supprimer la phrase secrète, la commande suivante permet son décryptage :

openssl rsa -in encrypted-key.pem -out key.pem

Configurer crowdsec pour utiliser un certificat auto-signé

Sur le serveur 1, nous devons indiquer à crowdsec d’utiliser le certificat généré. Les options tls.cert_file et tls.key_file dans la section api.server de l’extrait /etc/crowdec/config.yaml suivant doivent être définies sur le fichier de certificat généré.

api:
  client:
    insecure_skip_verify: true
    credentials_path: /etc/crowdsec/local_api_credentials.yaml
  server:
    log_level: info
    listen_uri: 127.0.0.1:8080
    profiles_path: /etc/crowdsec/profiles.yaml
    console_path: /etc/crowdsec/console.yaml
    online_client: # Central API credentials (to push signals and receive bad IPs)
      credentials_path: /etc/crowdsec/online_api_credentials.yaml
    trusted_ips: # IP ranges, or IPs which can have admin API access
      - 127.0.0.1
      - ::1
#    tls:
#      cert_file: /etc/crowdsec/ssl/cert.pem
#      key_file: /etc/crowdsec/ssl/key.pem

Côté client, les changements de configuration se produisent dans deux fichiers. Nous devons d’abord modifier /etc/crowdec/config.yaml pour accepter les certificats auto-signés en définissant insecure_skip_verify sur true. Nous devons également remplacer http par https dans le fichier /etc/crowdsec/local_api_credentials.yaml afin de refléter les modifications. Ce petit changement doit être effectué sur les trois serveurs.

url: https://10.0.0.1:8080/
login: <login>
password: <password>

Remarque complémentaire: Évidemment, l’utilisation de certificats auto-signés ne donne aucune confiance quant à la propriété sur le serveur lapi : les serveurs utilisant le service (serveur-2 ou serveur-3 dans notre configuration) sont toujours vulnérables à l’attaque de l’homme au milieu, mais à au moins cette configuration fournit des communications cryptées. C’est la raison pour laquelle l’option InsecureSkipVerify est nécessaire.

2. Utilisation d’un certificat émis par une autorité de certification

On pourrait dire que Letsencrypt, ou des services comme Amazon ACM, pourraient être exploités pour contourner InsecureSkipVerify; en émettant un certificat pour un nom de domaine complet qui pourrait être ajouté à /etc/hosts ou à un serveur DNS local. /etc/crowdsec/local_api_credentials.yaml pourrait alors être rempli avec ce nom de domaine complet spécifié.

Cela fonctionne en effet et évite que l’option InsecureSkipVerify soit définie. Cela garantit que la communication entre le client et le serveur ne peut pas être altérée tant que la configuration DNS est fiable, mais doit toujours être considérée comme une solution de contournement.

3. Utilisation d’une PKI

Ce n’est pas le but de ce billet de blog de montrer comment configurer et gérer un pki SSL. Veuillez consulter la documentation officielle d’openssl. Le simple scénario pki est suffisant pour faire fonctionner les trucs Crowdsec.

Suite à cette documentation, il y a quelques chose à mentionner:

Pour être utilisables dans notre scénario crowdsec tls, les demandes de certificat doivent être émises avec un autre nom de sujet correspondant à l’adresse IP du serveur Crowdsec LAPI. Cela peut être fait en positionnant la variable d’environnement SAN lors de l’invocation d’openssl pour la demande de certificat (cf étape 3.3 du scénario openssl simple pki) :

SAN=IP:10.0.0.1 openssl req -new -config etc/server.conf -out certs/crowdsec.csr -keyout certs/crowdsec.key

La partie publique de la racine et les certificats de signature (fichier bundle créé à l’étape 4.5 dans le scénario openssl simple pki) doivent être ajoutés au magasin de certificats local avant de démarrer l’agent crowdsec. Dans cette configuration, cela est nécessaire pour se connecter au serveur LAPI. Il existe de nombreuses façons de le faire, les sources golang spécifient où les certificats sont attendus, ou on peut utiliser la variable d’environnement SSL_CERT_FILE dans le fichier de service systemd pour spécifier où trouver le certificat lors du lancement de l’agent crowdsec.

Conclusion

Cet article donne quelques points saillants sur la façon d’assurer des communications sécurisées entre nos différentes installations crowdsec. Le cas d’utilisation considéré est celui des installations crowdsec dans un réseau privé, mais cela peut également être déployé sur un réseau public avec communication sur Internet. Dans un tel cas, un certificat tiers ferait facilement l’affaire.

En fonction des besoins, j’ai proposé trois manières différentes de sécuriser les communications tls entre les instances crowdsec.

  • Le premier scénario avec des certificats auto-signés si l’on veut seulement assurer une communication cryptée sans besoin d’authentification.
  • Le deuxième scénario proposé ne peut être considéré comme une solution de contournement que lorsque l’on a la possibilité de modifier les résolutions DNS locales.
  • Le troisième scénario proposé est le plus compliqué, mais conviendrait à la plupart des cas d’utilisation et pourrait être la voie à suivre lorsque les problèmes de sécurité sont élevés.