summaryrefslogtreecommitdiff
path: root/src/VBox/Additions/WINNT/VBoxCredProv/VBoxCredProvCredential.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/VBox/Additions/WINNT/VBoxCredProv/VBoxCredProvCredential.cpp')
-rw-r--r--src/VBox/Additions/WINNT/VBoxCredProv/VBoxCredProvCredential.cpp177
1 files changed, 108 insertions, 69 deletions
diff --git a/src/VBox/Additions/WINNT/VBoxCredProv/VBoxCredProvCredential.cpp b/src/VBox/Additions/WINNT/VBoxCredProv/VBoxCredProvCredential.cpp
index ef3e7264..c373ace7 100644
--- a/src/VBox/Additions/WINNT/VBoxCredProv/VBoxCredProvCredential.cpp
+++ b/src/VBox/Additions/WINNT/VBoxCredProv/VBoxCredProvCredential.cpp
@@ -22,6 +22,7 @@
# include <ntstatus.h>
# define WIN32_NO_STATUS
#endif
+#include <intsafe.h>
#include "VBoxCredentialProvider.h"
@@ -37,10 +38,12 @@
+
VBoxCredProvCredential::VBoxCredProvCredential(void) :
m_enmUsageScenario(CPUS_INVALID),
m_cRefs(1),
- m_pEvents(NULL)
+ m_pEvents(NULL),
+ m_fHaveCreds(false)
{
VBoxCredProvVerbose(0, "VBoxCredProvCredential: Created\n");
VBoxCredentialProviderAcquire();
@@ -124,20 +127,33 @@ VBoxCredProvCredential::QueryInterface(REFIID interfaceID, void **ppvInterface)
HRESULT
VBoxCredProvCredential::RTUTF16ToUnicode(PUNICODE_STRING pUnicodeDest, PRTUTF16 pwszSource, bool fCopy)
{
- AssertPtrReturn(pUnicodeDest, VERR_INVALID_POINTER);
- AssertPtrReturn(pwszSource, VERR_INVALID_POINTER);
+ AssertPtrReturn(pUnicodeDest, E_POINTER);
+ AssertPtrReturn(pwszSource, E_POINTER);
size_t cbLen = RTUtf16Len(pwszSource) * sizeof(RTUTF16);
+ AssertReturn(cbLen <= USHORT_MAX, E_INVALIDARG);
- pUnicodeDest->Length = cbLen;
- pUnicodeDest->MaximumLength = pUnicodeDest->Length;
+ HRESULT hr;
if (fCopy)
- memcpy(pUnicodeDest->Buffer, pwszSource, cbLen);
+ {
+ if (cbLen <= pUnicodeDest->MaximumLength)
+ {
+ memcpy(pUnicodeDest->Buffer, pwszSource, cbLen);
+ pUnicodeDest->Length = (USHORT)cbLen;
+ hr = S_OK;
+ }
+ else
+ hr = E_INVALIDARG;
+ }
else /* Just assign the buffer. */
- pUnicodeDest->Buffer = pwszSource;
+ {
+ pUnicodeDest->Buffer = pwszSource;
+ pUnicodeDest->Length = (USHORT)cbLen;
+ hr = S_OK;
+ }
- return S_OK;
+ return hr;
}
@@ -337,6 +353,18 @@ VBoxCredProvCredential::RetrieveCredentials(void)
m_apwszCredentials[VBOXCREDPROV_FIELDID_DOMAINNAME]);
}
}
+
+ m_fHaveCreds = true;
+ }
+ else
+ {
+ /* If credentials already were retrieved by a former call, don't try to retrieve new ones
+ * and just report back the already retrieved ones. */
+ if (m_fHaveCreds)
+ {
+ VBoxCredProvVerbose(0, "VBoxCredProvCredential::RetrieveCredentials: Credentials already retrieved\n");
+ rc = VINF_SUCCESS;
+ }
}
VBoxCredProvVerbose(0, "VBoxCredProvCredential::RetrieveCredentials: Returned rc=%Rrc\n", rc);
@@ -601,7 +629,7 @@ VBoxCredProvCredential::ExtractAccoutData(PWSTR pwszAccountData, PWSTR *ppwszAcc
if ( (pPos = StrChrW(pwszAccountData, L'@')) != NULL
&& pPos != pwszAccountData)
{
- DWORD cbSize = (pPos - pwszAccountData) * sizeof(WCHAR);
+ size_t cbSize = (pPos - pwszAccountData) * sizeof(WCHAR);
LPWSTR pwszName = (LPWSTR)CoTaskMemAlloc(cbSize + sizeof(WCHAR)); /* Space for terminating zero. */
LPWSTR pwszDomain = NULL;
AssertPtr(pwszName);
@@ -869,94 +897,105 @@ VBoxCredProvCredential::GetSerialization(CREDENTIAL_PROVIDER_GET_SERIALIZATION_R
hr = HRESULT_FROM_WIN32(GetLastError());
}
+ /* Fill in the username and password. */
if (SUCCEEDED(hr))
{
- /* Fill in the username and password. */
+ hr = RTUTF16ToUnicode(&pKerberosLogon->UserName,
+ m_apwszCredentials[VBOXCREDPROV_FIELDID_USERNAME],
+ false /* Just assign, no copy */);
if (SUCCEEDED(hr))
{
- hr = RTUTF16ToUnicode(&pKerberosLogon->UserName,
- m_apwszCredentials[VBOXCREDPROV_FIELDID_USERNAME],
+ hr = RTUTF16ToUnicode(&pKerberosLogon->Password,
+ m_apwszCredentials[VBOXCREDPROV_FIELDID_PASSWORD],
false /* Just assign, no copy */);
if (SUCCEEDED(hr))
{
- hr = RTUTF16ToUnicode(&pKerberosLogon->Password,
- m_apwszCredentials[VBOXCREDPROV_FIELDID_PASSWORD],
- false /* Just assign, no copy */);
- if (SUCCEEDED(hr))
+ /* Set credential type according to current usage scenario. */
+ AssertPtr(pKerberosLogon);
+ switch (m_enmUsageScenario)
{
- /* Set credential type according to current usage scenario. */
- AssertPtr(pKerberosLogon);
- switch (m_enmUsageScenario)
- {
- case CPUS_UNLOCK_WORKSTATION:
- pKerberosLogon->MessageType = KerbWorkstationUnlockLogon;
- break;
+ case CPUS_UNLOCK_WORKSTATION:
+ pKerberosLogon->MessageType = KerbWorkstationUnlockLogon;
+ break;
- case CPUS_LOGON:
- pKerberosLogon->MessageType = KerbInteractiveLogon;
- break;
+ case CPUS_LOGON:
+ pKerberosLogon->MessageType = KerbInteractiveLogon;
+ break;
- case CPUS_CREDUI:
- pKerberosLogon->MessageType = (KERB_LOGON_SUBMIT_TYPE)0; /* No message type required here. */
- break;
+ case CPUS_CREDUI:
+ pKerberosLogon->MessageType = (KERB_LOGON_SUBMIT_TYPE)0; /* No message type required here. */
+ break;
- default:
- hr = E_FAIL;
- break;
- }
+ default:
+ hr = E_FAIL;
+ break;
+ }
- if (SUCCEEDED(hr)) /* Build the logon package. */
- hr = AllocateLogonPackage(KerberosUnlockLogon,
- &pcpCredentialSerialization->rgbSerialization,
- &pcpCredentialSerialization->cbSerialization);
+ if (FAILED(hr))
+ VBoxCredProvVerbose(0, "VBoxCredProvCredential::GetSerialization: Unknown usage scenario=%ld\n", m_enmUsageScenario);
- if (SUCCEEDED(hr))
- {
- ULONG ulAuthPackage;
+ if (SUCCEEDED(hr)) /* Build the logon package. */
+ {
+ hr = AllocateLogonPackage(KerberosUnlockLogon,
+ &pcpCredentialSerialization->rgbSerialization,
+ &pcpCredentialSerialization->cbSerialization);
+ if (FAILED(hr))
+ VBoxCredProvVerbose(0, "VBoxCredProvCredential::GetSerialization: Failed to allocate logon package, hr=0x%08x\n", hr);
+ }
- HANDLE hLsa;
- NTSTATUS s = LsaConnectUntrusted(&hLsa);
- if (SUCCEEDED(HRESULT_FROM_NT(s)))
+ if (SUCCEEDED(hr))
+ {
+ ULONG ulAuthPackage;
+
+ HANDLE hLsa;
+ NTSTATUS s = LsaConnectUntrusted(&hLsa);
+ if (SUCCEEDED(HRESULT_FROM_NT(s)))
+ {
+ LSA_STRING lsaszKerberosName;
+ size_t cchKerberosName;
+ hr = StringCchLengthA(NEGOSSP_NAME_A, USHORT_MAX, &cchKerberosName);
+ if (SUCCEEDED(hr))
{
- LSA_STRING lsaszKerberosName;
- size_t cchKerberosName;
- hr = StringCchLengthA(NEGOSSP_NAME_A, USHORT_MAX, &cchKerberosName);
+ USHORT usLength;
+ hr = SizeTToUShort(cchKerberosName, &usLength);
if (SUCCEEDED(hr))
{
- USHORT usLength;
- hr = SizeTToUShort(cchKerberosName, &usLength);
- if (SUCCEEDED(hr))
- {
- lsaszKerberosName.Buffer = (PCHAR)NEGOSSP_NAME_A;
- lsaszKerberosName.Length = usLength;
- lsaszKerberosName.MaximumLength = lsaszKerberosName.Length + 1;
-
- }
- }
+ lsaszKerberosName.Buffer = (PCHAR)NEGOSSP_NAME_A;
+ lsaszKerberosName.Length = usLength;
+ lsaszKerberosName.MaximumLength = lsaszKerberosName.Length + 1;
- if (SUCCEEDED(hr))
- {
- s = LsaLookupAuthenticationPackage(hLsa, &lsaszKerberosName,
- &ulAuthPackage);
- if (FAILED(HRESULT_FROM_NT(s)))
- hr = HRESULT_FROM_NT(s);
}
-
- LsaDeregisterLogonProcess(hLsa);
}
if (SUCCEEDED(hr))
{
- pcpCredentialSerialization->ulAuthenticationPackage = ulAuthPackage;
- pcpCredentialSerialization->clsidCredentialProvider = CLSID_VBoxCredProvider;
-
- /* We're done -- let the logon UI know. */
- *pcpGetSerializationResponse = CPGSR_RETURN_CREDENTIAL_FINISHED;
+ s = LsaLookupAuthenticationPackage(hLsa, &lsaszKerberosName,
+ &ulAuthPackage);
+ if (FAILED(HRESULT_FROM_NT(s)))
+ {
+ hr = HRESULT_FROM_NT(s);
+ VBoxCredProvVerbose(0, "VBoxCredProvCredential::GetSerialization: Failed looking up authentication package, hr=0x%08x\n", hr);
+ }
}
+
+ LsaDeregisterLogonProcess(hLsa);
+ }
+
+ if (SUCCEEDED(hr))
+ {
+ pcpCredentialSerialization->ulAuthenticationPackage = ulAuthPackage;
+ pcpCredentialSerialization->clsidCredentialProvider = CLSID_VBoxCredProvider;
+
+ /* We're done -- let the logon UI know. */
+ *pcpGetSerializationResponse = CPGSR_RETURN_CREDENTIAL_FINISHED;
}
}
}
+ else
+ VBoxCredProvVerbose(0, "VBoxCredProvCredential::GetSerialization: Error copying password, hr=0x%08x\n", hr);
}
+ else
+ VBoxCredProvVerbose(0, "VBoxCredProvCredential::GetSerialization: Error copying user name, hr=0x%08x\n", hr);
}
VBoxCredProvVerbose(0, "VBoxCredProvCredential::GetSerialization returned hr=0x%08x\n", hr);