mirror of
https://github.com/reactos/reactos.git
synced 2025-08-05 09:23:06 +00:00
- Sync to date wine AdvApi32 cross tests.
svn path=/trunk/; revision=37982
This commit is contained in:
parent
2291d9b3b4
commit
339bbdd5bf
5 changed files with 614 additions and 198 deletions
|
@ -97,12 +97,19 @@ static void test_CredWriteA(void)
|
||||||
|
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = pCredWriteA(&new_cred, 0);
|
ret = pCredWriteA(&new_cred, 0);
|
||||||
ok(!ret, "CredWrite with username without domain should have failed\n");
|
if (ret)
|
||||||
ok(GetLastError() == ERROR_BAD_USERNAME ||
|
{
|
||||||
GetLastError() == ERROR_NO_SUCH_LOGON_SESSION || /* Vista */
|
/* Vista */
|
||||||
broken(GetLastError() == ERROR_IO_PENDING),
|
ok(GetLastError() == ERROR_IO_PENDING,
|
||||||
"CredWrite with username without domain should return ERROR_BAD_USERNAME"
|
"Expected ERROR_IO_PENDING, got %d\n", GetLastError());
|
||||||
"or ERROR_NO_SUCH_LOGON_SESSION not %d\n", GetLastError());
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
ok(GetLastError() == ERROR_BAD_USERNAME ||
|
||||||
|
GetLastError() == ERROR_NO_SUCH_LOGON_SESSION, /* Vista */
|
||||||
|
"CredWrite with username without domain should return ERROR_BAD_USERNAME"
|
||||||
|
"or ERROR_NO_SUCH_LOGON_SESSION not %d\n", GetLastError());
|
||||||
|
}
|
||||||
|
|
||||||
new_cred.UserName = NULL;
|
new_cred.UserName = NULL;
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
|
|
|
@ -274,11 +274,11 @@ static void test_incorrect_api_usage(void)
|
||||||
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
||||||
|
|
||||||
dwLen = 1;
|
dwLen = 1;
|
||||||
result = pCryptDecrypt(hKey, (HCRYPTHASH)NULL, TRUE, 0, &temp, &dwLen);
|
result = pCryptDecrypt(hKey, 0, TRUE, 0, &temp, &dwLen);
|
||||||
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
||||||
|
|
||||||
dwLen = 1;
|
dwLen = 1;
|
||||||
result = pCryptEncrypt(hKey, (HCRYPTHASH)NULL, TRUE, 0, &temp, &dwLen, 1);
|
result = pCryptEncrypt(hKey, 0, TRUE, 0, &temp, &dwLen, 1);
|
||||||
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
||||||
|
|
||||||
result = pCryptDeriveKey(hProv, CALG_RC4, hHash, 0, &hKey2);
|
result = pCryptDeriveKey(hProv, CALG_RC4, hHash, 0, &hKey2);
|
||||||
|
@ -293,7 +293,7 @@ static void test_incorrect_api_usage(void)
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
dwLen = 1;
|
dwLen = 1;
|
||||||
result = pCryptExportKey(hKey, (HCRYPTPROV)NULL, 0, 0, &temp, &dwLen);
|
result = pCryptExportKey(hKey, 0, 0, 0, &temp, &dwLen);
|
||||||
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
||||||
|
|
||||||
result = pCryptGenKey(hProv, CALG_RC4, 0, &hKey2);
|
result = pCryptGenKey(hProv, CALG_RC4, 0, &hKey2);
|
||||||
|
@ -320,7 +320,7 @@ static void test_incorrect_api_usage(void)
|
||||||
result = pCryptHashSessionKey(hHash, hKey, 0);
|
result = pCryptHashSessionKey(hHash, hKey, 0);
|
||||||
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
||||||
|
|
||||||
result = pCryptImportKey(hProv, &temp, 1, (HCRYPTKEY)NULL, 0, &hKey2);
|
result = pCryptImportKey(hProv, &temp, 1, 0, 0, &hKey2);
|
||||||
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
ok (!result && GetLastError() == ERROR_INVALID_PARAMETER, "%d\n", GetLastError());
|
||||||
|
|
||||||
if (pCryptSignHashW)
|
if (pCryptSignHashW)
|
||||||
|
@ -560,59 +560,77 @@ static void test_enum_providers(void)
|
||||||
LocalFree(provider);
|
LocalFree(provider);
|
||||||
}
|
}
|
||||||
|
|
||||||
static BOOL FindProvTypesRegVals(DWORD dwIndex, DWORD *pdwProvType, LPSTR *pszTypeName,
|
static BOOL FindProvTypesRegVals(DWORD *pdwIndex, DWORD *pdwProvType, LPSTR *pszTypeName,
|
||||||
DWORD *pcbTypeName, DWORD *pdwTypeCount)
|
DWORD *pcbTypeName, DWORD *pdwTypeCount)
|
||||||
{
|
{
|
||||||
HKEY hKey;
|
HKEY hKey;
|
||||||
HKEY hSubKey;
|
HKEY hSubKey;
|
||||||
PSTR ch;
|
PSTR ch;
|
||||||
|
LPSTR szName;
|
||||||
|
DWORD cbName;
|
||||||
|
BOOL ret = FALSE;
|
||||||
|
|
||||||
if (RegOpenKey(HKEY_LOCAL_MACHINE, "Software\\Microsoft\\Cryptography\\Defaults\\Provider Types", &hKey))
|
if (RegOpenKey(HKEY_LOCAL_MACHINE, "Software\\Microsoft\\Cryptography\\Defaults\\Provider Types", &hKey))
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
if (RegQueryInfoKey(hKey, NULL, NULL, NULL, pdwTypeCount, pcbTypeName, NULL,
|
|
||||||
NULL, NULL, NULL, NULL, NULL))
|
|
||||||
return FALSE;
|
|
||||||
(*pcbTypeName)++;
|
|
||||||
|
|
||||||
if (!(*pszTypeName = ((LPSTR)LocalAlloc(LMEM_ZEROINIT, *pcbTypeName))))
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
if (RegEnumKeyEx(hKey, dwIndex, *pszTypeName, pcbTypeName, NULL, NULL, NULL, NULL))
|
|
||||||
return FALSE;
|
|
||||||
(*pcbTypeName)++;
|
|
||||||
ch = *pszTypeName + strlen(*pszTypeName);
|
|
||||||
/* Convert "Type 000" to 0, etc/ */
|
|
||||||
*pdwProvType = *(--ch) - '0';
|
|
||||||
*pdwProvType += (*(--ch) - '0') * 10;
|
|
||||||
*pdwProvType += (*(--ch) - '0') * 100;
|
|
||||||
|
|
||||||
if (RegOpenKey(hKey, *pszTypeName, &hSubKey))
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
if (RegQueryValueEx(hSubKey, "TypeName", NULL, NULL, NULL, pcbTypeName))
|
|
||||||
return FALSE;
|
|
||||||
|
|
||||||
if (!(*pszTypeName = ((LPSTR)LocalAlloc(LMEM_ZEROINIT, *pcbTypeName))))
|
if (RegQueryInfoKey(hKey, NULL, NULL, NULL, pdwTypeCount, &cbName, NULL,
|
||||||
return FALSE;
|
NULL, NULL, NULL, NULL, NULL))
|
||||||
|
goto cleanup;
|
||||||
if (RegQueryValueEx(hSubKey, "TypeName", NULL, NULL, (LPBYTE)*pszTypeName, pcbTypeName))
|
cbName++;
|
||||||
return FALSE;
|
|
||||||
|
if (!(szName = LocalAlloc(LMEM_ZEROINIT, cbName)))
|
||||||
|
goto cleanup;
|
||||||
|
|
||||||
|
while (!RegEnumKeyEx(hKey, *pdwIndex, szName, &cbName, NULL, NULL, NULL, NULL))
|
||||||
|
{
|
||||||
|
cbName++;
|
||||||
|
ch = szName + strlen(szName);
|
||||||
|
/* Convert "Type 000" to 0, etc/ */
|
||||||
|
*pdwProvType = *(--ch) - '0';
|
||||||
|
*pdwProvType += (*(--ch) - '0') * 10;
|
||||||
|
*pdwProvType += (*(--ch) - '0') * 100;
|
||||||
|
|
||||||
|
if (RegOpenKey(hKey, szName, &hSubKey))
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (!RegQueryValueEx(hSubKey, "TypeName", NULL, NULL, NULL, pcbTypeName))
|
||||||
|
{
|
||||||
|
if (!(*pszTypeName = LocalAlloc(LMEM_ZEROINIT, *pcbTypeName)))
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (!RegQueryValueEx(hSubKey, "TypeName", NULL, NULL, (LPBYTE)*pszTypeName, pcbTypeName))
|
||||||
|
{
|
||||||
|
ret = TRUE;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
LocalFree(*pszTypeName);
|
||||||
|
}
|
||||||
|
|
||||||
|
RegCloseKey(hSubKey);
|
||||||
|
|
||||||
|
(*pdwIndex)++;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!ret)
|
||||||
|
LocalFree(*pszTypeName);
|
||||||
RegCloseKey(hSubKey);
|
RegCloseKey(hSubKey);
|
||||||
|
LocalFree(szName);
|
||||||
|
|
||||||
|
cleanup:
|
||||||
RegCloseKey(hKey);
|
RegCloseKey(hKey);
|
||||||
|
|
||||||
return TRUE;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void test_enum_provider_types(void)
|
static void test_enum_provider_types(void)
|
||||||
{
|
{
|
||||||
/* expected values */
|
/* expected values */
|
||||||
DWORD dwProvType;
|
DWORD dwProvType = 0;
|
||||||
LPSTR pszTypeName = NULL;
|
LPSTR pszTypeName = NULL;
|
||||||
DWORD cbTypeName;
|
DWORD cbTypeName;
|
||||||
DWORD dwTypeCount;
|
DWORD dwTypeCount;
|
||||||
|
|
||||||
/* actual values */
|
/* actual values */
|
||||||
DWORD index = 0;
|
DWORD index = 0;
|
||||||
DWORD provType;
|
DWORD provType;
|
||||||
|
@ -622,45 +640,47 @@ static void test_enum_provider_types(void)
|
||||||
DWORD result;
|
DWORD result;
|
||||||
DWORD notNull = 5;
|
DWORD notNull = 5;
|
||||||
DWORD notZeroFlags = 5;
|
DWORD notZeroFlags = 5;
|
||||||
|
|
||||||
if(!pCryptEnumProviderTypesA)
|
if(!pCryptEnumProviderTypesA)
|
||||||
{
|
{
|
||||||
skip("CryptEnumProviderTypesA is not available\n");
|
skip("CryptEnumProviderTypesA is not available\n");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!FindProvTypesRegVals(index, &dwProvType, &pszTypeName, &cbTypeName, &dwTypeCount))
|
if (!FindProvTypesRegVals(&index, &dwProvType, &pszTypeName, &cbTypeName, &dwTypeCount))
|
||||||
{
|
{
|
||||||
skip("Could not find provider types in registry\n");
|
skip("Could not find provider types in registry\n");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* check pdwReserved for NULL */
|
/* check pdwReserved for NULL */
|
||||||
result = pCryptEnumProviderTypesA(index, ¬Null, 0, &provType, typeName, &typeNameSize);
|
result = pCryptEnumProviderTypesA(index, ¬Null, 0, &provType, typeName, &typeNameSize);
|
||||||
ok(!result && GetLastError()==ERROR_INVALID_PARAMETER, "expected %i, got %d\n",
|
ok(!result && GetLastError()==ERROR_INVALID_PARAMETER, "expected ERROR_INVALID_PARAMETER, got %d\n",
|
||||||
ERROR_INVALID_PARAMETER, GetLastError());
|
GetLastError());
|
||||||
|
|
||||||
/* check dwFlags == zero */
|
/* check dwFlags == zero */
|
||||||
result = pCryptEnumProviderTypesA(index, NULL, notZeroFlags, &provType, typeName, &typeNameSize);
|
result = pCryptEnumProviderTypesA(index, NULL, notZeroFlags, &provType, typeName, &typeNameSize);
|
||||||
ok(!result && GetLastError()==NTE_BAD_FLAGS, "expected %i, got %d\n",
|
ok(!result && GetLastError()==NTE_BAD_FLAGS, "expected ERROR_INVALID_PARAMETER, got %d\n",
|
||||||
ERROR_INVALID_PARAMETER, GetLastError());
|
GetLastError());
|
||||||
|
|
||||||
/* alloc provider type to half the size required
|
|
||||||
* cbTypeName holds the size required */
|
|
||||||
typeNameSize = cbTypeName / 2;
|
|
||||||
if (!(typeName = ((LPSTR)LocalAlloc(LMEM_ZEROINIT, typeNameSize))))
|
|
||||||
return;
|
|
||||||
|
|
||||||
/* This test fails under Win2k SP4:
|
/* This test fails under Win2k SP4:
|
||||||
result = TRUE, GetLastError() == 0xdeadbeef
|
* result = TRUE, GetLastError() == 0xdeadbeef */
|
||||||
SetLastError(0xdeadbeef);
|
if (0)
|
||||||
result = pCryptEnumProviderTypesA(index, NULL, 0, &provType, typeName, &typeNameSize);
|
{
|
||||||
ok(!result && GetLastError()==ERROR_MORE_DATA, "expected 0/ERROR_MORE_DATA, got %d/%08lx\n",
|
/* alloc provider type to half the size required
|
||||||
result, GetLastError());
|
* cbTypeName holds the size required */
|
||||||
*/
|
typeNameSize = cbTypeName / 2;
|
||||||
|
if (!(typeName = ((LPSTR)LocalAlloc(LMEM_ZEROINIT, typeNameSize))))
|
||||||
LocalFree(typeName);
|
goto cleanup;
|
||||||
|
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
result = pCryptEnumProviderTypesA(index, NULL, 0, &provType, typeName, &typeNameSize);
|
||||||
|
ok(!result && GetLastError()==ERROR_MORE_DATA, "expected 0/ERROR_MORE_DATA, got %d/%d\n",
|
||||||
|
result, GetLastError());
|
||||||
|
|
||||||
|
LocalFree(typeName);
|
||||||
|
}
|
||||||
|
|
||||||
/* loop through the provider types to get the number of provider types
|
/* loop through the provider types to get the number of provider types
|
||||||
* after loop ends, count should be dwTypeCount + 1 so subtract 1
|
* after loop ends, count should be dwTypeCount + 1 so subtract 1
|
||||||
* to get actual number of provider types */
|
* to get actual number of provider types */
|
||||||
|
@ -669,30 +689,31 @@ static void test_enum_provider_types(void)
|
||||||
;
|
;
|
||||||
typeCount--;
|
typeCount--;
|
||||||
ok(typeCount==dwTypeCount, "expected %d, got %d\n", dwTypeCount, typeCount);
|
ok(typeCount==dwTypeCount, "expected %d, got %d\n", dwTypeCount, typeCount);
|
||||||
|
|
||||||
/* loop past the actual number of provider types to get the error
|
/* loop past the actual number of provider types to get the error
|
||||||
* ERROR_NO_MORE_ITEMS */
|
* ERROR_NO_MORE_ITEMS */
|
||||||
for (typeCount = 0; typeCount < dwTypeCount + 1; typeCount++)
|
for (typeCount = 0; typeCount < dwTypeCount + 1; typeCount++)
|
||||||
result = pCryptEnumProviderTypesA(typeCount, NULL, 0, &provType, NULL, &typeNameSize);
|
result = pCryptEnumProviderTypesA(typeCount, NULL, 0, &provType, NULL, &typeNameSize);
|
||||||
ok(!result && GetLastError()==ERROR_NO_MORE_ITEMS, "expected %i, got %d\n",
|
ok(!result && GetLastError()==ERROR_NO_MORE_ITEMS, "expected ERROR_NO_MORE_ITEMS, got %d\n",
|
||||||
ERROR_NO_MORE_ITEMS, GetLastError());
|
GetLastError());
|
||||||
|
|
||||||
|
|
||||||
/* check expected versus actual values returned */
|
/* check expected versus actual values returned */
|
||||||
result = pCryptEnumProviderTypesA(index, NULL, 0, &provType, NULL, &typeNameSize);
|
result = pCryptEnumProviderTypesA(index, NULL, 0, &provType, NULL, &typeNameSize);
|
||||||
ok(result && typeNameSize==cbTypeName, "expected %d, got %d\n", cbTypeName, typeNameSize);
|
ok(result && typeNameSize==cbTypeName, "expected %d, got %d\n", cbTypeName, typeNameSize);
|
||||||
if (!(typeName = ((LPSTR)LocalAlloc(LMEM_ZEROINIT, typeNameSize))))
|
if (!(typeName = ((LPSTR)LocalAlloc(LMEM_ZEROINIT, typeNameSize))))
|
||||||
return;
|
goto cleanup;
|
||||||
|
|
||||||
typeNameSize = 0xdeadbeef;
|
typeNameSize = 0xdeadbeef;
|
||||||
result = pCryptEnumProviderTypesA(index, NULL, 0, &provType, typeName, &typeNameSize);
|
result = pCryptEnumProviderTypesA(index, NULL, 0, &provType, typeName, &typeNameSize);
|
||||||
ok(result, "expected TRUE, got %d\n", result);
|
ok(result, "expected TRUE, got %d\n", result);
|
||||||
ok(provType==dwProvType, "expected %d, got %d\n", dwProvType, provType);
|
ok(provType==dwProvType, "expected %d, got %d\n", dwProvType, provType);
|
||||||
if (pszTypeName)
|
if (pszTypeName)
|
||||||
ok(!strcmp(pszTypeName, typeName), "expected %s, got %s\n", pszTypeName, typeName);
|
ok(!strcmp(pszTypeName, typeName), "expected %s, got %s\n", pszTypeName, typeName);
|
||||||
ok(typeNameSize==cbTypeName, "expected %d, got %d\n", cbTypeName, typeNameSize);
|
ok(typeNameSize==cbTypeName, "expected %d, got %d\n", cbTypeName, typeNameSize);
|
||||||
|
|
||||||
LocalFree(typeName);
|
LocalFree(typeName);
|
||||||
|
cleanup:
|
||||||
|
LocalFree(pszTypeName);
|
||||||
}
|
}
|
||||||
|
|
||||||
static BOOL FindDfltProvRegVals(DWORD dwProvType, DWORD dwFlags, LPSTR *pszProvName, DWORD *pcbProvName)
|
static BOOL FindDfltProvRegVals(DWORD dwProvType, DWORD dwFlags, LPSTR *pszProvName, DWORD *pcbProvName)
|
||||||
|
|
|
@ -199,13 +199,14 @@ static void setup_main_key(void)
|
||||||
assert (!RegCreateKeyA( HKEY_CURRENT_USER, "Software\\Wine\\Test", &hkey_main ));
|
assert (!RegCreateKeyA( HKEY_CURRENT_USER, "Software\\Wine\\Test", &hkey_main ));
|
||||||
}
|
}
|
||||||
|
|
||||||
static void test_hkey_main_Value_A(LPCSTR name, LPCSTR string,
|
#define lok ok_(__FILE__, line)
|
||||||
|
#define test_hkey_main_Value_A(name, string, full_byte_len) _test_hkey_main_Value_A(__LINE__, name, string, full_byte_len)
|
||||||
|
static void _test_hkey_main_Value_A(int line, LPCSTR name, LPCSTR string,
|
||||||
DWORD full_byte_len)
|
DWORD full_byte_len)
|
||||||
{
|
{
|
||||||
DWORD ret, type, cbData;
|
DWORD ret, type, cbData;
|
||||||
DWORD str_byte_len;
|
DWORD str_byte_len;
|
||||||
LPSTR value;
|
BYTE* value;
|
||||||
static const char nA[]={'N', 0};
|
|
||||||
|
|
||||||
type=0xdeadbeef;
|
type=0xdeadbeef;
|
||||||
cbData=0xdeadbeef;
|
cbData=0xdeadbeef;
|
||||||
|
@ -215,43 +216,44 @@ static void test_hkey_main_Value_A(LPCSTR name, LPCSTR string,
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = RegQueryValueExA(hkey_main, name, NULL, &type, NULL, &cbData);
|
ret = RegQueryValueExA(hkey_main, name, NULL, &type, NULL, &cbData);
|
||||||
GLE = GetLastError();
|
GLE = GetLastError();
|
||||||
ok(ret == ERROR_SUCCESS, "RegQueryValueExA failed: %d, GLE=%d\n", ret, GLE);
|
lok(ret == ERROR_SUCCESS, "RegQueryValueExA/1 failed: %d, GLE=%d\n", ret, GLE);
|
||||||
/* It is wrong for the Ansi version to not be implemented */
|
/* It is wrong for the Ansi version to not be implemented */
|
||||||
ok(GLE == 0xdeadbeef, "RegQueryValueExA set GLE = %u\n", GLE);
|
ok(GLE == 0xdeadbeef, "RegQueryValueExA set GLE = %u\n", GLE);
|
||||||
if(GLE == ERROR_CALL_NOT_IMPLEMENTED) return;
|
if(GLE == ERROR_CALL_NOT_IMPLEMENTED) return;
|
||||||
|
|
||||||
str_byte_len = (string ? lstrlenA(string) : 0) + 1;
|
str_byte_len = (string ? lstrlenA(string) : 0) + 1;
|
||||||
ok(type == REG_SZ, "RegQueryValueExA returned type %d\n", type);
|
lok(type == REG_SZ, "RegQueryValueExA/1 returned type %d\n", type);
|
||||||
ok(cbData == full_byte_len || cbData == str_byte_len /* Win9x */,
|
lok(cbData == full_byte_len || cbData == str_byte_len /* Win9x */,
|
||||||
"cbData=%d instead of %d or %d\n", cbData, full_byte_len, str_byte_len);
|
"cbData=%d instead of %d or %d\n", cbData, full_byte_len, str_byte_len);
|
||||||
|
|
||||||
value = HeapAlloc(GetProcessHeap(), 0, (cbData+2)*sizeof(*value));
|
value = HeapAlloc(GetProcessHeap(), 0, cbData+1);
|
||||||
strcpy(value, nA);
|
memset(value, 0xbd, cbData+1);
|
||||||
type=0xdeadbeef;
|
type=0xdeadbeef;
|
||||||
ret = RegQueryValueExA(hkey_main, name, NULL, &type, (BYTE*)value, &cbData);
|
ret = RegQueryValueExA(hkey_main, name, NULL, &type, value, &cbData);
|
||||||
GLE = GetLastError();
|
GLE = GetLastError();
|
||||||
ok(ret == ERROR_SUCCESS, "RegQueryValueExA failed: %d, GLE=%d\n", ret, GLE);
|
lok(ret == ERROR_SUCCESS, "RegQueryValueExA/2 failed: %d, GLE=%d\n", ret, GLE);
|
||||||
if (!string)
|
if (!string)
|
||||||
{
|
{
|
||||||
/* When cbData == 0, RegQueryValueExA() should not modify the buffer */
|
/* When cbData == 0, RegQueryValueExA() should not modify the buffer */
|
||||||
ok(strcmp(value, nA) == 0 || (cbData == 1 && *value == '\0') /* Win9x */,
|
lok(*value == 0xbd || (cbData == 1 && *value == '\0') /* Win9x */,
|
||||||
"RegQueryValueExA failed: '%s' != '%s'\n", value, string);
|
"RegQueryValueExA overflowed: cbData=%u *value=%02x\n", cbData, *value);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
ok(memcmp(value, string, cbData) == 0, "RegQueryValueExA failed: %s/%d != %s/%d\n",
|
lok(memcmp(value, string, cbData) == 0, "RegQueryValueExA/2 failed: %s/%d != %s/%d\n",
|
||||||
wine_debugstr_an(value, cbData), cbData,
|
wine_debugstr_an((char*)value, cbData), cbData,
|
||||||
wine_debugstr_an(string, full_byte_len), full_byte_len);
|
wine_debugstr_an(string, full_byte_len), full_byte_len);
|
||||||
|
lok(*(value+cbData) == 0xbd, "RegQueryValueExA/2 overflowed at offset %u: %02x != bd\n", cbData, *(value+cbData));
|
||||||
}
|
}
|
||||||
HeapFree(GetProcessHeap(), 0, value);
|
HeapFree(GetProcessHeap(), 0, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void test_hkey_main_Value_W(LPCWSTR name, LPCWSTR string,
|
#define test_hkey_main_Value_W(name, string, full_byte_len) _test_hkey_main_Value_W(__LINE__, name, string, full_byte_len)
|
||||||
|
static void _test_hkey_main_Value_W(int line, LPCWSTR name, LPCWSTR string,
|
||||||
DWORD full_byte_len)
|
DWORD full_byte_len)
|
||||||
{
|
{
|
||||||
DWORD ret, type, cbData;
|
DWORD ret, type, cbData;
|
||||||
LPWSTR value;
|
BYTE* value;
|
||||||
static const WCHAR nW[]={'N', 0};
|
|
||||||
|
|
||||||
type=0xdeadbeef;
|
type=0xdeadbeef;
|
||||||
cbData=0xdeadbeef;
|
cbData=0xdeadbeef;
|
||||||
|
@ -261,31 +263,33 @@ static void test_hkey_main_Value_W(LPCWSTR name, LPCWSTR string,
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = RegQueryValueExW(hkey_main, name, NULL, &type, NULL, &cbData);
|
ret = RegQueryValueExW(hkey_main, name, NULL, &type, NULL, &cbData);
|
||||||
GLE = GetLastError();
|
GLE = GetLastError();
|
||||||
ok(ret == ERROR_SUCCESS, "RegQueryValueExW failed: %d, GLE=%d\n", ret, GLE);
|
lok(ret == ERROR_SUCCESS, "RegQueryValueExW/1 failed: %d, GLE=%d\n", ret, GLE);
|
||||||
if(GLE == ERROR_CALL_NOT_IMPLEMENTED)
|
if(GLE == ERROR_CALL_NOT_IMPLEMENTED)
|
||||||
{
|
{
|
||||||
win_skip("RegQueryValueExW() is not implemented\n");
|
win_skip("RegQueryValueExW() is not implemented\n");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
ok(type == REG_SZ, "RegQueryValueExW returned type %d\n", type);
|
lok(type == REG_SZ, "RegQueryValueExW/1 returned type %d\n", type);
|
||||||
ok(cbData == full_byte_len,
|
lok(cbData == full_byte_len,
|
||||||
"cbData=%d instead of %d\n", cbData, full_byte_len);
|
"cbData=%d instead of %d\n", cbData, full_byte_len);
|
||||||
|
|
||||||
value = HeapAlloc(GetProcessHeap(), 0, (cbData+2)*sizeof(*value));
|
/* Give enough space to overflow by one WCHAR */
|
||||||
lstrcpyW(value, nW);
|
value = HeapAlloc(GetProcessHeap(), 0, cbData+2);
|
||||||
|
memset(value, 0xbd, cbData+2);
|
||||||
type=0xdeadbeef;
|
type=0xdeadbeef;
|
||||||
ret = RegQueryValueExW(hkey_main, name, NULL, &type, (BYTE*)value, &cbData);
|
ret = RegQueryValueExW(hkey_main, name, NULL, &type, value, &cbData);
|
||||||
GLE = GetLastError();
|
GLE = GetLastError();
|
||||||
ok(ret == ERROR_SUCCESS, "RegQueryValueExW failed: %d, GLE=%d\n", ret, GLE);
|
lok(ret == ERROR_SUCCESS, "RegQueryValueExW/2 failed: %d, GLE=%d\n", ret, GLE);
|
||||||
if (!string)
|
if (string)
|
||||||
{
|
{
|
||||||
/* When cbData == 0, RegQueryValueExW() should not modify the buffer */
|
lok(memcmp(value, string, cbData) == 0, "RegQueryValueExW failed: %s/%d != %s/%d\n",
|
||||||
string=nW;
|
wine_debugstr_wn((WCHAR*)value, cbData / sizeof(WCHAR)), cbData,
|
||||||
|
wine_debugstr_wn(string, full_byte_len / sizeof(WCHAR)), full_byte_len);
|
||||||
}
|
}
|
||||||
ok(memcmp(value, string, cbData) == 0, "RegQueryValueExW failed: %s/%d != %s/%d\n",
|
/* This implies that when cbData == 0, RegQueryValueExW() should not modify the buffer */
|
||||||
wine_debugstr_wn(value, cbData / sizeof(WCHAR)), cbData,
|
lok(*(value+cbData) == 0xbd, "RegQueryValueExW/2 overflowed at %u: %02x != bd\n", cbData, *(value+cbData));
|
||||||
wine_debugstr_wn(string, full_byte_len / sizeof(WCHAR)), full_byte_len);
|
lok(*(value+cbData+1) == 0xbd, "RegQueryValueExW/2 overflowed at %u+1: %02x != bd\n", cbData, *(value+cbData+1));
|
||||||
HeapFree(GetProcessHeap(), 0, value);
|
HeapFree(GetProcessHeap(), 0, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -957,6 +961,14 @@ static void test_reg_open_key(void)
|
||||||
ret == ERROR_FILE_NOT_FOUND /* Win9x,ME */
|
ret == ERROR_FILE_NOT_FOUND /* Win9x,ME */
|
||||||
, "expected ERROR_BAD_PATHNAME or ERROR_FILE_NOT_FOUND, got %d\n", ret);
|
, "expected ERROR_BAD_PATHNAME or ERROR_FILE_NOT_FOUND, got %d\n", ret);
|
||||||
|
|
||||||
|
hkResult = NULL;
|
||||||
|
ret = RegOpenKeyExA(HKEY_CLASSES_ROOT, "\\clsid", 0, KEY_QUERY_VALUE, &hkResult);
|
||||||
|
ok(ret == ERROR_SUCCESS || /* 2k/XP */
|
||||||
|
ret == ERROR_BAD_PATHNAME || /* NT */
|
||||||
|
ret == ERROR_FILE_NOT_FOUND /* Win9x,ME */
|
||||||
|
, "expected ERROR_SUCCESS, ERROR_BAD_PATHNAME or ERROR_FILE_NOT_FOUND, got %d\n", ret);
|
||||||
|
RegCloseKey(hkResult);
|
||||||
|
|
||||||
/* WOW64 flags */
|
/* WOW64 flags */
|
||||||
hkResult = NULL;
|
hkResult = NULL;
|
||||||
ret = RegOpenKeyExA(HKEY_LOCAL_MACHINE, "Software", 0, KEY_READ|KEY_WOW64_32KEY, &hkResult);
|
ret = RegOpenKeyExA(HKEY_LOCAL_MACHINE, "Software", 0, KEY_READ|KEY_WOW64_32KEY, &hkResult);
|
||||||
|
@ -1308,6 +1320,87 @@ cleanup:
|
||||||
RegCloseKey(subkey);
|
RegCloseKey(subkey);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void test_string_termination(void)
|
||||||
|
{
|
||||||
|
HKEY subkey;
|
||||||
|
LSTATUS ret;
|
||||||
|
static const char string[] = "FullString";
|
||||||
|
char name[11];
|
||||||
|
BYTE buffer[11];
|
||||||
|
DWORD insize, outsize, nsize;
|
||||||
|
|
||||||
|
ret = RegCreateKeyA(hkey_main, "string_termination", &subkey);
|
||||||
|
ok(ret == ERROR_SUCCESS, "Expected ERROR_SUCCESS, got %d\n", ret);
|
||||||
|
|
||||||
|
/* Off-by-one RegSetValueExA -> adds a trailing '\0'! */
|
||||||
|
insize=sizeof(string)-1;
|
||||||
|
ret = RegSetValueExA(subkey, "stringtest", 0, REG_SZ, (BYTE*)string, insize);
|
||||||
|
ok(ret == ERROR_SUCCESS, "RegSetValueExA failed: %d\n", ret);
|
||||||
|
outsize=insize;
|
||||||
|
ret = RegQueryValueExA(subkey, "stringtest", NULL, NULL, buffer, &outsize);
|
||||||
|
ok(ret == ERROR_MORE_DATA, "RegQueryValueExA returned: %d\n", ret);
|
||||||
|
|
||||||
|
/* Off-by-two RegSetValueExA -> no trailing '\0', except on Win9x */
|
||||||
|
insize=sizeof(string)-2;
|
||||||
|
ret = RegSetValueExA(subkey, "stringtest", 0, REG_SZ, (BYTE*)string, insize);
|
||||||
|
ok(ret == ERROR_SUCCESS, "RegSetValueExA failed: %d\n", ret);
|
||||||
|
outsize=0;
|
||||||
|
ret = RegQueryValueExA(subkey, "stringtest", NULL, NULL, NULL, &outsize);
|
||||||
|
ok(ret == ERROR_SUCCESS, "RegQueryValueExA failed: %d\n", ret);
|
||||||
|
ok(outsize == insize || broken(outsize == sizeof(string)) /* Win9x */,
|
||||||
|
"wrong size %u != %u\n", outsize, insize);
|
||||||
|
|
||||||
|
if (outsize == insize)
|
||||||
|
{
|
||||||
|
/* RegQueryValueExA may return a string with no trailing '\0' */
|
||||||
|
outsize=insize;
|
||||||
|
memset(buffer, 0xbd, sizeof(buffer));
|
||||||
|
ret = RegQueryValueExA(subkey, "stringtest", NULL, NULL, buffer, &outsize);
|
||||||
|
ok(ret == ERROR_SUCCESS, "RegQueryValueExA failed: %d\n", ret);
|
||||||
|
ok(outsize == insize, "wrong size: %u != %u\n", outsize, insize);
|
||||||
|
ok(memcmp(buffer, string, outsize) == 0, "bad string: %s/%u != %s\n",
|
||||||
|
wine_debugstr_an((char*)buffer, outsize), outsize, string);
|
||||||
|
ok(buffer[insize] == 0xbd, "buffer overflow at %u %02x\n", insize, buffer[insize]);
|
||||||
|
|
||||||
|
/* RegQueryValueExA adds a trailing '\0' if there is room */
|
||||||
|
outsize=insize+1;
|
||||||
|
memset(buffer, 0xbd, sizeof(buffer));
|
||||||
|
ret = RegQueryValueExA(subkey, "stringtest", NULL, NULL, buffer, &outsize);
|
||||||
|
ok(ret == ERROR_SUCCESS, "RegQueryValueExA failed: %d\n", ret);
|
||||||
|
ok(outsize == insize, "wrong size: %u != %u\n", outsize, insize);
|
||||||
|
ok(memcmp(buffer, string, outsize) == 0, "bad string: %s/%u != %s\n",
|
||||||
|
wine_debugstr_an((char*)buffer, outsize), outsize, string);
|
||||||
|
ok(buffer[insize] == 0, "buffer overflow at %u %02x\n", insize, buffer[insize]);
|
||||||
|
|
||||||
|
/* RegEnumValueA may return a string with no trailing '\0' */
|
||||||
|
outsize=insize;
|
||||||
|
memset(buffer, 0xbd, sizeof(buffer));
|
||||||
|
nsize=sizeof(name);
|
||||||
|
ret = RegEnumValueA(subkey, 0, name, &nsize, NULL, NULL, buffer, &outsize);
|
||||||
|
ok(ret == ERROR_SUCCESS, "RegEnumValueA failed: %d\n", ret);
|
||||||
|
ok(strcmp(name, "stringtest") == 0, "wrong name: %s\n", name);
|
||||||
|
ok(outsize == insize, "wrong size: %u != %u\n", outsize, insize);
|
||||||
|
ok(memcmp(buffer, string, outsize) == 0, "bad string: %s/%u != %s\n",
|
||||||
|
wine_debugstr_an((char*)buffer, outsize), outsize, string);
|
||||||
|
ok(buffer[insize] == 0xbd, "buffer overflow at %u %02x\n", insize, buffer[insize]);
|
||||||
|
|
||||||
|
/* RegEnumValueA adds a trailing '\0' if there is room */
|
||||||
|
outsize=insize+1;
|
||||||
|
memset(buffer, 0xbd, sizeof(buffer));
|
||||||
|
nsize=sizeof(name);
|
||||||
|
ret = RegEnumValueA(subkey, 0, name, &nsize, NULL, NULL, buffer, &outsize);
|
||||||
|
ok(ret == ERROR_SUCCESS, "RegEnumValueA failed: %d\n", ret);
|
||||||
|
ok(strcmp(name, "stringtest") == 0, "wrong name: %s\n", name);
|
||||||
|
ok(outsize == insize, "wrong size: %u != %u\n", outsize, insize);
|
||||||
|
ok(memcmp(buffer, string, outsize) == 0, "bad string: %s/%u != %s\n",
|
||||||
|
wine_debugstr_an((char*)buffer, outsize), outsize, string);
|
||||||
|
ok(buffer[insize] == 0, "buffer overflow at %u %02x\n", insize, buffer[insize]);
|
||||||
|
}
|
||||||
|
|
||||||
|
RegDeleteKeyA(subkey, "");
|
||||||
|
RegCloseKey(subkey);
|
||||||
|
}
|
||||||
|
|
||||||
static void test_reg_delete_tree(void)
|
static void test_reg_delete_tree(void)
|
||||||
{
|
{
|
||||||
CHAR buffer[MAX_PATH];
|
CHAR buffer[MAX_PATH];
|
||||||
|
@ -1398,6 +1491,7 @@ START_TEST(registry)
|
||||||
test_reg_close_key();
|
test_reg_close_key();
|
||||||
test_reg_delete_key();
|
test_reg_delete_key();
|
||||||
test_reg_query_value();
|
test_reg_query_value();
|
||||||
|
test_string_termination();
|
||||||
|
|
||||||
/* SaveKey/LoadKey require the SE_BACKUP_NAME privilege to be set */
|
/* SaveKey/LoadKey require the SE_BACKUP_NAME privilege to be set */
|
||||||
if (set_privileges(SE_BACKUP_NAME, TRUE) &&
|
if (set_privileges(SE_BACKUP_NAME, TRUE) &&
|
||||||
|
|
|
@ -81,10 +81,14 @@ typedef BOOL (WINAPI *fnConvertSidToStringSidA)( PSID pSid, LPSTR *str );
|
||||||
typedef BOOL (WINAPI *fnConvertStringSidToSidA)( LPCSTR str, PSID pSid );
|
typedef BOOL (WINAPI *fnConvertStringSidToSidA)( LPCSTR str, PSID pSid );
|
||||||
static BOOL (WINAPI *pConvertStringSecurityDescriptorToSecurityDescriptorA)(LPCSTR, DWORD,
|
static BOOL (WINAPI *pConvertStringSecurityDescriptorToSecurityDescriptorA)(LPCSTR, DWORD,
|
||||||
PSECURITY_DESCRIPTOR*, PULONG );
|
PSECURITY_DESCRIPTOR*, PULONG );
|
||||||
|
static BOOL (WINAPI *pConvertStringSecurityDescriptorToSecurityDescriptorW)(LPCWSTR, DWORD,
|
||||||
|
PSECURITY_DESCRIPTOR*, PULONG );
|
||||||
static BOOL (WINAPI *pConvertSecurityDescriptorToStringSecurityDescriptorA)(PSECURITY_DESCRIPTOR, DWORD,
|
static BOOL (WINAPI *pConvertSecurityDescriptorToStringSecurityDescriptorA)(PSECURITY_DESCRIPTOR, DWORD,
|
||||||
SECURITY_INFORMATION, LPSTR *, PULONG );
|
SECURITY_INFORMATION, LPSTR *, PULONG );
|
||||||
typedef BOOL (WINAPI *fnGetFileSecurityA)(LPCSTR, SECURITY_INFORMATION,
|
typedef BOOL (WINAPI *fnGetFileSecurityA)(LPCSTR, SECURITY_INFORMATION,
|
||||||
PSECURITY_DESCRIPTOR, DWORD, LPDWORD);
|
PSECURITY_DESCRIPTOR, DWORD, LPDWORD);
|
||||||
|
typedef BOOL (WINAPI *fnSetFileSecurityA)(LPCSTR, SECURITY_INFORMATION,
|
||||||
|
PSECURITY_DESCRIPTOR);
|
||||||
static DWORD (WINAPI *pGetNamedSecurityInfoA)(LPSTR, SE_OBJECT_TYPE, SECURITY_INFORMATION,
|
static DWORD (WINAPI *pGetNamedSecurityInfoA)(LPSTR, SE_OBJECT_TYPE, SECURITY_INFORMATION,
|
||||||
PSID*, PSID*, PACL*, PACL*,
|
PSID*, PSID*, PACL*, PACL*,
|
||||||
PSECURITY_DESCRIPTOR*);
|
PSECURITY_DESCRIPTOR*);
|
||||||
|
@ -117,6 +121,7 @@ fnMakeSelfRelativeSD pMakeSelfRelativeSD;
|
||||||
fnConvertSidToStringSidA pConvertSidToStringSidA;
|
fnConvertSidToStringSidA pConvertSidToStringSidA;
|
||||||
fnConvertStringSidToSidA pConvertStringSidToSidA;
|
fnConvertStringSidToSidA pConvertStringSidToSidA;
|
||||||
fnGetFileSecurityA pGetFileSecurityA;
|
fnGetFileSecurityA pGetFileSecurityA;
|
||||||
|
fnSetFileSecurityA pSetFileSecurityA;
|
||||||
fnRtlAdjustPrivilege pRtlAdjustPrivilege;
|
fnRtlAdjustPrivilege pRtlAdjustPrivilege;
|
||||||
fnCreateWellKnownSid pCreateWellKnownSid;
|
fnCreateWellKnownSid pCreateWellKnownSid;
|
||||||
fnDuplicateTokenEx pDuplicateTokenEx;
|
fnDuplicateTokenEx pDuplicateTokenEx;
|
||||||
|
@ -144,8 +149,12 @@ static void init(void)
|
||||||
pAddAuditAccessAceEx = (void *)GetProcAddress(hmod, "AddAuditAccessAceEx");
|
pAddAuditAccessAceEx = (void *)GetProcAddress(hmod, "AddAuditAccessAceEx");
|
||||||
pConvertStringSecurityDescriptorToSecurityDescriptorA =
|
pConvertStringSecurityDescriptorToSecurityDescriptorA =
|
||||||
(void *)GetProcAddress(hmod, "ConvertStringSecurityDescriptorToSecurityDescriptorA" );
|
(void *)GetProcAddress(hmod, "ConvertStringSecurityDescriptorToSecurityDescriptorA" );
|
||||||
|
pConvertStringSecurityDescriptorToSecurityDescriptorW =
|
||||||
|
(void *)GetProcAddress(hmod, "ConvertStringSecurityDescriptorToSecurityDescriptorW" );
|
||||||
pConvertSecurityDescriptorToStringSecurityDescriptorA =
|
pConvertSecurityDescriptorToStringSecurityDescriptorA =
|
||||||
(void *)GetProcAddress(hmod, "ConvertSecurityDescriptorToStringSecurityDescriptorA" );
|
(void *)GetProcAddress(hmod, "ConvertSecurityDescriptorToStringSecurityDescriptorA" );
|
||||||
|
pGetFileSecurityA = (fnGetFileSecurityA)GetProcAddress(hmod, "GetFileSecurityA" );
|
||||||
|
pSetFileSecurityA = (fnSetFileSecurityA)GetProcAddress(hmod, "SetFileSecurityA" );
|
||||||
pCreateWellKnownSid = (fnCreateWellKnownSid)GetProcAddress( hmod, "CreateWellKnownSid" );
|
pCreateWellKnownSid = (fnCreateWellKnownSid)GetProcAddress( hmod, "CreateWellKnownSid" );
|
||||||
pGetNamedSecurityInfoA = (void *)GetProcAddress(hmod, "GetNamedSecurityInfoA");
|
pGetNamedSecurityInfoA = (void *)GetProcAddress(hmod, "GetNamedSecurityInfoA");
|
||||||
pMakeSelfRelativeSD = (void *)GetProcAddress(hmod, "MakeSelfRelativeSD");
|
pMakeSelfRelativeSD = (void *)GetProcAddress(hmod, "MakeSelfRelativeSD");
|
||||||
|
@ -495,7 +504,7 @@ static void test_trustee(void)
|
||||||
#define SE_DEBUG_PRIVILEGE 20L
|
#define SE_DEBUG_PRIVILEGE 20L
|
||||||
#define SE_AUDIT_PRIVILEGE 21L
|
#define SE_AUDIT_PRIVILEGE 21L
|
||||||
#define SE_SYSTEM_ENVIRONMENT_PRIVILEGE 22L
|
#define SE_SYSTEM_ENVIRONMENT_PRIVILEGE 22L
|
||||||
#define SE_CHANGE_NOTIFY_PRIVILLEGE 23L
|
#define SE_CHANGE_NOTIFY_PRIVILEGE 23L
|
||||||
#define SE_REMOTE_SHUTDOWN_PRIVILEGE 24L
|
#define SE_REMOTE_SHUTDOWN_PRIVILEGE 24L
|
||||||
#define SE_UNDOCK_PRIVILEGE 25L
|
#define SE_UNDOCK_PRIVILEGE 25L
|
||||||
#define SE_SYNC_AGENT_PRIVILEGE 26L
|
#define SE_SYNC_AGENT_PRIVILEGE 26L
|
||||||
|
@ -570,7 +579,7 @@ static void test_lookupPrivilegeName(void)
|
||||||
"SeCreateTokenPrivilege (got %d, expected %d)\n", cchName,
|
"SeCreateTokenPrivilege (got %d, expected %d)\n", cchName,
|
||||||
(int)strlen("SeCreateTokenPrivilege"));
|
(int)strlen("SeCreateTokenPrivilege"));
|
||||||
/* check known values */
|
/* check known values */
|
||||||
for (i = SE_MIN_WELL_KNOWN_PRIVILEGE; i < SE_MAX_WELL_KNOWN_PRIVILEGE; i++)
|
for (i = SE_MIN_WELL_KNOWN_PRIVILEGE; i <= SE_MAX_WELL_KNOWN_PRIVILEGE; i++)
|
||||||
{
|
{
|
||||||
luid.LowPart = i;
|
luid.LowPart = i;
|
||||||
cchName = sizeof(buf);
|
cchName = sizeof(buf);
|
||||||
|
@ -625,7 +634,7 @@ static void test_lookupPrivilegeValue(void)
|
||||||
{ "SeDebugPrivilege", SE_DEBUG_PRIVILEGE },
|
{ "SeDebugPrivilege", SE_DEBUG_PRIVILEGE },
|
||||||
{ "SeAuditPrivilege", SE_AUDIT_PRIVILEGE },
|
{ "SeAuditPrivilege", SE_AUDIT_PRIVILEGE },
|
||||||
{ "SeSystemEnvironmentPrivilege", SE_SYSTEM_ENVIRONMENT_PRIVILEGE },
|
{ "SeSystemEnvironmentPrivilege", SE_SYSTEM_ENVIRONMENT_PRIVILEGE },
|
||||||
{ "SeChangeNotifyPrivilege", SE_CHANGE_NOTIFY_PRIVILLEGE },
|
{ "SeChangeNotifyPrivilege", SE_CHANGE_NOTIFY_PRIVILEGE },
|
||||||
{ "SeRemoteShutdownPrivilege", SE_REMOTE_SHUTDOWN_PRIVILEGE },
|
{ "SeRemoteShutdownPrivilege", SE_REMOTE_SHUTDOWN_PRIVILEGE },
|
||||||
{ "SeUndockPrivilege", SE_UNDOCK_PRIVILEGE },
|
{ "SeUndockPrivilege", SE_UNDOCK_PRIVILEGE },
|
||||||
{ "SeSyncAgentPrivilege", SE_SYNC_AGENT_PRIVILEGE },
|
{ "SeSyncAgentPrivilege", SE_SYNC_AGENT_PRIVILEGE },
|
||||||
|
@ -690,31 +699,128 @@ static void test_luid(void)
|
||||||
|
|
||||||
static void test_FileSecurity(void)
|
static void test_FileSecurity(void)
|
||||||
{
|
{
|
||||||
char directory[MAX_PATH];
|
char wintmpdir [MAX_PATH];
|
||||||
DWORD retval, outSize;
|
char path [MAX_PATH];
|
||||||
BOOL result;
|
char file [MAX_PATH];
|
||||||
BYTE buffer[0x40];
|
BOOL rc;
|
||||||
|
HANDLE fh;
|
||||||
|
DWORD sdSize;
|
||||||
|
DWORD retSize;
|
||||||
|
BYTE *sd;
|
||||||
|
SECURITY_INFORMATION const request = OWNER_SECURITY_INFORMATION
|
||||||
|
| GROUP_SECURITY_INFORMATION
|
||||||
|
| DACL_SECURITY_INFORMATION;
|
||||||
|
|
||||||
pGetFileSecurityA = (fnGetFileSecurityA)
|
if (!pGetFileSecurityA) {
|
||||||
GetProcAddress( hmod, "GetFileSecurityA" );
|
win_skip ("GetFileSecurity is not available\n");
|
||||||
if( !pGetFileSecurityA )
|
|
||||||
return;
|
|
||||||
|
|
||||||
retval = GetTempPathA(sizeof(directory), directory);
|
|
||||||
if (!retval) {
|
|
||||||
trace("GetTempPathA failed\n");
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
strcpy(directory, "\\Should not exist");
|
if (!pSetFileSecurityA) {
|
||||||
|
win_skip ("SetFileSecurity is not available\n");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
SetLastError(NO_ERROR);
|
if (!GetTempPathA (sizeof (wintmpdir), wintmpdir)) {
|
||||||
result = pGetFileSecurityA( directory,OWNER_SECURITY_INFORMATION,buffer,0x40,&outSize);
|
win_skip ("GetTempPathA failed\n");
|
||||||
ok(!result, "GetFileSecurityA should fail for not existing directories/files\n");
|
return;
|
||||||
ok( (GetLastError() == ERROR_FILE_NOT_FOUND ) ||
|
}
|
||||||
(GetLastError() == ERROR_CALL_NOT_IMPLEMENTED) ,
|
|
||||||
"last error ERROR_FILE_NOT_FOUND / ERROR_CALL_NOT_IMPLEMENTED (98) "
|
/* Create a temporary directory and in it a temporary file */
|
||||||
"expected, got %d\n", GetLastError());
|
strcat (strcpy (path, wintmpdir), "rary");
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = CreateDirectoryA (path, NULL);
|
||||||
|
ok (rc || GetLastError() == ERROR_ALREADY_EXISTS, "CreateDirectoryA "
|
||||||
|
"failed for '%s' with %d\n", path, GetLastError());
|
||||||
|
|
||||||
|
strcat (strcpy (file, path), "\\ess");
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
fh = CreateFileA (file, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, 0, NULL);
|
||||||
|
ok (fh != INVALID_HANDLE_VALUE, "CreateFileA "
|
||||||
|
"failed for '%s' with %d\n", file, GetLastError());
|
||||||
|
CloseHandle (fh);
|
||||||
|
|
||||||
|
/* For the temporary file ... */
|
||||||
|
|
||||||
|
/* Get size needed */
|
||||||
|
retSize = 0;
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = pGetFileSecurityA (file, request, NULL, 0, &retSize);
|
||||||
|
if (!rc && (GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)) {
|
||||||
|
win_skip("GetFileSecurityA is not implemented\n");
|
||||||
|
goto cleanup;
|
||||||
|
}
|
||||||
|
ok (!rc, "GetFileSecurityA "
|
||||||
|
"was expected to fail for '%s'\n", file);
|
||||||
|
ok (GetLastError() == ERROR_INSUFFICIENT_BUFFER, "GetFileSecurityA "
|
||||||
|
"returned %d; expected ERROR_INSUFFICIENT_BUFFER\n", GetLastError());
|
||||||
|
ok (retSize > sizeof (SECURITY_DESCRIPTOR), "GetFileSecurityA returned size %d\n", retSize);
|
||||||
|
|
||||||
|
sdSize = retSize;
|
||||||
|
sd = HeapAlloc (GetProcessHeap (), 0, sdSize);
|
||||||
|
|
||||||
|
/* Get security descriptor for real */
|
||||||
|
retSize = -1;
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = pGetFileSecurityA (file, request, sd, sdSize, &retSize);
|
||||||
|
ok (rc, "GetFileSecurityA "
|
||||||
|
"was not expected to fail '%s': %d\n", file, GetLastError());
|
||||||
|
ok (retSize == sdSize ||
|
||||||
|
broken(retSize == 0), /* NT4 */
|
||||||
|
"GetFileSecurityA returned size %d; expected %d\n", retSize, sdSize);
|
||||||
|
|
||||||
|
/* Use it to set security descriptor */
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = pSetFileSecurityA (file, request, sd);
|
||||||
|
ok (rc, "SetFileSecurityA "
|
||||||
|
"was not expected to fail '%s': %d\n", file, GetLastError());
|
||||||
|
|
||||||
|
HeapFree (GetProcessHeap (), 0, sd);
|
||||||
|
|
||||||
|
/* Repeat for the temporary directory ... */
|
||||||
|
|
||||||
|
/* Get size needed */
|
||||||
|
retSize = 0;
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = pGetFileSecurityA (path, request, NULL, 0, &retSize);
|
||||||
|
ok (!rc, "GetFileSecurityA "
|
||||||
|
"was expected to fail for '%s'\n", path);
|
||||||
|
ok (GetLastError() == ERROR_INSUFFICIENT_BUFFER, "GetFileSecurityA "
|
||||||
|
"returned %d; expected ERROR_INSUFFICIENT_BUFFER\n", GetLastError());
|
||||||
|
ok (retSize > sizeof (SECURITY_DESCRIPTOR), "GetFileSecurityA returned size %d\n", retSize);
|
||||||
|
|
||||||
|
sdSize = retSize;
|
||||||
|
sd = HeapAlloc (GetProcessHeap (), 0, sdSize);
|
||||||
|
|
||||||
|
/* Get security descriptor for real */
|
||||||
|
retSize = -1;
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = pGetFileSecurityA (path, request, sd, sdSize, &retSize);
|
||||||
|
ok (rc, "GetFileSecurityA "
|
||||||
|
"was not expected to fail '%s': %d\n", path, GetLastError());
|
||||||
|
ok (retSize == sdSize ||
|
||||||
|
broken(retSize == 0), /* NT4 */
|
||||||
|
"GetFileSecurityA returned size %d; expected %d\n", retSize, sdSize);
|
||||||
|
|
||||||
|
/* Use it to set security descriptor */
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = pSetFileSecurityA (path, request, sd);
|
||||||
|
ok (rc, "SetFileSecurityA "
|
||||||
|
"was not expected to fail '%s': %d\n", path, GetLastError());
|
||||||
|
HeapFree (GetProcessHeap (), 0, sd);
|
||||||
|
|
||||||
|
/* Old test */
|
||||||
|
strcpy (wintmpdir, "\\Should not exist");
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
rc = pGetFileSecurityA (wintmpdir, OWNER_SECURITY_INFORMATION, NULL, 0, &sdSize);
|
||||||
|
ok (!rc, "GetFileSecurityA should fail for not existing directories/files\n");
|
||||||
|
ok (GetLastError() == ERROR_FILE_NOT_FOUND,
|
||||||
|
"last error ERROR_FILE_NOT_FOUND expected, got %d\n", GetLastError());
|
||||||
|
|
||||||
|
cleanup:
|
||||||
|
/* Remove temporary file and directory */
|
||||||
|
DeleteFileA(file);
|
||||||
|
RemoveDirectoryA(path);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void test_AccessCheck(void)
|
static void test_AccessCheck(void)
|
||||||
|
@ -1310,6 +1416,14 @@ static void test_LookupAccountSid(void)
|
||||||
ret = LookupAccountSidW(NULL, pUsersSid, accountW, &real_acc_sizeW, domainW, &real_dom_sizeW, &use);
|
ret = LookupAccountSidW(NULL, pUsersSid, accountW, &real_acc_sizeW, domainW, &real_dom_sizeW, &use);
|
||||||
ok(ret, "LookupAccountSidW() Expected TRUE, got FALSE\n");
|
ok(ret, "LookupAccountSidW() Expected TRUE, got FALSE\n");
|
||||||
|
|
||||||
|
/* try an invalid system name */
|
||||||
|
real_acc_sizeA = MAX_PATH;
|
||||||
|
real_dom_sizeA = MAX_PATH;
|
||||||
|
ret = LookupAccountSidA("deepthought", pUsersSid, accountA, &real_acc_sizeA, domainA, &real_dom_sizeA, &use);
|
||||||
|
ok(!ret, "LookupAccountSidA() Expected FALSE got TRUE\n");
|
||||||
|
ok(GetLastError() == RPC_S_SERVER_UNAVAILABLE || GetLastError() == RPC_S_INVALID_NET_ADDR /* Vista */,
|
||||||
|
"LookupAccountSidA() Expected RPC_S_SERVER_UNAVAILABLE or RPC_S_INVALID_NET_ADDR, got %u\n", GetLastError());
|
||||||
|
|
||||||
/* native windows crashes if domainW or accountW is NULL */
|
/* native windows crashes if domainW or accountW is NULL */
|
||||||
|
|
||||||
/* try a small account buffer */
|
/* try a small account buffer */
|
||||||
|
@ -1550,10 +1664,10 @@ static void test_LookupAccountName(void)
|
||||||
{
|
{
|
||||||
ok(!lstrcmp(account, user_name), "Expected %s, got %s\n", user_name, account);
|
ok(!lstrcmp(account, user_name), "Expected %s, got %s\n", user_name, account);
|
||||||
ok(!lstrcmp(domain, sid_dom), "Expected %s, got %s\n", sid_dom, domain);
|
ok(!lstrcmp(domain, sid_dom), "Expected %s, got %s\n", sid_dom, domain);
|
||||||
ok(domain_size == domain_save - 1, "Expected %d, got %d\n", domain_save - 1, domain_size);
|
|
||||||
ok(lstrlen(domain) == domain_size, "Expected %d\n", lstrlen(domain));
|
|
||||||
ok(sid_use == SidTypeUser, "Expected SidTypeUser, got %d\n", sid_use);
|
|
||||||
}
|
}
|
||||||
|
ok(domain_size == domain_save - 1, "Expected %d, got %d\n", domain_save - 1, domain_size);
|
||||||
|
ok(lstrlen(domain) == domain_size, "Expected %d, got %d\n", lstrlen(domain), domain_size);
|
||||||
|
ok(sid_use == SidTypeUser, "Expected SidTypeUser (%d), got %d\n", SidTypeUser, sid_use);
|
||||||
domain_size = domain_save;
|
domain_size = domain_save;
|
||||||
sid_size = sid_save;
|
sid_size = sid_save;
|
||||||
|
|
||||||
|
@ -1568,12 +1682,10 @@ static void test_LookupAccountName(void)
|
||||||
ok(ret, "Failed to lookup account name\n");
|
ok(ret, "Failed to lookup account name\n");
|
||||||
ok(sid_size != 0, "sid_size was zero\n");
|
ok(sid_size != 0, "sid_size was zero\n");
|
||||||
ok(!lstrcmp(account, "Everyone"), "Expected Everyone, got %s\n", account);
|
ok(!lstrcmp(account, "Everyone"), "Expected Everyone, got %s\n", account);
|
||||||
todo_wine
|
|
||||||
ok(!lstrcmp(domain, sid_dom), "Expected %s, got %s\n", sid_dom, domain);
|
ok(!lstrcmp(domain, sid_dom), "Expected %s, got %s\n", sid_dom, domain);
|
||||||
ok(domain_size == 0, "Expected 0, got %d\n", domain_size);
|
ok(domain_size == 0, "Expected 0, got %d\n", domain_size);
|
||||||
todo_wine
|
|
||||||
ok(lstrlen(domain) == domain_size, "Expected %d, got %d\n", lstrlen(domain), domain_size);
|
ok(lstrlen(domain) == domain_size, "Expected %d, got %d\n", lstrlen(domain), domain_size);
|
||||||
ok(sid_use == SidTypeWellKnownGroup, "Expected SidTypeUser, got %d\n", sid_use);
|
ok(sid_use == SidTypeWellKnownGroup, "Expected SidTypeWellKnownGroup (%d), got %d\n", SidTypeWellKnownGroup, sid_use);
|
||||||
domain_size = domain_save;
|
domain_size = domain_save;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1616,28 +1728,33 @@ static void test_LookupAccountName(void)
|
||||||
sid_use = 0xcafebabe;
|
sid_use = 0xcafebabe;
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = LookupAccountNameA(NULL, NULL, NULL, &sid_size, NULL, &domain_size, &sid_use);
|
ret = LookupAccountNameA(NULL, NULL, NULL, &sid_size, NULL, &domain_size, &sid_use);
|
||||||
ok(!ret, "Expected 0, got %d\n", ret);
|
if (!ret && GetLastError() != ERROR_NONE_MAPPED)
|
||||||
ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER,
|
|
||||||
"Expected ERROR_INSUFFICIENT_BUFFER, got %d\n", GetLastError());
|
|
||||||
ok(sid_size != 0, "Expected non-zero sid size\n");
|
|
||||||
ok(domain_size != 0, "Expected non-zero domain size\n");
|
|
||||||
ok(sid_use == 0xcafebabe, "Expected 0xcafebabe, got %d\n", sid_use);
|
|
||||||
|
|
||||||
psid = HeapAlloc(GetProcessHeap(), 0, sid_size);
|
|
||||||
domain = HeapAlloc(GetProcessHeap(), 0, domain_size);
|
|
||||||
|
|
||||||
/* try NULL account name */
|
|
||||||
ret = LookupAccountNameA(NULL, NULL, psid, &sid_size, domain, &domain_size, &sid_use);
|
|
||||||
get_sid_info(psid, &account, &sid_dom);
|
|
||||||
ok(ret, "Failed to lookup account name\n");
|
|
||||||
todo_wine
|
|
||||||
{
|
{
|
||||||
|
ok(!ret, "Expected 0, got %d\n", ret);
|
||||||
|
ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER,
|
||||||
|
"Expected ERROR_INSUFFICIENT_BUFFER, got %d\n", GetLastError());
|
||||||
|
ok(sid_size != 0, "Expected non-zero sid size\n");
|
||||||
|
ok(domain_size != 0, "Expected non-zero domain size\n");
|
||||||
|
ok(sid_use == 0xcafebabe, "Expected 0xcafebabe, got %d\n", sid_use);
|
||||||
|
|
||||||
|
psid = HeapAlloc(GetProcessHeap(), 0, sid_size);
|
||||||
|
domain = HeapAlloc(GetProcessHeap(), 0, domain_size);
|
||||||
|
|
||||||
|
/* try NULL account name */
|
||||||
|
ret = LookupAccountNameA(NULL, NULL, psid, &sid_size, domain, &domain_size, &sid_use);
|
||||||
|
get_sid_info(psid, &account, &sid_dom);
|
||||||
|
ok(ret, "Failed to lookup account name\n");
|
||||||
/* Using a fixed string will not work on different locales */
|
/* Using a fixed string will not work on different locales */
|
||||||
ok(!lstrcmp(account, domain),
|
ok(!lstrcmp(account, domain),
|
||||||
"Got %s for account and %s for domain, these should be the same\n",
|
"Got %s for account and %s for domain, these should be the same\n",
|
||||||
account, domain);
|
account, domain);
|
||||||
ok(sid_use == SidTypeDomain, "Expected SidTypeDomain, got %d\n", SidTypeDomain);
|
ok(sid_use == SidTypeDomain, "Expected SidTypeDomain (%d), got %d\n", SidTypeDomain, sid_use);
|
||||||
|
|
||||||
|
HeapFree(GetProcessHeap(), 0, psid);
|
||||||
|
HeapFree(GetProcessHeap(), 0, domain);
|
||||||
}
|
}
|
||||||
|
else
|
||||||
|
win_skip("NULL account name doesn't work on NT4\n");
|
||||||
|
|
||||||
/* try an invalid account name */
|
/* try an invalid account name */
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
|
@ -1645,17 +1762,22 @@ static void test_LookupAccountName(void)
|
||||||
domain_size = 0;
|
domain_size = 0;
|
||||||
ret = LookupAccountNameA(NULL, "oogabooga", NULL, &sid_size, NULL, &domain_size, &sid_use);
|
ret = LookupAccountNameA(NULL, "oogabooga", NULL, &sid_size, NULL, &domain_size, &sid_use);
|
||||||
ok(!ret, "Expected 0, got %d\n", ret);
|
ok(!ret, "Expected 0, got %d\n", ret);
|
||||||
todo_wine
|
ok(GetLastError() == ERROR_NONE_MAPPED ||
|
||||||
{
|
broken(GetLastError() == ERROR_TRUSTED_RELATIONSHIP_FAILURE),
|
||||||
ok(GetLastError() == ERROR_NONE_MAPPED ||
|
"Expected ERROR_NONE_MAPPED, got %d\n", GetLastError());
|
||||||
broken(GetLastError() == ERROR_TRUSTED_RELATIONSHIP_FAILURE),
|
ok(sid_size == 0, "Expected 0, got %d\n", sid_size);
|
||||||
"Expected ERROR_NONE_MAPPED, got %d\n", GetLastError());
|
ok(domain_size == 0, "Expected 0, got %d\n", domain_size);
|
||||||
ok(sid_size == 0, "Expected 0, got %d\n", sid_size);
|
|
||||||
ok(domain_size == 0, "Expected 0, got %d\n", domain_size);
|
|
||||||
}
|
|
||||||
|
|
||||||
HeapFree(GetProcessHeap(), 0, psid);
|
/* try an invalid system name */
|
||||||
HeapFree(GetProcessHeap(), 0, domain);
|
SetLastError(0xdeadbeef);
|
||||||
|
sid_size = 0;
|
||||||
|
domain_size = 0;
|
||||||
|
ret = LookupAccountNameA("deepthought", NULL, NULL, &sid_size, NULL, &domain_size, &sid_use);
|
||||||
|
ok(!ret, "Expected 0, got %d\n", ret);
|
||||||
|
ok(GetLastError() == RPC_S_SERVER_UNAVAILABLE || GetLastError() == RPC_S_INVALID_NET_ADDR /* Vista */,
|
||||||
|
"Expected RPC_S_SERVER_UNAVAILABLE or RPC_S_INVALID_NET_ADDR, got %d\n", GetLastError());
|
||||||
|
ok(sid_size == 0, "Expected 0, got %d\n", sid_size);
|
||||||
|
ok(domain_size == 0, "Expected 0, got %d\n", domain_size);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void test_security_descriptor(void)
|
static void test_security_descriptor(void)
|
||||||
|
@ -1962,7 +2084,7 @@ static void test_impersonation_level(void)
|
||||||
ret = GetTokenInformation(Token, TokenUser, NULL, 0, &Size);
|
ret = GetTokenInformation(Token, TokenUser, NULL, 0, &Size);
|
||||||
error = GetLastError();
|
error = GetLastError();
|
||||||
ok(!ret && error == ERROR_INSUFFICIENT_BUFFER, "GetTokenInformation(TokenUser) should have failed with ERROR_INSUFFICIENT_BUFFER instead of %d\n", error);
|
ok(!ret && error == ERROR_INSUFFICIENT_BUFFER, "GetTokenInformation(TokenUser) should have failed with ERROR_INSUFFICIENT_BUFFER instead of %d\n", error);
|
||||||
User = (TOKEN_USER *)HeapAlloc(GetProcessHeap(), 0, Size);
|
User = HeapAlloc(GetProcessHeap(), 0, Size);
|
||||||
ret = GetTokenInformation(Token, TokenUser, User, Size, &Size);
|
ret = GetTokenInformation(Token, TokenUser, User, Size, &Size);
|
||||||
ok(ret, "GetTokenInformation(TokenUser) failed with error %d\n", GetLastError());
|
ok(ret, "GetTokenInformation(TokenUser) failed with error %d\n", GetLastError());
|
||||||
HeapFree(GetProcessHeap(), 0, User);
|
HeapFree(GetProcessHeap(), 0, User);
|
||||||
|
@ -1971,11 +2093,11 @@ static void test_impersonation_level(void)
|
||||||
ret = GetTokenInformation(Token, TokenPrivileges, NULL, 0, &Size);
|
ret = GetTokenInformation(Token, TokenPrivileges, NULL, 0, &Size);
|
||||||
error = GetLastError();
|
error = GetLastError();
|
||||||
ok(!ret && error == ERROR_INSUFFICIENT_BUFFER, "GetTokenInformation(TokenPrivileges) should have failed with ERROR_INSUFFICIENT_BUFFER instead of %d\n", error);
|
ok(!ret && error == ERROR_INSUFFICIENT_BUFFER, "GetTokenInformation(TokenPrivileges) should have failed with ERROR_INSUFFICIENT_BUFFER instead of %d\n", error);
|
||||||
Privileges = (TOKEN_PRIVILEGES *)HeapAlloc(GetProcessHeap(), 0, Size);
|
Privileges = HeapAlloc(GetProcessHeap(), 0, Size);
|
||||||
ret = GetTokenInformation(Token, TokenPrivileges, Privileges, Size, &Size);
|
ret = GetTokenInformation(Token, TokenPrivileges, Privileges, Size, &Size);
|
||||||
ok(ret, "GetTokenInformation(TokenPrivileges) failed with error %d\n", GetLastError());
|
ok(ret, "GetTokenInformation(TokenPrivileges) failed with error %d\n", GetLastError());
|
||||||
|
|
||||||
PrivilegeSet = (PRIVILEGE_SET *)HeapAlloc(GetProcessHeap(), 0, FIELD_OFFSET(PRIVILEGE_SET, Privilege[Privileges->PrivilegeCount]));
|
PrivilegeSet = HeapAlloc(GetProcessHeap(), 0, FIELD_OFFSET(PRIVILEGE_SET, Privilege[Privileges->PrivilegeCount]));
|
||||||
PrivilegeSet->PrivilegeCount = Privileges->PrivilegeCount;
|
PrivilegeSet->PrivilegeCount = Privileges->PrivilegeCount;
|
||||||
memcpy(PrivilegeSet->Privilege, Privileges->Privileges, PrivilegeSet->PrivilegeCount * sizeof(PrivilegeSet->Privilege[0]));
|
memcpy(PrivilegeSet->Privilege, Privileges->Privileges, PrivilegeSet->PrivilegeCount * sizeof(PrivilegeSet->Privilege[0]));
|
||||||
PrivilegeSet->Control = PRIVILEGE_SET_ALL_NECESSARY;
|
PrivilegeSet->Control = PRIVILEGE_SET_ALL_NECESSARY;
|
||||||
|
@ -2031,7 +2153,7 @@ static void test_SetEntriesInAcl(void)
|
||||||
|
|
||||||
if (!pSetEntriesInAclW)
|
if (!pSetEntriesInAclW)
|
||||||
{
|
{
|
||||||
skip("SetEntriesInAclW is not available\n");
|
win_skip("SetEntriesInAclW is not available\n");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -2039,17 +2161,20 @@ static void test_SetEntriesInAcl(void)
|
||||||
res = pSetEntriesInAclW(0, NULL, NULL, &NewAcl);
|
res = pSetEntriesInAclW(0, NULL, NULL, &NewAcl);
|
||||||
if(res == ERROR_CALL_NOT_IMPLEMENTED)
|
if(res == ERROR_CALL_NOT_IMPLEMENTED)
|
||||||
{
|
{
|
||||||
skip("SetEntriesInAclW is not implemented\n");
|
win_skip("SetEntriesInAclW is not implemented\n");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
ok(res == ERROR_SUCCESS, "SetEntriesInAclW failed: %u\n", res);
|
ok(res == ERROR_SUCCESS, "SetEntriesInAclW failed: %u\n", res);
|
||||||
ok(NewAcl == NULL, "NewAcl=%p, expected NULL\n", NewAcl);
|
ok(NewAcl == NULL ||
|
||||||
|
broken(NewAcl != NULL), /* NT4 */
|
||||||
|
"NewAcl=%p, expected NULL\n", NewAcl);
|
||||||
|
LocalFree(NewAcl);
|
||||||
|
|
||||||
OldAcl = HeapAlloc(GetProcessHeap(), 0, 256);
|
OldAcl = HeapAlloc(GetProcessHeap(), 0, 256);
|
||||||
res = InitializeAcl(OldAcl, 256, ACL_REVISION);
|
res = InitializeAcl(OldAcl, 256, ACL_REVISION);
|
||||||
if(!res && GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)
|
if(!res && GetLastError() == ERROR_CALL_NOT_IMPLEMENTED)
|
||||||
{
|
{
|
||||||
skip("ACLs not implemented - skipping tests\n");
|
win_skip("ACLs not implemented - skipping tests\n");
|
||||||
HeapFree(GetProcessHeap(), 0, OldAcl);
|
HeapFree(GetProcessHeap(), 0, OldAcl);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
@ -2093,16 +2218,22 @@ static void test_SetEntriesInAcl(void)
|
||||||
|
|
||||||
ExplicitAccess.Trustee.TrusteeForm = TRUSTEE_BAD_FORM;
|
ExplicitAccess.Trustee.TrusteeForm = TRUSTEE_BAD_FORM;
|
||||||
res = pSetEntriesInAclW(1, &ExplicitAccess, OldAcl, &NewAcl);
|
res = pSetEntriesInAclW(1, &ExplicitAccess, OldAcl, &NewAcl);
|
||||||
ok(res == ERROR_INVALID_PARAMETER, "SetEntriesInAclW failed: %u\n", res);
|
ok(res == ERROR_INVALID_PARAMETER ||
|
||||||
ok(NewAcl == NULL, "returned acl wasn't NULL: %p\n", NewAcl);
|
broken(res == ERROR_NOT_SUPPORTED), /* NT4 */
|
||||||
LocalFree(NewAcl);
|
"SetEntriesInAclW failed: %u\n", res);
|
||||||
|
ok(NewAcl == NULL ||
|
||||||
|
broken(NewAcl != NULL), /* NT4 */
|
||||||
|
"returned acl wasn't NULL: %p\n", NewAcl);
|
||||||
|
|
||||||
ExplicitAccess.Trustee.TrusteeForm = TRUSTEE_IS_USER;
|
ExplicitAccess.Trustee.TrusteeForm = TRUSTEE_IS_USER;
|
||||||
ExplicitAccess.Trustee.MultipleTrusteeOperation = TRUSTEE_IS_IMPERSONATE;
|
ExplicitAccess.Trustee.MultipleTrusteeOperation = TRUSTEE_IS_IMPERSONATE;
|
||||||
res = pSetEntriesInAclW(1, &ExplicitAccess, OldAcl, &NewAcl);
|
res = pSetEntriesInAclW(1, &ExplicitAccess, OldAcl, &NewAcl);
|
||||||
ok(res == ERROR_INVALID_PARAMETER, "SetEntriesInAclW failed: %u\n", res);
|
ok(res == ERROR_INVALID_PARAMETER ||
|
||||||
ok(NewAcl == NULL, "returned acl wasn't NULL: %p\n", NewAcl);
|
broken(res == ERROR_NOT_SUPPORTED), /* NT4 */
|
||||||
LocalFree(NewAcl);
|
"SetEntriesInAclW failed: %u\n", res);
|
||||||
|
ok(NewAcl == NULL ||
|
||||||
|
broken(NewAcl != NULL), /* NT4 */
|
||||||
|
"returned acl wasn't NULL: %p\n", NewAcl);
|
||||||
|
|
||||||
ExplicitAccess.Trustee.MultipleTrusteeOperation = NO_MULTIPLE_TRUSTEE;
|
ExplicitAccess.Trustee.MultipleTrusteeOperation = NO_MULTIPLE_TRUSTEE;
|
||||||
ExplicitAccess.grfAccessMode = SET_ACCESS;
|
ExplicitAccess.grfAccessMode = SET_ACCESS;
|
||||||
|
@ -2175,6 +2306,7 @@ static void test_ConvertStringSecurityDescriptor(void)
|
||||||
{
|
{
|
||||||
BOOL ret;
|
BOOL ret;
|
||||||
PSECURITY_DESCRIPTOR pSD;
|
PSECURITY_DESCRIPTOR pSD;
|
||||||
|
static const WCHAR Blank[] = { 0 };
|
||||||
|
|
||||||
if (!pConvertStringSecurityDescriptorToSecurityDescriptorA)
|
if (!pConvertStringSecurityDescriptorToSecurityDescriptorA)
|
||||||
{
|
{
|
||||||
|
@ -2255,11 +2387,51 @@ static void test_ConvertStringSecurityDescriptor(void)
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
"D:(A;;ROB;;;WD)", SDDL_REVISION_1, &pSD, NULL);
|
"D:(A;;ROB;;;WD)", SDDL_REVISION_1, &pSD, NULL);
|
||||||
todo_wine
|
|
||||||
ok(!ret && GetLastError() == ERROR_INVALID_ACL,
|
ok(!ret && GetLastError() == ERROR_INVALID_ACL,
|
||||||
"ConvertStringSecurityDescriptorToSecurityDescriptor should have failed with ERROR_INVALID_ACL instead of %d\n",
|
"ConvertStringSecurityDescriptorToSecurityDescriptor should have failed with ERROR_INVALID_ACL instead of %d\n",
|
||||||
GetLastError());
|
GetLastError());
|
||||||
|
|
||||||
|
/* test behaviour with NULL parameters */
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
|
NULL, 0xdeadbeef, &pSD, NULL);
|
||||||
|
todo_wine
|
||||||
|
ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER,
|
||||||
|
"ConvertStringSecurityDescriptorToSecurityDescriptor should have failed with ERROR_INVALID_PARAMETER instead of %d\n",
|
||||||
|
GetLastError());
|
||||||
|
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorW(
|
||||||
|
NULL, 0xdeadbeef, &pSD, NULL);
|
||||||
|
ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER,
|
||||||
|
"ConvertStringSecurityDescriptorToSecurityDescriptor should have failed with ERROR_INVALID_PARAMETER instead of %d\n",
|
||||||
|
GetLastError());
|
||||||
|
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
|
"D:(A;;ROB;;;WD)", 0xdeadbeef, NULL, NULL);
|
||||||
|
ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER,
|
||||||
|
"ConvertStringSecurityDescriptorToSecurityDescriptor should have failed with ERROR_INVALID_PARAMETER instead of %d\n",
|
||||||
|
GetLastError());
|
||||||
|
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
|
"D:(A;;ROB;;;WD)", SDDL_REVISION_1, NULL, NULL);
|
||||||
|
ok(!ret && GetLastError() == ERROR_INVALID_PARAMETER,
|
||||||
|
"ConvertStringSecurityDescriptorToSecurityDescriptor should have failed with ERROR_INVALID_PARAMETER instead of %d\n",
|
||||||
|
GetLastError());
|
||||||
|
|
||||||
|
/* test behaviour with empty strings */
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
|
"", SDDL_REVISION_1, &pSD, NULL);
|
||||||
|
ok(ret, "ConvertStringSecurityDescriptorToSecurityDescriptor failed with error %d\n", GetLastError());
|
||||||
|
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorW(
|
||||||
|
Blank, SDDL_REVISION_1, &pSD, NULL);
|
||||||
|
ok(ret, "ConvertStringSecurityDescriptorToSecurityDescriptor failed with error %d\n", GetLastError());
|
||||||
|
|
||||||
/* test ACE string SID */
|
/* test ACE string SID */
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
ret = pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
|
@ -2386,11 +2558,100 @@ static void test_ConvertSecurityDescriptorToString()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void test_SetSecurityDescriptorControl (PSECURITY_DESCRIPTOR sec)
|
||||||
|
{
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL ref;
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL test;
|
||||||
|
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL const mutable
|
||||||
|
= SE_DACL_AUTO_INHERIT_REQ | SE_SACL_AUTO_INHERIT_REQ
|
||||||
|
| SE_DACL_AUTO_INHERITED | SE_SACL_AUTO_INHERITED
|
||||||
|
| SE_DACL_PROTECTED | SE_SACL_PROTECTED
|
||||||
|
| 0x00000040 | 0x00000080 /* not defined in winnt.h */
|
||||||
|
;
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL const immutable
|
||||||
|
= SE_OWNER_DEFAULTED | SE_GROUP_DEFAULTED
|
||||||
|
| SE_DACL_PRESENT | SE_DACL_DEFAULTED
|
||||||
|
| SE_SACL_PRESENT | SE_SACL_DEFAULTED
|
||||||
|
| SE_RM_CONTROL_VALID | SE_SELF_RELATIVE
|
||||||
|
;
|
||||||
|
|
||||||
|
int bit;
|
||||||
|
DWORD dwRevision;
|
||||||
|
LPCSTR fmt = "Expected error %s, got %u\n";
|
||||||
|
|
||||||
|
GetSecurityDescriptorControl (sec, &ref, &dwRevision);
|
||||||
|
|
||||||
|
/* The mutable bits are mutable regardless of the truth of
|
||||||
|
SE_DACL_PRESENT and/or SE_SACL_PRESENT */
|
||||||
|
|
||||||
|
/* Check call barfs if any bit-of-interest is immutable */
|
||||||
|
for (bit = 0; bit < 16; ++bit)
|
||||||
|
{
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL const bitOfInterest = 1 << bit;
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL setOrClear = ref & bitOfInterest;
|
||||||
|
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL ctrl;
|
||||||
|
|
||||||
|
DWORD dwExpect = (bitOfInterest & immutable)
|
||||||
|
? ERROR_INVALID_PARAMETER : 0xbebecaca;
|
||||||
|
LPCSTR strExpect = (bitOfInterest & immutable)
|
||||||
|
? "ERROR_INVALID_PARAMETER" : "0xbebecaca";
|
||||||
|
|
||||||
|
ctrl = (bitOfInterest & mutable) ? ref + bitOfInterest : ref;
|
||||||
|
setOrClear ^= bitOfInterest;
|
||||||
|
SetLastError (0xbebecaca);
|
||||||
|
pSetSecurityDescriptorControl (sec, bitOfInterest, setOrClear);
|
||||||
|
ok (GetLastError () == dwExpect, fmt, strExpect, GetLastError ());
|
||||||
|
GetSecurityDescriptorControl(sec, &test, &dwRevision);
|
||||||
|
expect_eq(test, ctrl, int, "%x");
|
||||||
|
|
||||||
|
ctrl = ref;
|
||||||
|
setOrClear ^= bitOfInterest;
|
||||||
|
SetLastError (0xbebecaca);
|
||||||
|
pSetSecurityDescriptorControl (sec, bitOfInterest, setOrClear);
|
||||||
|
ok (GetLastError () == dwExpect, fmt, strExpect, GetLastError ());
|
||||||
|
GetSecurityDescriptorControl (sec, &test, &dwRevision);
|
||||||
|
expect_eq(test, ref, int, "%x");
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Check call barfs if any bit-to-set is immutable
|
||||||
|
even when not a bit-of-interest */
|
||||||
|
for (bit = 0; bit < 16; ++bit)
|
||||||
|
{
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL const bitsOfInterest = mutable;
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL setOrClear = ref & bitsOfInterest;
|
||||||
|
|
||||||
|
SECURITY_DESCRIPTOR_CONTROL ctrl;
|
||||||
|
|
||||||
|
DWORD dwExpect = ((1 << bit) & immutable)
|
||||||
|
? ERROR_INVALID_PARAMETER : 0xbebecaca;
|
||||||
|
LPCSTR strExpect = ((1 << bit) & immutable)
|
||||||
|
? "ERROR_INVALID_PARAMETER" : "0xbebecaca";
|
||||||
|
|
||||||
|
ctrl = ((1 << bit) & immutable) ? test : ref | mutable;
|
||||||
|
setOrClear ^= bitsOfInterest;
|
||||||
|
SetLastError (0xbebecaca);
|
||||||
|
pSetSecurityDescriptorControl (sec, bitsOfInterest, setOrClear | (1 << bit));
|
||||||
|
ok (GetLastError () == dwExpect, fmt, strExpect, GetLastError ());
|
||||||
|
GetSecurityDescriptorControl(sec, &test, &dwRevision);
|
||||||
|
expect_eq(test, ctrl, int, "%x");
|
||||||
|
|
||||||
|
ctrl = ((1 << bit) & immutable) ? test : ref | (1 << bit);
|
||||||
|
setOrClear ^= bitsOfInterest;
|
||||||
|
SetLastError (0xbebecaca);
|
||||||
|
pSetSecurityDescriptorControl (sec, bitsOfInterest, setOrClear | (1 << bit));
|
||||||
|
ok (GetLastError () == dwExpect, fmt, strExpect, GetLastError ());
|
||||||
|
GetSecurityDescriptorControl(sec, &test, &dwRevision);
|
||||||
|
expect_eq(test, ctrl, int, "%x");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static void test_PrivateObjectSecurity(void)
|
static void test_PrivateObjectSecurity(void)
|
||||||
{
|
{
|
||||||
SECURITY_INFORMATION sec_info = OWNER_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|DACL_SECURITY_INFORMATION|SACL_SECURITY_INFORMATION;
|
SECURITY_INFORMATION sec_info = OWNER_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|DACL_SECURITY_INFORMATION|SACL_SECURITY_INFORMATION;
|
||||||
SECURITY_DESCRIPTOR_CONTROL ctrl;
|
SECURITY_DESCRIPTOR_CONTROL ctrl;
|
||||||
PSECURITY_DESCRIPTOR sec = NULL;
|
PSECURITY_DESCRIPTOR sec;
|
||||||
DWORD dwDescSize;
|
DWORD dwDescSize;
|
||||||
DWORD dwRevision;
|
DWORD dwRevision;
|
||||||
DWORD retSize;
|
DWORD retSize;
|
||||||
|
@ -2404,16 +2665,36 @@ static void test_PrivateObjectSecurity(void)
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ok(pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
|
"O:SY"
|
||||||
|
"G:S-1-5-21-93476-23408-4576"
|
||||||
|
"D:(A;NP;GAGXGWGR;;;SU)(A;IOID;CCDC;;;SU)"
|
||||||
|
"(D;OICI;0xffffffff;;;S-1-5-21-93476-23408-4576)"
|
||||||
|
"S:(AU;OICINPIOIDSAFA;CCDCLCSWRPRC;;;SU)(AU;NPSA;0x12019f;;;SU)",
|
||||||
|
SDDL_REVISION_1, &sec, &dwDescSize), "Creating descriptor failed\n");
|
||||||
|
|
||||||
|
test_SetSecurityDescriptorControl(sec);
|
||||||
|
|
||||||
|
LocalFree(sec);
|
||||||
|
|
||||||
|
ok(pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
|
"O:SY"
|
||||||
|
"G:S-1-5-21-93476-23408-4576",
|
||||||
|
SDDL_REVISION_1, &sec, &dwDescSize), "Creating descriptor failed\n");
|
||||||
|
|
||||||
|
test_SetSecurityDescriptorControl(sec);
|
||||||
|
|
||||||
|
LocalFree(sec);
|
||||||
|
|
||||||
ok(pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
ok(pConvertStringSecurityDescriptorToSecurityDescriptorA(
|
||||||
"O:SY"
|
"O:SY"
|
||||||
"G:S-1-5-21-93476-23408-4576"
|
"G:S-1-5-21-93476-23408-4576"
|
||||||
"D:(A;NP;GAGXGWGR;;;SU)(A;IOID;CCDC;;;SU)(D;OICI;0xffffffff;;;S-1-5-21-93476-23408-4576)"
|
"D:(A;NP;GAGXGWGR;;;SU)(A;IOID;CCDC;;;SU)(D;OICI;0xffffffff;;;S-1-5-21-93476-23408-4576)"
|
||||||
"S:(AU;OICINPIOIDSAFA;CCDCLCSWRPRC;;;SU)(AU;NPSA;0x12019f;;;SU)", SDDL_REVISION_1, &sec, &dwDescSize), "Creating descriptor failed\n");
|
"S:(AU;OICINPIOIDSAFA;CCDCLCSWRPRC;;;SU)(AU;NPSA;0x12019f;;;SU)", SDDL_REVISION_1, &sec, &dwDescSize), "Creating descriptor failed\n");
|
||||||
buf = HeapAlloc(GetProcessHeap(), 0, dwDescSize);
|
buf = HeapAlloc(GetProcessHeap(), 0, dwDescSize);
|
||||||
DbgPrint("Received %p\n", sec);
|
|
||||||
pSetSecurityDescriptorControl(sec, SE_DACL_PROTECTED, SE_DACL_PROTECTED);
|
pSetSecurityDescriptorControl(sec, SE_DACL_PROTECTED, SE_DACL_PROTECTED);
|
||||||
GetSecurityDescriptorControl(sec, &ctrl, &dwRevision);
|
GetSecurityDescriptorControl(sec, &ctrl, &dwRevision);
|
||||||
todo_wine expect_eq(ctrl, 0x9014, int, "%x");
|
expect_eq(ctrl, 0x9014, int, "%x");
|
||||||
|
|
||||||
ok(GetPrivateObjectSecurity(sec, GROUP_SECURITY_INFORMATION, buf, dwDescSize, &retSize),
|
ok(GetPrivateObjectSecurity(sec, GROUP_SECURITY_INFORMATION, buf, dwDescSize, &retSize),
|
||||||
"GetPrivateObjectSecurity failed (err=%u)\n", GetLastError());
|
"GetPrivateObjectSecurity failed (err=%u)\n", GetLastError());
|
||||||
|
@ -2488,11 +2769,17 @@ static void test_acls(void)
|
||||||
ret = IsValidAcl(pAcl);
|
ret = IsValidAcl(pAcl);
|
||||||
ok(ret, "IsValidAcl failed with error %d\n", GetLastError());
|
ok(ret, "IsValidAcl failed with error %d\n", GetLastError());
|
||||||
|
|
||||||
|
SetLastError(0xdeadbeef);
|
||||||
ret = InitializeAcl(pAcl, sizeof(buffer), ACL_REVISION4);
|
ret = InitializeAcl(pAcl, sizeof(buffer), ACL_REVISION4);
|
||||||
ok(ret, "InitializeAcl(ACL_REVISION4) failed with error %d\n", GetLastError());
|
if (GetLastError() != ERROR_INVALID_PARAMETER)
|
||||||
|
{
|
||||||
|
ok(ret, "InitializeAcl(ACL_REVISION4) failed with error %d\n", GetLastError());
|
||||||
|
|
||||||
ret = IsValidAcl(pAcl);
|
ret = IsValidAcl(pAcl);
|
||||||
ok(ret, "IsValidAcl failed with error %d\n", GetLastError());
|
ok(ret, "IsValidAcl failed with error %d\n", GetLastError());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
win_skip("ACL_REVISION4 is not implemented on NT4\n");
|
||||||
|
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = InitializeAcl(pAcl, sizeof(buffer), -1);
|
ret = InitializeAcl(pAcl, sizeof(buffer), -1);
|
||||||
|
@ -2540,6 +2827,13 @@ static void test_GetSecurityInfo(void)
|
||||||
|
|
||||||
LocalFree(sd);
|
LocalFree(sd);
|
||||||
|
|
||||||
|
if (!pCreateWellKnownSid)
|
||||||
|
{
|
||||||
|
win_skip("NULL parameter test would crash on NT4\n");
|
||||||
|
CloseHandle(obj);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
/* If we don't ask for the security descriptor, Windows will still give us
|
/* If we don't ask for the security descriptor, Windows will still give us
|
||||||
the other stuff, leaving us no way to free it. */
|
the other stuff, leaving us no way to free it. */
|
||||||
ret = pGetSecurityInfo(obj, SE_FILE_OBJECT,
|
ret = pGetSecurityInfo(obj, SE_FILE_OBJECT,
|
||||||
|
|
|
@ -564,7 +564,7 @@ static void test_get_displayname(void)
|
||||||
displaysize = tempsizeW / 2;
|
displaysize = tempsizeW / 2;
|
||||||
ret = GetServiceDisplayNameW(scm_handle, spoolerW, displaynameW, &displaysize);
|
ret = GetServiceDisplayNameW(scm_handle, spoolerW, displaynameW, &displaysize);
|
||||||
ok(!ret, "Expected failure\n");
|
ok(!ret, "Expected failure\n");
|
||||||
ok(displaysize = tempsizeW, "Expected the needed buffersize\n");
|
ok(displaysize == tempsizeW, "Expected the needed buffersize\n");
|
||||||
ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER,
|
ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER,
|
||||||
"Expected ERROR_INSUFFICIENT_BUFFER, got %d\n", GetLastError());
|
"Expected ERROR_INSUFFICIENT_BUFFER, got %d\n", GetLastError());
|
||||||
|
|
||||||
|
@ -573,7 +573,7 @@ static void test_get_displayname(void)
|
||||||
displaysize = tempsizeW;
|
displaysize = tempsizeW;
|
||||||
ret = GetServiceDisplayNameW(scm_handle, spoolerW, displaynameW, &displaysize);
|
ret = GetServiceDisplayNameW(scm_handle, spoolerW, displaynameW, &displaysize);
|
||||||
ok(!ret, "Expected failure\n");
|
ok(!ret, "Expected failure\n");
|
||||||
ok(displaysize = tempsizeW, "Expected the needed buffersize\n");
|
ok(displaysize == tempsizeW, "Expected the needed buffersize\n");
|
||||||
ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER,
|
ok(GetLastError() == ERROR_INSUFFICIENT_BUFFER,
|
||||||
"Expected ERROR_INSUFFICIENT_BUFFER, got %d\n", GetLastError());
|
"Expected ERROR_INSUFFICIENT_BUFFER, got %d\n", GetLastError());
|
||||||
|
|
||||||
|
@ -649,7 +649,7 @@ static void test_get_displayname(void)
|
||||||
|
|
||||||
/* Delete the service */
|
/* Delete the service */
|
||||||
ret = DeleteService(svc_handle);
|
ret = DeleteService(svc_handle);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
|
|
||||||
CloseServiceHandle(svc_handle);
|
CloseServiceHandle(svc_handle);
|
||||||
CloseServiceHandle(scm_handle);
|
CloseServiceHandle(scm_handle);
|
||||||
|
@ -882,7 +882,7 @@ static void test_query_svc(void)
|
||||||
/* Only info level is correct. It looks like the buffer/size is checked second */
|
/* Only info level is correct. It looks like the buffer/size is checked second */
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = pQueryServiceStatusEx(NULL, 0, NULL, 0, &needed);
|
ret = pQueryServiceStatusEx(NULL, 0, NULL, 0, &needed);
|
||||||
/* NT4 checks the handle first */
|
/* NT4 and Wine check the handle first */
|
||||||
if (GetLastError() != ERROR_INVALID_HANDLE)
|
if (GetLastError() != ERROR_INVALID_HANDLE)
|
||||||
{
|
{
|
||||||
ok(!ret, "Expected failure\n");
|
ok(!ret, "Expected failure\n");
|
||||||
|
@ -893,7 +893,7 @@ static void test_query_svc(void)
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Pass a correct buffer and buffersize but a NULL handle */
|
/* Pass a correct buffer and buffersize but a NULL handle */
|
||||||
statusproc = HeapAlloc(GetProcessHeap(), 0, needed);
|
statusproc = HeapAlloc(GetProcessHeap(), 0, sizeof(SERVICE_STATUS_PROCESS));
|
||||||
bufsize = needed;
|
bufsize = needed;
|
||||||
SetLastError(0xdeadbeef);
|
SetLastError(0xdeadbeef);
|
||||||
ret = pQueryServiceStatusEx(NULL, 0, (BYTE*)statusproc, bufsize, &needed);
|
ret = pQueryServiceStatusEx(NULL, 0, (BYTE*)statusproc, bufsize, &needed);
|
||||||
|
@ -1985,7 +1985,7 @@ static void test_refcount(void)
|
||||||
|
|
||||||
/* Check if we can close the handle to the Service Control Manager */
|
/* Check if we can close the handle to the Service Control Manager */
|
||||||
ret = CloseServiceHandle(scm_handle);
|
ret = CloseServiceHandle(scm_handle);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
|
|
||||||
/* Get a new handle to the Service Control Manager */
|
/* Get a new handle to the Service Control Manager */
|
||||||
scm_handle = OpenSCManagerA(NULL, NULL, GENERIC_ALL);
|
scm_handle = OpenSCManagerA(NULL, NULL, GENERIC_ALL);
|
||||||
|
@ -1997,7 +1997,7 @@ static void test_refcount(void)
|
||||||
|
|
||||||
/* Delete the service */
|
/* Delete the service */
|
||||||
ret = DeleteService(svc_handle4);
|
ret = DeleteService(svc_handle4);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
|
|
||||||
/* We cannot create the same service again as it's still marked as 'being deleted'.
|
/* We cannot create the same service again as it's still marked as 'being deleted'.
|
||||||
* The reason is that we still have 4 open handles to this service even though we
|
* The reason is that we still have 4 open handles to this service even though we
|
||||||
|
@ -2023,13 +2023,13 @@ static void test_refcount(void)
|
||||||
|
|
||||||
/* Close all the handles to the service and try again */
|
/* Close all the handles to the service and try again */
|
||||||
ret = CloseServiceHandle(svc_handle4);
|
ret = CloseServiceHandle(svc_handle4);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
ret = CloseServiceHandle(svc_handle3);
|
ret = CloseServiceHandle(svc_handle3);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
ret = CloseServiceHandle(svc_handle2);
|
ret = CloseServiceHandle(svc_handle2);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
ret = CloseServiceHandle(svc_handle1);
|
ret = CloseServiceHandle(svc_handle1);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
|
|
||||||
/* Wait a while. Doing a CreateService too soon will result again
|
/* Wait a while. Doing a CreateService too soon will result again
|
||||||
* in an ERROR_SERVICE_MARKED_FOR_DELETE error.
|
* in an ERROR_SERVICE_MARKED_FOR_DELETE error.
|
||||||
|
@ -2044,7 +2044,7 @@ static void test_refcount(void)
|
||||||
|
|
||||||
/* Delete the service */
|
/* Delete the service */
|
||||||
ret = DeleteService(svc_handle5);
|
ret = DeleteService(svc_handle5);
|
||||||
ok(ret, "Expected success\n");
|
ok(ret, "Expected success (err=%d)\n", GetLastError());
|
||||||
|
|
||||||
/* Wait a while. Just in case one of the following tests does a CreateService again */
|
/* Wait a while. Just in case one of the following tests does a CreateService again */
|
||||||
Sleep(1000);
|
Sleep(1000);
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue