[PATCH 2/2] ntdll: Implement RunlevelInformationInActivationContext in RtlQueryInformationActivationContext
Nikolay Sivov
nsivov at codeweavers.com
Sat Feb 17 08:41:16 CST 2018
From: Michael Müller <michael at fds-team.de>
Signed-off-by: Nikolay Sivov <nsivov at codeweavers.com>
---
Minor modifications from original to make tests pass on XP, where such context info is not supported.
dlls/kernel32/tests/actctx.c | 243 ++++++++++++++++++++++++++++++++++++++++---
dlls/ntdll/actctx.c | 21 ++++
2 files changed, 249 insertions(+), 15 deletions(-)
diff --git a/dlls/kernel32/tests/actctx.c b/dlls/kernel32/tests/actctx.c
index a182cfa4be..cef11a5e63 100644
--- a/dlls/kernel32/tests/actctx.c
+++ b/dlls/kernel32/tests/actctx.c
@@ -244,6 +244,61 @@ static const char manifest5[] =
"</dependency>"
"</assembly>";
+static const char manifest6[] =
+"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
+"<assemblyIdentity version=\"1.0.0.0\" name=\"Wine.Test\" type=\"win32\"></assemblyIdentity>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v1\">"
+" <security>"
+" <requestedPrivileges>"
+" <requestedExecutionLevel level=\"ASINVOKER\" uiAccess=\"false\"/>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"</assembly>";
+
+static const char manifest7[] =
+"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
+"<assemblyIdentity version=\"1.0.0.0\" name=\"Wine.Test\" type=\"win32\"></assemblyIdentity>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v2\">"
+" <security>"
+" <requestedPrivileges>"
+" <requestedExecutionLevel level=\"requireAdministrator\" uiAccess=\"TRUE\"/>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"</assembly>";
+
+static const char manifest8[] =
+"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
+"<assemblyIdentity version=\"1.0.0.0\" name=\"Wine.Test\" type=\"win32\"></assemblyIdentity>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v2\">"
+" <security>"
+" <requestedPrivileges>"
+" <requestedExecutionLevel level=\"requireAdministrator\" uiAccess=\"true\">"
+" </requestedExecutionLevel>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"</assembly>";
+
+static const char manifest9[] =
+"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
+"<assemblyIdentity version=\"1.0.0.0\" name=\"Wine.Test\" type=\"win32\"></assemblyIdentity>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v2\">"
+" <security>"
+" <requestedPrivileges>"
+" <requestedExecutionLevel level=\"requireAdministrator\"/>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v2\">"
+" <security>"
+" <requestedPrivileges>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"</assembly>";
+
static const char testdep_manifest1[] =
"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
"<assemblyIdentity type=\"win32\" name=\"testdep\" version=\"6.5.4.3\" processorArchitecture=\"" ARCH "\"/>"
@@ -310,6 +365,38 @@ static const char wrong_manifest8[] =
"<file></file>"
"</assembly>";
+static const char wrong_manifest9[] =
+"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
+"<assemblyIdentity version=\"1.0.0.0\" name=\"Wine.Test\" type=\"win32\"></assemblyIdentity>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v2\">"
+" <security>"
+" <requestedPrivileges>"
+" <requestedExecutionLevel level=\"requireAdministrator\"/>"
+" <requestedExecutionLevel uiAccess=\"true\"/>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"</assembly>";
+
+static const char wrong_manifest10[] =
+"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
+"<assemblyIdentity version=\"1.0.0.0\" name=\"Wine.Test\" type=\"win32\"></assemblyIdentity>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v2\">"
+" <security>"
+" <requestedPrivileges>"
+" <requestedExecutionLevel level=\"requireAdministrator\"/>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"<trustInfo xmlns=\"urn:schemas-microsoft-com:asm.v2\">"
+" <security>"
+" <requestedPrivileges>"
+" <requestedExecutionLevel uiAccess=\"true\"/>"
+" </requestedPrivileges>"
+" </security>"
+"</trustInfo>"
+"</assembly>";
+
static const char wrong_depmanifest1[] =
"<assembly xmlns=\"urn:schemas-microsoft-com:asm.v1\" manifestVersion=\"1.0\">"
"<assemblyIdentity type=\"win32\" name=\"testdep\" version=\"6.5.4.4\" processorArchitecture=\"" ARCH "\" />"
@@ -783,6 +870,57 @@ static void test_file_info(HANDLE handle, ULONG assid, ULONG fileid, LPCWSTR fil
HeapFree(GetProcessHeap(), 0, info);
}
+typedef struct {
+ ACTCTX_REQUESTED_RUN_LEVEL run_level;
+ DWORD ui_access;
+} runlevel_info_t;
+
+static const runlevel_info_t runlevel_info0 = {
+ ACTCTX_RUN_LEVEL_UNSPECIFIED, FALSE,
+};
+
+static const runlevel_info_t runlevel_info6 = {
+ ACTCTX_RUN_LEVEL_AS_INVOKER, FALSE,
+};
+
+static const runlevel_info_t runlevel_info7 = {
+ ACTCTX_RUN_LEVEL_REQUIRE_ADMIN, TRUE,
+};
+
+static const runlevel_info_t runlevel_info8 = {
+ ACTCTX_RUN_LEVEL_REQUIRE_ADMIN, TRUE,
+};
+
+static const runlevel_info_t runlevel_info9 = {
+ ACTCTX_RUN_LEVEL_REQUIRE_ADMIN, FALSE,
+};
+
+static void test_runlevel_info(HANDLE handle, const runlevel_info_t *exinfo, int line)
+{
+ ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION runlevel_info;
+ SIZE_T size, retsize;
+ BOOL b;
+
+ size = sizeof(runlevel_info);
+ b = pQueryActCtxW(0, handle, NULL,
+ RunlevelInformationInActivationContext, &runlevel_info,
+ sizeof(runlevel_info), &retsize);
+ if (!b && GetLastError() == ERROR_INVALID_PARAMETER)
+ {
+ win_skip("RunlevelInformationInActivationContext not supported.\n");
+ return;
+ }
+
+ ok_(__FILE__, line)(b, "QueryActCtx failed: %u\n", GetLastError());
+ ok_(__FILE__, line)(retsize == size, "size=%ld, expected %ld\n", retsize, size);
+
+ ok_(__FILE__, line)(runlevel_info.ulFlags == 0, "runlevel_info.ulFlags=%x\n", runlevel_info.ulFlags);
+ ok_(__FILE__, line)(runlevel_info.RunLevel == exinfo->run_level,
+ "runlevel_info.RunLevel=%u, expected %u\n", runlevel_info.RunLevel, exinfo->run_level);
+ ok_(__FILE__, line)(runlevel_info.UiAccess == exinfo->ui_access,
+ "runlevel_info.UiAccess=%u, expected %u\n", runlevel_info.UiAccess, exinfo->ui_access);
+}
+
static HANDLE test_create(const char *file)
{
ACTCTXW actctx;
@@ -814,7 +952,7 @@ static HANDLE test_create(const char *file)
return handle;
}
-static void test_create_and_fail(const char *manifest, const char *depmanifest, int todo)
+static void test_create_and_fail(const char *manifest, const char *depmanifest, int todo, BOOL is_broken)
{
ACTCTXW actctx;
HANDLE handle;
@@ -829,8 +967,14 @@ static void test_create_and_fail(const char *manifest, const char *depmanifest,
handle = pCreateActCtxW(&actctx);
todo_wine_if(todo)
{
- ok(handle == INVALID_HANDLE_VALUE, "handle != INVALID_HANDLE_VALUE\n");
- ok(GetLastError() == ERROR_SXS_CANT_GEN_ACTCTX, "GetLastError == %u\n", GetLastError());
+ if (is_broken)
+ ok(broken(handle != INVALID_HANDLE_VALUE) || handle == INVALID_HANDLE_VALUE,
+ "Unexpected context handle %p.\n", handle);
+ else
+ ok(handle == INVALID_HANDLE_VALUE, "Unexpected context handle %p.\n", handle);
+
+ if (handle == INVALID_HANDLE_VALUE)
+ ok(GetLastError() == ERROR_SXS_CANT_GEN_ACTCTX, "Unexpected error %d.\n", GetLastError());
}
if (handle != INVALID_HANDLE_VALUE) pReleaseActCtx( handle );
DeleteFileA("bad.manifest");
@@ -873,27 +1017,31 @@ static void test_create_fail(void)
ok(GetLastError() == ERROR_FILE_NOT_FOUND, "GetLastError == %u\n", GetLastError());
trace("wrong_manifest1\n");
- test_create_and_fail(wrong_manifest1, NULL, 0 );
+ test_create_and_fail(wrong_manifest1, NULL, 0, FALSE);
trace("wrong_manifest2\n");
- test_create_and_fail(wrong_manifest2, NULL, 0 );
+ test_create_and_fail(wrong_manifest2, NULL, 0, FALSE);
trace("wrong_manifest3\n");
- test_create_and_fail(wrong_manifest3, NULL, 1 );
+ test_create_and_fail(wrong_manifest3, NULL, 1, FALSE);
trace("wrong_manifest4\n");
- test_create_and_fail(wrong_manifest4, NULL, 1 );
+ test_create_and_fail(wrong_manifest4, NULL, 1, FALSE);
trace("wrong_manifest5\n");
- test_create_and_fail(wrong_manifest5, NULL, 0 );
+ test_create_and_fail(wrong_manifest5, NULL, 0, FALSE);
trace("wrong_manifest6\n");
- test_create_and_fail(wrong_manifest6, NULL, 0 );
+ test_create_and_fail(wrong_manifest6, NULL, 0, FALSE);
trace("wrong_manifest7\n");
- test_create_and_fail(wrong_manifest7, NULL, 1 );
+ test_create_and_fail(wrong_manifest7, NULL, 1, FALSE);
trace("wrong_manifest8\n");
- test_create_and_fail(wrong_manifest8, NULL, 0 );
+ test_create_and_fail(wrong_manifest8, NULL, 0, FALSE);
+ trace("wrong_manifest9\n");
+ test_create_and_fail(wrong_manifest9, NULL, 0, TRUE /* WinXP */);
+ trace("wrong_manifest10\n");
+ test_create_and_fail(wrong_manifest10, NULL, 0, TRUE /* WinXP */);
trace("UTF-16 manifest1 without BOM\n");
test_create_wide_and_fail(manifest1, FALSE );
trace("manifest2\n");
- test_create_and_fail(manifest2, NULL, 0 );
+ test_create_and_fail(manifest2, NULL, 0, FALSE);
trace("manifest2+depmanifest1\n");
- test_create_and_fail(manifest2, wrong_depmanifest1, 0 );
+ test_create_and_fail(manifest2, wrong_depmanifest1, 0, FALSE);
}
struct strsection_header
@@ -1825,8 +1973,6 @@ static void test_actctx(void)
HANDLE handle;
BOOL b;
- test_create_fail();
-
trace("default actctx\n");
b = pGetCurrentActCtx(&handle);
@@ -1835,6 +1981,7 @@ static void test_actctx(void)
if(b) {
test_basic_info(handle, __LINE__);
test_detailed_info(handle, &detailed_info0, __LINE__);
+ test_runlevel_info(handle, &runlevel_info0, __LINE__);
pReleaseActCtx(handle);
}
@@ -2006,6 +2153,71 @@ static void test_actctx(void)
pReleaseActCtx(handle);
}
+ trace("manifest6\n");
+
+ if(create_manifest_file("test6.manifest", manifest6, -1, NULL, NULL)) {
+ handle = test_create("test6.manifest");
+ ok(handle != INVALID_HANDLE_VALUE || broken(handle == INVALID_HANDLE_VALUE) /* WinXP */,
+ "Unexpected context handle %p.\n", handle);
+ DeleteFileA("test6.manifest");
+ DeleteFileA("testdep.manifest");
+ if(handle != INVALID_HANDLE_VALUE)
+ {
+ test_runlevel_info(handle, &runlevel_info6, __LINE__);
+ pReleaseActCtx(handle);
+ }
+ }
+ else
+ skip("Could not create manifest file 6\n");
+
+ trace("manifest7\n");
+
+ if(create_manifest_file("test7.manifest", manifest7, -1, NULL, NULL)) {
+ handle = test_create("test7.manifest");
+ ok(handle != INVALID_HANDLE_VALUE, "handle == INVALID_HANDLE_VALUE, error %u\n", GetLastError());
+ DeleteFileA("test7.manifest");
+ DeleteFileA("testdep.manifest");
+ if(handle != INVALID_HANDLE_VALUE)
+ {
+ test_runlevel_info(handle, &runlevel_info7, __LINE__);
+ pReleaseActCtx(handle);
+ }
+ }
+ else
+ skip("Could not create manifest file 7\n");
+
+ trace("manifest8\n");
+
+ if(create_manifest_file("test8.manifest", manifest8, -1, NULL, NULL)) {
+ handle = test_create("test8.manifest");
+ ok(handle != INVALID_HANDLE_VALUE, "handle == INVALID_HANDLE_VALUE, error %u\n", GetLastError());
+ DeleteFileA("test8.manifest");
+ DeleteFileA("testdep.manifest");
+ if(handle != INVALID_HANDLE_VALUE)
+ {
+ test_runlevel_info(handle, &runlevel_info8, __LINE__);
+ pReleaseActCtx(handle);
+ }
+ }
+ else
+ skip("Could not create manifest file 8\n");
+
+ trace("manifest9\n");
+
+ if(create_manifest_file("test9.manifest", manifest9, -1, NULL, NULL)) {
+ handle = test_create("test9.manifest");
+ ok(handle != INVALID_HANDLE_VALUE, "handle == INVALID_HANDLE_VALUE, error %u\n", GetLastError());
+ DeleteFileA("test9.manifest");
+ DeleteFileA("testdep.manifest");
+ if(handle != INVALID_HANDLE_VALUE)
+ {
+ test_runlevel_info(handle, &runlevel_info9, __LINE__);
+ pReleaseActCtx(handle);
+ }
+ }
+ else
+ skip("Could not create manifest file 9\n");
+
trace("manifest4\n");
if(!create_manifest_file("test4.manifest", manifest4, -1, NULL, NULL)) {
@@ -2731,6 +2943,7 @@ START_TEST(actctx)
}
test_actctx();
+ test_create_fail();
test_CreateActCtx();
test_findsectionstring();
test_ZombifyActCtx();
diff --git a/dlls/ntdll/actctx.c b/dlls/ntdll/actctx.c
index 3ba407d83a..4a3370048f 100644
--- a/dlls/ntdll/actctx.c
+++ b/dlls/ntdll/actctx.c
@@ -5271,6 +5271,27 @@ NTSTATUS WINAPI RtlQueryInformationActivationContext( ULONG flags, HANDLE handle
}
break;
+ case RunlevelInformationInActivationContext:
+ {
+ ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION *acrli = buffer;
+ struct assembly *assembly;
+ SIZE_T len;
+
+ if (!(actctx = check_actctx(handle))) return STATUS_INVALID_PARAMETER;
+
+ len = sizeof(*acrli);
+ if (retlen) *retlen = len;
+ if (!buffer || bufsize < len)
+ return STATUS_BUFFER_TOO_SMALL;
+
+ assembly = actctx->assemblies;
+
+ acrli->ulFlags = 0;
+ acrli->RunLevel = assembly ? assembly->run_level : ACTCTX_RUN_LEVEL_UNSPECIFIED;
+ acrli->UiAccess = assembly ? assembly->ui_access : 0;
+ }
+ break;
+
default:
FIXME( "class %u not implemented\n", class );
return STATUS_NOT_IMPLEMENTED;
--
2.16.1
More information about the wine-devel
mailing list