А АTuesday, 16 November 2021

Подписываем PowerShell скрипт с помощью сертификата.


Всем привет.

Наличие цифровой подписи у скрипта или исполняемого файла позволяет пользователю удостовериться, что файл является оригинальным и его код не был изменен третьими лицами. В современных версиях PowerShell есть встроенные средства для подписывания кода файла скриптов *.ps1 с помощью цифровых сертификатов.

Для подписывания скриптов PowerShell нужно использовать специальный сертификат типа Code Signing. Этот сертификат может быть получен от внешнего коммерческого центра сертификации, внутреннего корпоративного Certificate Authority (CA) или можно даже самоподписанный сертификат.

Шаг 1 - сертификат.

В первую очередь нам нужно получить сертификат типа CodeSign из локального хранилища сертификатов текущего пользователя. Сначала выведем список всех сертификатов, которые можно использовать для подписывания кода:

Get-ChildItem Cert:\CurrentUser\My -CodeSigningCert

Возьмем первый сертификат и сохраним его в переменную $cert.

$cert = (Get-ChildItem cert:\CurrentUser\my –CodeSigningCert)[0]

Затем можно использовать данный сертификат, чтобы подписать файл PS1 с вашим скриптом PowerShell:

Set-AuthenticodeSignature MyTest.ps1 -Certificate $cert

Или

Set-AuthenticodeSignature -Certificate $cert -FilePath MyTest.ps1

Теперь можно проверить, что скрипт подписан. Можно использовать командлет Get-AuthenticodeSignature  или открыть свойства PS1 файла и перейдти на вкладку Digital Signatures: Get-AuthenticodeSignature MyTest.ps1 | ft -AutoSize

Если при выполнении команды Set-AuthenticodeSignature появится предупреждение  UnknownError, значит наш сертификат недоверенный, т.к. находится в персональном хранилище сертификатов пользователя. Нужно переместить его в корневые сертификаты:

Move-Item -Path $cert.PSPath -Destination "Cert:\LocalMachine\Root"

Хотя наш сертификат теперь из доверенного Центра Сертификации, но он не от доверенного издателя. Поэтому следует его также скопировать в раздел Trusted Publishers с помощью обычной операции Copy-Paste в консоли Certificates.

В качестве альтернативы для получения сертификатов подписи кода вы можете применять сторонние Центры Авторизации, например, DigiCert, которые по умолчанию обладают доверием со стороны Windows. В распространении доверенный сертификатов корневого Центра Авторизации способствует Программа Доверенного Корня Microsoft. Относительно дополнительных сведений о сертификатах подписи кода DigiCert обращайтесь к https://digicert.leaderssl.com/suppliers/digicert/products#codesigning-products. 

Если у вас наблюдются визуальные артефакты при чтении некоторых сертификатов то можно использовать такую функцию:

[Console]::OutputEncoding = [System.Text.Encoding]::GetEncoding("cp866")

function ConvertTo-Encoding ([string]$From, [string]$To){

Begin{

$encFrom = [System.Text.Encoding]::GetEncoding($from)

$encTo = [System.Text.Encoding]::GetEncoding($to)

}

Process{

$bytes = $encTo.GetBytes($_)

$bytes = [System.Text.Encoding]::Convert($encFrom, $encTo, $bytes)

$encTo.GetString($bytes)

}

}

Например так читаем все сертификаты которые станут просроченными через 60 дней:

(Get-ChildItem -Path cert: -Recurse -ExpiringInDays 60).subject | ConvertTo-Encoding cp866 windows-1251

Если вы внесете изменения в свой скрипт, то его нужно будет заново переподписать. Это очевидно.

Шаг 2 - политика.

Узнаем текущую политику исполнения скриптов:

Get-ExecutionPolicy

Чтобы разрешить запуск только подписанных PS1 скриптов, можно изменить настройку политики исполнения скриптов на AllSigned или RemoteSigned (разница между ними в том, что RemoteSigned требует наличие подписи только для скриптов, полученных из интернета):

Set-ExecutionPolicy AllSigned -Force

Set-ExecutionPolicy RemoteSigned -Force

Также можно использовать данный сертификат, чтобы подписать ЕХЕ-файл:

Set-AuthenticodeSignature D:\PortQry.exe -Certificate (Get-ChildItem Cert:\CurrentUser\My -CodeSigningCert)[1]

Get-AuthenticodeSignature D:\PortQry.exe | ft -AutoSize

Замечу что таким же образом dll и другие двоичные типы файлов тоже легко подписываются, т.е. утилита signtool теперь не нужна. Однако сам по себе ЕХЕ-файл выполнится в любом случае. Поэтому в этом есть смысл если вы разрешите запуск подписанных приложений по подписи издателя через AppLocker или Windows Defender Application Control.

Успехов.

No comments:

Post a Comment

А что вы думаете по этому поводу?

Версия на печать

Популярное