diff --git a/patches/ntdll-RunlevelInformationInActivationContext/0001-include-Add-run-level-information-enum-and-structure.patch b/patches/ntdll-RunlevelInformationInActivationContext/0001-include-Add-run-level-information-enum-and-structure.patch new file mode 100644 index 00000000..1554f5d7 --- /dev/null +++ b/patches/ntdll-RunlevelInformationInActivationContext/0001-include-Add-run-level-information-enum-and-structure.patch @@ -0,0 +1,47 @@ +From c8675f4675c856711f0b3e3395e484e77e6c4c00 Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Michael=20M=C3=BCller?= +Date: Tue, 10 Jan 2017 21:04:11 +0100 +Subject: include: Add run level information enum and structure to winnt.h. + +--- + include/winnt.h | 19 +++++++++++++++++++ + 1 file changed, 19 insertions(+) + +diff --git a/include/winnt.h b/include/winnt.h +index 72c399b410f..abdd7569eed 100644 +--- a/include/winnt.h ++++ b/include/winnt.h +@@ -5670,11 +5670,30 @@ typedef struct _ASSEMBLY_FILE_DETAILED_INFORMATION { + + typedef const ASSEMBLY_FILE_DETAILED_INFORMATION *PCASSEMBLY_FILE_DETAILED_INFORMATION; + ++typedef enum { ++ ACTCTX_RUN_LEVEL_UNSPECIFIED = 0, ++ ACTCTX_RUN_LEVEL_AS_INVOKER, ++ ACTCTX_RUN_LEVEL_HIGHEST_AVAILABLE, ++ ACTCTX_RUN_LEVEL_REQUIRE_ADMIN, ++ ACTCTX_RUN_LEVEL_NUMBERS ++} ACTCTX_REQUESTED_RUN_LEVEL; ++ ++typedef struct _ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION { ++ DWORD ulFlags; ++ ACTCTX_REQUESTED_RUN_LEVEL RunLevel; ++ DWORD UiAccess; ++} ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION, *PACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION; ++ ++typedef const struct _ACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION *PCACTIVATION_CONTEXT_RUN_LEVEL_INFORMATION; ++ + typedef enum _ACTIVATION_CONTEXT_INFO_CLASS { + ActivationContextBasicInformation = 1, + ActivationContextDetailedInformation = 2, + AssemblyDetailedInformationInActivationContext = 3, + FileInformationInAssemblyOfAssemblyInActivationContext = 4, ++ RunlevelInformationInActivationContext = 5, ++ CompatibilityInformationInActivationContext = 6, ++ ActivationContextManifestResourceName = 7, + MaxActivationContextInfoClass, + + AssemblyDetailedInformationInActivationContxt = 3, +-- +2.11.0 + diff --git a/patches/ntdll-RunlevelInformationInActivationContext/0002-ntdll-Parse-execution-level-information-in-manifest-.patch b/patches/ntdll-RunlevelInformationInActivationContext/0002-ntdll-Parse-execution-level-information-in-manifest-.patch new file mode 100644 index 00000000..e405e592 --- /dev/null +++ b/patches/ntdll-RunlevelInformationInActivationContext/0002-ntdll-Parse-execution-level-information-in-manifest-.patch @@ -0,0 +1,210 @@ +From d7c46fb48d7fab2cd7caa498843f85ff085cae6a Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Michael=20M=C3=BCller?= +Date: Tue, 10 Jan 2017 21:06:06 +0100 +Subject: ntdll: Parse execution level information in manifest data. + +--- + dlls/ntdll/actctx.c | 166 +++++++++++++++++++++++++++++++++++++++++++++++++--- + 1 file changed, 157 insertions(+), 9 deletions(-) + +diff --git a/dlls/ntdll/actctx.c b/dlls/ntdll/actctx.c +index 323ee68fc09..6801bcfb6d2 100644 +--- a/dlls/ntdll/actctx.c ++++ b/dlls/ntdll/actctx.c +@@ -490,15 +490,18 @@ enum assembly_type + + struct assembly + { +- enum assembly_type type; +- struct assembly_identity id; +- struct file_info manifest; +- WCHAR *directory; +- BOOL no_inherit; +- struct dll_redirect *dlls; +- unsigned int num_dlls; +- unsigned int allocated_dlls; +- struct entity_array entities; ++ enum assembly_type type; ++ struct assembly_identity id; ++ struct file_info manifest; ++ WCHAR *directory; ++ BOOL no_inherit; ++ struct dll_redirect *dlls; ++ unsigned int num_dlls; ++ unsigned int allocated_dlls; ++ struct entity_array entities; ++ BOOL rel_found; ++ ACTCTX_REQUESTED_RUN_LEVEL run_level; ++ DWORD ui_access; + }; + + enum context_sections +@@ -557,6 +560,10 @@ static const WCHAR fileW[] = {'f','i','l','e',0}; + static const WCHAR hashW[] = {'h','a','s','h',0}; + static const WCHAR noInheritW[] = {'n','o','I','n','h','e','r','i','t',0}; + static const WCHAR noInheritableW[] = {'n','o','I','n','h','e','r','i','t','a','b','l','e',0}; ++static const WCHAR requestedExecutionLevelW[] = {'r','e','q','u','e','s','t','e','d','E','x','e','c','u','t','i','o','n','L','e','v','e','l',0}; ++static const WCHAR requestedPrivilegesW[] = {'r','e','q','u','e','s','t','e','d','P','r','i','v','i','l','e','g','e','s',0}; ++static const WCHAR securityW[] ={'s','e','c','u','r','i','t','y',0}; ++static const WCHAR trustInfoW[] = {'t','r','u','s','t','I','n','f','o',0}; + static const WCHAR typelibW[] = {'t','y','p','e','l','i','b',0}; + static const WCHAR windowClassW[] = {'w','i','n','d','o','w','C','l','a','s','s',0}; + +@@ -2024,6 +2031,142 @@ static BOOL parse_clr_surrogate_elem(xmlbuf_t* xmlbuf, struct assembly* assembly + return parse_expect_end_elem(xmlbuf, clrSurrogateW, asmv1W); + } + ++static BOOL parse_requested_execution_level_elem(xmlbuf_t* xmlbuf, struct assembly* assembly, struct actctx_loader *acl) ++{ ++ static const WCHAR levelW[] = {'l','e','v','e','l',0}; ++ static const WCHAR asInvokerW[] = {'a','s','I','n','v','o','k','e','r',0}; ++ static const WCHAR requireAdministratorW[] = {'r','e','q','u','i','r','e','A','d','m','i','n','i','s','t','r','a','t','o','r',0}; ++ static const WCHAR highestAvailableW[] = {'h','i','g','h','e','s','t','A','v','a','i','l','a','b','l','e',0}; ++ static const WCHAR uiAccessW[] = {'u','i','A','c','c','e','s','s',0}; ++ static const WCHAR falseW[] = {'f','a','l','s','e',0}; ++ static const WCHAR trueW[] = {'t','r','u','e',0}; ++ ++ xmlstr_t attr_name, attr_value, elem; ++ BOOL end = FALSE, ret = TRUE, error; ++ ++ /* windows does not like multiple requestedExecutionLevel tags */ ++ if (assembly->rel_found) ++ return FALSE; ++ assembly->rel_found = TRUE; ++ ++ while (next_xml_attr(xmlbuf, &attr_name, &attr_value, &error, &end)) ++ { ++ if (xmlstr_cmp(&attr_name, levelW)) ++ { ++ if (xmlstr_cmpi(&attr_value, asInvokerW)) ++ assembly->run_level = ACTCTX_RUN_LEVEL_AS_INVOKER; ++ else if (xmlstr_cmpi(&attr_value, highestAvailableW)) ++ assembly->run_level = ACTCTX_RUN_LEVEL_HIGHEST_AVAILABLE; ++ else if (xmlstr_cmpi(&attr_value, requireAdministratorW)) ++ assembly->run_level = ACTCTX_RUN_LEVEL_REQUIRE_ADMIN; ++ else ++ FIXME("unknown security level: %s\n", debugstr_xmlstr(&attr_value)); ++ } ++ else if (xmlstr_cmp(&attr_name, uiAccessW)) ++ { ++ if (xmlstr_cmpi(&attr_value, falseW)) ++ assembly->ui_access = FALSE; ++ else if (xmlstr_cmpi(&attr_value, trueW)) ++ assembly->ui_access = TRUE; ++ else ++ FIXME("unknown uiAccess value: %s\n", debugstr_xmlstr(&attr_value)); ++ } ++ else ++ FIXME("unknown attr %s=%s\n", debugstr_xmlstr(&attr_name), debugstr_xmlstr(&attr_value)); ++ } ++ ++ if (error) return FALSE; ++ if (end) return TRUE; ++ ++ while (ret && (ret = next_xml_elem(xmlbuf, &elem))) ++ { ++ if (xmlstr_cmp_end(&elem, requestedExecutionLevelW)) ++ { ++ ret = parse_end_element(xmlbuf); ++ break; ++ } ++ else ++ { ++ FIXME("unknown element %s\n", debugstr_xmlstr(&elem)); ++ ret = parse_unknown_elem(xmlbuf, &elem); ++ } ++ } ++ ++ return ret; ++} ++ ++static BOOL parse_requested_privileges_elem(xmlbuf_t* xmlbuf, struct assembly* assembly, struct actctx_loader *acl) ++{ ++ xmlstr_t elem; ++ BOOL ret = TRUE; ++ ++ while (ret && (ret = next_xml_elem(xmlbuf, &elem))) ++ { ++ if (xmlstr_cmp_end(&elem, requestedPrivilegesW)) ++ { ++ ret = parse_end_element(xmlbuf); ++ break; ++ } ++ else if (xmlstr_cmp(&elem, requestedExecutionLevelW)) ++ ret = parse_requested_execution_level_elem(xmlbuf, assembly, acl); ++ else ++ { ++ WARN("unknown elem %s\n", debugstr_xmlstr(&elem)); ++ ret = parse_unknown_elem(xmlbuf, &elem); ++ } ++ } ++ ++ return ret; ++} ++ ++static BOOL parse_security_elem(xmlbuf_t* xmlbuf, struct assembly* assembly, struct actctx_loader *acl) ++{ ++ xmlstr_t elem; ++ BOOL ret = TRUE; ++ ++ while (ret && (ret = next_xml_elem(xmlbuf, &elem))) ++ { ++ if (xmlstr_cmp_end(&elem, securityW)) ++ { ++ ret = parse_end_element(xmlbuf); ++ break; ++ } ++ else if (xmlstr_cmp(&elem, requestedPrivilegesW)) ++ ret = parse_requested_privileges_elem(xmlbuf, assembly, acl); ++ else ++ { ++ WARN("unknown elem %s\n", debugstr_xmlstr(&elem)); ++ ret = parse_unknown_elem(xmlbuf, &elem); ++ } ++ } ++ ++ return ret; ++} ++ ++static BOOL parse_trust_info_elem(xmlbuf_t* xmlbuf, struct assembly* assembly, struct actctx_loader *acl) ++{ ++ xmlstr_t elem; ++ BOOL ret = TRUE; ++ ++ while (ret && (ret = next_xml_elem(xmlbuf, &elem))) ++ { ++ if (xmlstr_cmp_end(&elem, trustInfoW)) ++ { ++ ret = parse_end_element(xmlbuf); ++ break; ++ } ++ else if (xmlstr_cmp(&elem, securityW)) ++ ret = parse_security_elem(xmlbuf, assembly, acl); ++ else ++ { ++ WARN("unknown elem %s\n", debugstr_xmlstr(&elem)); ++ ret = parse_unknown_elem(xmlbuf, &elem); ++ } ++ } ++ ++ return ret; ++} ++ + static BOOL parse_dependent_assembly_elem(xmlbuf_t* xmlbuf, struct actctx_loader* acl, BOOL optional) + { + struct assembly_identity ai; +@@ -2296,6 +2439,11 @@ static BOOL parse_assembly_elem(xmlbuf_t* xmlbuf, struct actctx_loader* acl, + { + ret = parse_clr_surrogate_elem(xmlbuf, assembly, acl); + } ++ else if (xml_elem_cmp(&elem, trustInfoW, asmv2W) || ++ xml_elem_cmp(&elem, trustInfoW, asmv1W)) ++ { ++ ret = parse_trust_info_elem(xmlbuf, assembly, acl); ++ } + else if (xml_elem_cmp(&elem, assemblyIdentityW, asmv1W)) + { + if (!parse_assembly_identity_elem(xmlbuf, acl->actctx, &assembly->id)) return FALSE; +-- +2.11.0 + diff --git a/patches/ntdll-RunlevelInformationInActivationContext/0003-ntdll-Implement-RunlevelInformationInActivationConte.patch b/patches/ntdll-RunlevelInformationInActivationContext/0003-ntdll-Implement-RunlevelInformationInActivationConte.patch new file mode 100644 index 00000000..b5a2843a --- /dev/null +++ b/patches/ntdll-RunlevelInformationInActivationContext/0003-ntdll-Implement-RunlevelInformationInActivationConte.patch @@ -0,0 +1,299 @@ +From b27724fbab526d24311fd312eeff280e2688ca1c Mon Sep 17 00:00:00 2001 +From: =?UTF-8?q?Michael=20M=C3=BCller?= +Date: Tue, 10 Jan 2017 21:07:58 +0100 +Subject: ntdll: Implement RunlevelInformationInActivationContext in + RtlQueryInformationActivationContext. + +--- + dlls/kernel32/tests/actctx.c | 207 +++++++++++++++++++++++++++++++++++++++++++ + dlls/ntdll/actctx.c | 21 +++++ + 2 files changed, 228 insertions(+) + +diff --git a/dlls/kernel32/tests/actctx.c b/dlls/kernel32/tests/actctx.c +index af3dadf79a5..f9f66d945eb 100644 +--- a/dlls/kernel32/tests/actctx.c ++++ b/dlls/kernel32/tests/actctx.c +@@ -244,6 +244,61 @@ static const char manifest5[] = + "" + ""; + ++static const char manifest6[] = ++"" ++"" ++"" ++" " ++" " ++" " ++" " ++" " ++"" ++""; ++ ++static const char manifest7[] = ++"" ++"" ++"" ++" " ++" " ++" " ++" " ++" " ++"" ++""; ++ ++static const char manifest8[] = ++"" ++"" ++"" ++" " ++" " ++" " ++" " ++" " ++" " ++"" ++""; ++ ++static const char manifest9[] = ++"" ++"" ++"" ++" " ++" " ++" " ++" " ++" " ++"" ++"" ++" " ++" " ++" " ++" " ++"" ++""; ++ + static const char testdep_manifest1[] = + "" + "" +@@ -310,6 +365,38 @@ static const char wrong_manifest8[] = + "" + ""; + ++static const char wrong_manifest9[] = ++"" ++"" ++"" ++" " ++" " ++" " ++" " ++" " ++" " ++"" ++""; ++ ++static const char wrong_manifest10[] = ++"" ++"" ++"" ++" " ++" " ++" " ++" " ++" " ++"" ++"" ++" " ++" " ++" " ++" " ++" " ++"" ++""; ++ + static const char wrong_depmanifest1[] = + "" + "" +@@ -732,6 +819,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; +@@ -837,6 +975,10 @@ static void test_create_fail(void) + test_create_and_fail(wrong_manifest7, NULL, 1 ); + trace("wrong_manifest8\n"); + test_create_and_fail(wrong_manifest8, NULL, 0 ); ++ trace("wrong_manifest9\n"); ++ test_create_and_fail(wrong_manifest9, NULL, 0 ); ++ trace("wrong_manifest10\n"); ++ test_create_and_fail(wrong_manifest10, NULL, 0 ); + trace("UTF-16 manifest1 without BOM\n"); + test_create_wide_and_fail(manifest1, FALSE ); + trace("manifest2\n"); +@@ -1784,6 +1926,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); + } + +@@ -1955,6 +2098,70 @@ 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, "handle == INVALID_HANDLE_VALUE, error %u\n", GetLastError()); ++ 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)) { +diff --git a/dlls/ntdll/actctx.c b/dlls/ntdll/actctx.c +index 6801bcfb6d2..c1c83fd7704 100644 +--- a/dlls/ntdll/actctx.c ++++ b/dlls/ntdll/actctx.c +@@ -5132,6 +5132,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 : FALSE; ++ } ++ break; ++ + default: + FIXME( "class %u not implemented\n", class ); + return STATUS_NOT_IMPLEMENTED; +-- +2.11.0 + diff --git a/patches/ntdll-RunlevelInformationInActivationContext/definition b/patches/ntdll-RunlevelInformationInActivationContext/definition new file mode 100644 index 00000000..ecedbdab --- /dev/null +++ b/patches/ntdll-RunlevelInformationInActivationContext/definition @@ -0,0 +1,2 @@ +Fixes: Implement RunlevelInformationInActivationContext in RtlQueryInformationActivationContext +# FIXME: Some tests do not pass on Windows versions < Vista yet. diff --git a/patches/patchinstall.sh b/patches/patchinstall.sh index 45ff0bf0..771040bc 100755 --- a/patches/patchinstall.sh +++ b/patches/patchinstall.sh @@ -246,6 +246,7 @@ patch_enable_all () enable_ntdll_RtlIpStringToAddress_Stubs="$1" enable_ntdll_RtlIpStringToAddress_Tests="$1" enable_ntdll_RtlQueryPackageIdentity="$1" + enable_ntdll_RunlevelInformationInActivationContext="$1" enable_ntdll_Serial_Port_Detection="$1" enable_ntdll_Stack_Guard_Page="$1" enable_ntdll_Stack_Overflow="$1" @@ -945,6 +946,9 @@ patch_enable () ntdll-RtlQueryPackageIdentity) enable_ntdll_RtlQueryPackageIdentity="$2" ;; + ntdll-RunlevelInformationInActivationContext) + enable_ntdll_RunlevelInformationInActivationContext="$2" + ;; ntdll-Serial_Port_Detection) enable_ntdll_Serial_Port_Detection="$2" ;; @@ -5680,6 +5684,22 @@ if test "$enable_ntdll_RtlIpStringToAddress_Tests" -eq 1; then ) >> "$patchlist" fi +# Patchset ntdll-RunlevelInformationInActivationContext +# | +# | Modified files: +# | * dlls/kernel32/tests/actctx.c, dlls/ntdll/actctx.c, include/winnt.h +# | +if test "$enable_ntdll_RunlevelInformationInActivationContext" -eq 1; then + patch_apply ntdll-RunlevelInformationInActivationContext/0001-include-Add-run-level-information-enum-and-structure.patch + patch_apply ntdll-RunlevelInformationInActivationContext/0002-ntdll-Parse-execution-level-information-in-manifest-.patch + patch_apply ntdll-RunlevelInformationInActivationContext/0003-ntdll-Implement-RunlevelInformationInActivationConte.patch + ( + echo '+ { "Michael Müller", "include: Add run level information enum and structure to winnt.h.", 1 },'; + echo '+ { "Michael Müller", "ntdll: Parse execution level information in manifest data.", 1 },'; + echo '+ { "Michael Müller", "ntdll: Implement RunlevelInformationInActivationContext in RtlQueryInformationActivationContext.", 1 },'; + ) >> "$patchlist" +fi + # Patchset ntdll-Serial_Port_Detection # | # | This patchset fixes the following Wine bugs: