[ADVAPI32][SERVICES] Pass encrypted passwords to the service manager.

- Encrypt passwords before passing them to the service manager. Right now, we are using a fixed encryption key. This will be fixed later.
- Replace the calls to ZeroMemory which are used to wipe the password buffers by calls to SecureZeroMemory.
This commit is contained in:
Eric Kohl 2018-09-18 21:33:29 +02:00
parent da73c81259
commit e5fcda922b
2 changed files with 106 additions and 19 deletions

View file

@ -15,6 +15,20 @@
#define NDEBUG
#include <debug.h>
struct ustring
{
DWORD Length;
DWORD MaximumLength;
unsigned char *Buffer;
};
NTSTATUS
WINAPI
SystemFunction005(
const struct ustring *in,
const struct ustring *key,
struct ustring *out);
/* FUNCTIONS *****************************************************************/
@ -684,17 +698,51 @@ ScmDecryptPassword(
_In_ DWORD dwPasswordSize,
_Out_ PWSTR *pClearTextPassword)
{
struct ustring inData, keyData, outData;
PCHAR pszKey = "TestEncryptionKey";
PWSTR pBuffer;
NTSTATUS Status;
/* Allocate a buffer for the decrypted password */
pBuffer = HeapAlloc(GetProcessHeap(), 0, dwPasswordSize);
inData.Length = dwPasswordSize;
inData.MaximumLength = inData.Length;
inData.Buffer = pPassword;
keyData.Length = strlen(pszKey);
keyData.MaximumLength = keyData.Length;
keyData.Buffer = (unsigned char *)pszKey;
outData.Length = 0;
outData.MaximumLength = 0;
outData.Buffer = NULL;
/* Get the required buffer size */
Status = SystemFunction005(&inData,
&keyData,
&outData);
if (Status != STATUS_BUFFER_TOO_SMALL)
{
DPRINT1("SystemFunction005 failed (Status 0x%08lx)\n", Status);
return RtlNtStatusToDosError(Status);
}
/* Allocate a buffer for the clear text password */
pBuffer = HeapAlloc(GetProcessHeap(), 0, outData.Length);
if (pBuffer == NULL)
return ERROR_OUTOFMEMORY;
outData.MaximumLength = outData.Length;
outData.Buffer = (unsigned char *)pBuffer;
/* Decrypt the password */
CopyMemory(pBuffer,
pPassword,
dwPasswordSize);
Status = SystemFunction005(&inData,
&keyData,
&outData);
if (!NT_SUCCESS(Status))
{
DPRINT1("SystemFunction005 failed (Status 0x%08lx)\n", Status);
HeapFree(GetProcessHeap(), 0, pBuffer);
return RtlNtStatusToDosError(Status);
}
*pClearTextPassword = pBuffer;

View file

@ -12,6 +12,12 @@
#include <advapi32.h>
WINE_DEFAULT_DEBUG_CHANNEL(advapi);
NTSTATUS
WINAPI
SystemFunction004(
const struct ustring *in,
const struct ustring *key,
struct ustring *out);
/* FUNCTIONS *****************************************************************/
@ -162,21 +168,54 @@ ScmEncryptPassword(
_Out_ PBYTE *pEncryptedPassword,
_Out_ PDWORD pEncryptedPasswordSize)
{
DWORD dwSize;
struct ustring inData, keyData, outData;
PCHAR pszKey = "TestEncryptionKey";
PBYTE pBuffer;
NTSTATUS Status;
dwSize = (wcslen(pClearTextPassword) + 1) * sizeof(WCHAR);
inData.Length = (wcslen(pClearTextPassword) + 1) * sizeof(WCHAR);
inData.MaximumLength = inData.Length;
inData.Buffer = (unsigned char *)pClearTextPassword;
pBuffer = HeapAlloc(GetProcessHeap(), 0, dwSize);
keyData.Length = strlen(pszKey);
keyData.MaximumLength = keyData.Length;
keyData.Buffer = (unsigned char *)pszKey;
outData.Length = 0;
outData.MaximumLength = 0;
outData.Buffer = NULL;
/* Get the required buffer size */
Status = SystemFunction004(&inData,
&keyData,
&outData);
if (Status != STATUS_BUFFER_TOO_SMALL)
{
ERR("SystemFunction004 failed (Status 0x%08lx)\n", Status);
return RtlNtStatusToDosError(Status);
}
/* Allocate a buffer for the encrypted password */
pBuffer = HeapAlloc(GetProcessHeap(), 0, outData.Length);
if (pBuffer == NULL)
return ERROR_OUTOFMEMORY;
CopyMemory(pBuffer,
pClearTextPassword,
dwSize);
outData.MaximumLength = outData.Length;
outData.Buffer = pBuffer;
*pEncryptedPassword = pBuffer;
*pEncryptedPasswordSize = dwSize;
/* Encrypt the password */
Status = SystemFunction004(&inData,
&keyData,
&outData);
if (!NT_SUCCESS(Status))
{
ERR("SystemFunction004 failed (Status 0x%08lx)\n", Status);
HeapFree(GetProcessHeap(), 0, pBuffer);
return RtlNtStatusToDosError(Status);
}
*pEncryptedPassword = outData.Buffer;
*pEncryptedPasswordSize = outData.Length;
return ERROR_SUCCESS;
}
@ -395,12 +434,12 @@ done:
if (lpPasswordW != NULL)
{
/* Wipe and release the password buffers */
ZeroMemory(lpPasswordW, (wcslen(lpPasswordW) + 1) * sizeof(WCHAR));
SecureZeroMemory(lpPasswordW, (wcslen(lpPasswordW) + 1) * sizeof(WCHAR));
HeapFree(GetProcessHeap(), 0, lpPasswordW);
if (lpEncryptedPassword != NULL)
{
ZeroMemory(lpEncryptedPassword, dwPasswordSize);
SecureZeroMemory(lpEncryptedPassword, dwPasswordSize);
HeapFree(GetProcessHeap(), 0, lpEncryptedPassword);
}
}
@ -498,7 +537,7 @@ done:
if (lpEncryptedPassword != NULL)
{
/* Wipe and release the password buffer */
ZeroMemory(lpEncryptedPassword, dwPasswordSize);
SecureZeroMemory(lpEncryptedPassword, dwPasswordSize);
HeapFree(GetProcessHeap(), 0, lpEncryptedPassword);
}
@ -723,12 +762,12 @@ done:
if (lpPasswordW != NULL)
{
/* Wipe and release the password buffers */
ZeroMemory(lpPasswordW, (wcslen(lpPasswordW) + 1) * sizeof(WCHAR));
SecureZeroMemory(lpPasswordW, (wcslen(lpPasswordW) + 1) * sizeof(WCHAR));
HeapFree(GetProcessHeap(), 0, lpPasswordW);
if (lpEncryptedPassword != NULL)
{
ZeroMemory(lpEncryptedPassword, dwPasswordSize);
SecureZeroMemory(lpEncryptedPassword, dwPasswordSize);
HeapFree(GetProcessHeap(), 0, lpEncryptedPassword);
}
}
@ -837,7 +876,7 @@ done:
if (lpEncryptedPassword != NULL)
{
/* Wipe and release the password buffers */
ZeroMemory(lpEncryptedPassword, dwPasswordSize);
SecureZeroMemory(lpEncryptedPassword, dwPasswordSize);
HeapFree(GetProcessHeap(), 0, lpEncryptedPassword);
}