Création — Nicolas THOREZ 2019/03/28 20:50
La sécurisation de l'exécution de script est importante. En effet, les scripts sont utilisés pour automatiser des actions et surtout les exécuter sans nécessiter la présence de l'utilisateur. Cela entraîne invariablement des dérives et si le processus est très exploité par des administrateurs dans leur tâches quotidiennes, il l'est aussi par des pirates et autres. A ce titre, il faut pouvoir contrôler l'exécution d'un script sur nos infrastructures.
En Powershell, la politique d'exécution est gérer par les commandes Get-ExecutionPolicy et Set-ExecutionPolicy.
L'exécution de Get-ExecutionPolicy nous retournera la politique de sécurité actuelle sur le poste. Parmi ces politiques, nous trouverons :
Restricted pour les postes de travail.RemoteSigned pour les serveurs. Unblock-File.Undefined est défini sur tous les périmètres d'activité, alors la politique Restricted s'applique.Unblock-File : MicrosoftLes différentes politiques peuvent s'appliquer à différents périmètres d'activité, indépendants les uns des autres. Parmi ces périmètres, nous avons :
UserPolicy mais avec inscription de la politique en base de registre (HKCU).MachinePolicy mais avec inscription de la politique en base de registre (HKLM). C'est le périmètre par défaut.
Get-ExecutionPolicy AllSigned
Get-ExecutionPolicy -List
Scope ExecutionPolicy
----- ---------------
MachinePolicy Undefined
UserPolicy Undefined
Process Undefined
CurrentUser Undefined
LocalMachine AllSigned
Restricted
Set-ExecutionPolicy -ExecutionPolicy Restricted
Unrestricted sur le périmètre CurrentUser
Set-ExecutionPolicy -ExecutionPolicy Unrestricted -Scope CurrentUser
Comme on vient de le voir, on peut renforcer la sécurité d'un script et de son exécution en le signant.
Pour cela, la procédure est assez simple mais nécessite quelques prérequis tels que :
Si les prérequis sont remplis, alors la signature d'un script, par exemple un script Hello-World.ps1 qui serait enregistré dans le dossier C:\Scripts\, devient possible via les commandes suivantes :
# On stocke les différentes informations nécessaires dans des variables
# D'abord le script à signer
$Script = "C:\Scripts\Hello-World.ps1"
# Ensuite le certificat
$Certificat = Get-ChildItem -Path Cert:\CurrentUser\My -CodeSigningCert
# Finalement la commande de signature
Set-AuthenticodeSignature -FilePath $Script -Certificate $Certificat
# Si notre certificat est sécurisé par un mot de passe, alors ce dernier sera demandé pour valider la signature.
# Le retour console est alors :
Répertoire : C:\Scripts
SignerCertificate Status Path
----------------- ------ ----
DDDDCD0C34FE6993EBDA34F436ADAF1EF3ADBF37 Valid Hello-World.ps1
Ce script nouvellement signé pourra désormais être exécuté sur le système de manière sécurisée et ce, tant que sera valide la certificat utilisé pour la signature. Du coup, certains pourraient avoir envie de signer définitivement un script quelle que soit la durée de vie du certificat. Powershell nous en donne la possibilité via la variable -TimestampServer qui permet d'ajouter une date validé lors de la signature. Dans ce cas alors lorsque que la signature sera vérifié, elle le sera par rapport à la validité du certificat au moment de la signature. Cette variable nécessite de faire appel à un serveur spécifique, appelé Timestamp Server, mais Powershell ne peut y accéder que via HTTP et non HTTPS, ce qui à mon goût représente un risque. Cependant, une rapide recherche sur Internet permet de trouver des serveurs utilisables gratuitement.
La syntaxe devient alors :
# On stocke les différentes informations nécessaires dans des variables
# D'abord le script à signer
$Script = "C:\Scripts\Hello-World.ps1"
# Ensuite le certificat
$Certificat = Get-ChildItem -Path Cert:\CurrentUser\My -CodeSigningCert
# Puis le serveur d'horodatage
$Server = "http://time.certum.pl"
# Finalement la commande de signature
Set-AuthenticodeSignature -FilePath $Script -Certificate $Certificat -TimestampServer $Server
# Là encore, si notre certificat est sécurisé par un mot de passe, alors ce dernier sera demandé pour valider la signature.
# Le retour console est alors :
Répertoire : C:\Scripts
SignerCertificate Status Path
----------------- ------ ----
DDDDCD0C34FE6993EBDA34F436ADAF1EF3ADBF37 Valid Hello-World.ps1
Set-AuthenticodeSignature : Microsoft