当前位置: 首页 > news >正文

【Windows】获取进程缓解策略设置情况

目录

一、前言

二、主要概念

三、实现步骤

四、总结


原文出处链接:[https://blog.csdn.net/qq_59075481/article/details/142234952]

一、前言

在现代操作系统中,进程缓解策略(Process Mitigation Policy)提供了一种防御机制,可以防止潜在的攻击对系统中的进程进行利用。通过分析进程的缓解策略设置,开发人员和系统管理员可以更好地了解当前进程的安全状态以及应用了哪些安全措施。

本文介绍一种通过编程方式获取进程的缓解策略设置的方法。我们将利用 Windows 提供的 GetProcessMitigationPolicy 函数来获取不同类型的缓解策略,并使用 C 示例来演示如何实现这一功能。

警告:我们将在下一篇讲解如何远程修改部分安全缓解策略以及缓解策略的绕过技术。

二、主要概念

在 Windows 操作系统中,每个进程都可以设置多种缓解策略,这些策略可以增强系统安全性。常见的缓解策略包括:

进程缓解策略是操作系统用来防止恶意软件或攻击者利用进程漏洞的安全机制。以下是一些常见的缓解策略:

  1. 数据执行防护 (DEP, Data Execution Prevention):DEP 是一种安全功能,旨在防止恶意代码执行非代码区域的内容(如堆栈或堆)。启用 DEP 后,如果在数据区中检测到代码执行,将导致进程异常终止。
  2. 地址空间布局随机化 (ASLR, Address Space Layout Randomization):ASLR 通过随机化程序的内存地址来增加攻击者预测这些地址的难度。通过随机化可执行文件、DLLs、堆、栈和其他内存区域的位置,ASLR 可以有效防止缓冲区溢出和其他内存攻击。
  3. 动态代码执行限制 (Dynamic Code Policy):该策略限制进程生成动态代码或修改现有的可执行代码,防止恶意代码注入和代码覆盖攻击。
  4. 控制流保护 (CFG, Control Flow Guard):CFG 是一种防御机制,用于防止间接调用的目标被篡改,从而保护程序免受控制流劫持攻击。CFG 可通过在运行时检查目标地址是否安全来防止攻击。
  5. 结构化异常处理覆盖保护 (SEHOP, Structured Exception Handling Overwrite Protection):SEHOP 保护 Windows 应用程序免受结构化异常处理(SEH)覆盖攻击,这是堆栈缓冲区溢出攻击的一种形式。
  6. 系统调用禁用 (System Call Disable Policy):该策略可以禁止进程进行特定的系统调用,以限制进程与操作系统内核的交互,降低进程被利用的风险。
  7. 子进程创建策略 (Child Process Policy):限制进程创建子进程的能力,防止恶意软件通过子进程传播或执行进一步的攻击。
  8. 映像加载策略 (Image Load Policy):该策略控制哪些类型的可执行文件可以映射到进程地址空间,防止从不受信任的来源加载恶意代码。

进程缓解策略有哪些?(进程缓解策略从 Win 8 开始引入,下面的版本是目前 Win10/11 上的枚举)。

typedef enum _PROCESS_MITIGATION_POLICY {ProcessDEPPolicy,ProcessASLRPolicy,ProcessDynamicCodePolicy,ProcessStrictHandleCheckPolicy,ProcessSystemCallDisablePolicy,ProcessMitigationOptionsMask,ProcessExtensionPointDisablePolicy,ProcessControlFlowGuardPolicy,ProcessSignaturePolicy,ProcessFontDisablePolicy,ProcessImageLoadPolicy,ProcessSystemCallFilterPolicy,ProcessPayloadRestrictionPolicy,ProcessChildProcessPolicy,ProcessSideChannelIsolationPolicy,ProcessUserShadowStackPolicy,ProcessRedirectionTrustPolicy,ProcessUserPointerAuthPolicy,ProcessSEHOPPolicy,ProcessActivationContextTrustPolicy,MaxProcessMitigationPolicy
} PROCESS_MITIGATION_POLICY, *PPROCESS_MITIGATION_POLICY;

三、实现步骤

以下步骤描述了如何获取和显示进程的缓解策略:

  1. 获取目标进程的句柄: 使用 OpenProcess 函数以 PROCESS_QUERY_LIMITED_INFORMATION 权限打开目标进程。
  2. 启用SE_DEBUG_NAME特权: 调用 EnableDebugPrivilege 函数启用调试特权,使得当前进程能够访问所有进程的信息。
  3. 获取进程的路径和描述信息: 使用 QueryFullProcessImageNameW 函数获取进程的完整路径,并调用 GetProcessDescription 函数获取PE文件的描述信息。
  4. 获取并显示缓解策略: 使用 GetProcessMitigationPolicy 函数依次获取不同类型的缓解策略(如 DEP、ASLR、CFG 等),并打印每个策略的二进制表示和详细分析。

代码示例

获取进程缓解策略的前提:当前线程对目标进程至少能打开有限信息查询访问句柄。

查询进程缓解策略的需求:至少以 PROCESS_QUERY_LIMITED_INFORMATION 访问权限打开进程。部分进程的访问可能需要至少需要管理员身份。

描述:目前 win11 上面有 20 组缓解策略,每个策略占一个 32 位二进制位(DWORD),但结构中有很多保留位暂未使用。

以下是核心代码实现,它展示了如何获取和打印进程的缓解策略:

#include <tchar.h>
#include <stdio.h>
#include <Windows.h>
#include <Processthreadsapi.h>
#include <winver.h>#pragma comment(lib, "Version.lib")// 打印 DWORD 类型的 Flags 的二进制表示,每一位之间用 | 分隔
static void PrintBinaryFlags(DWORD flags)
{printf(" Policy Flags: \n");// 打印位偏移(从 0 到 31)for (int i = 31; i >= 0; i--){printf("%2d", i);if (i != 0) {printf(" | ");}}printf("\n");// 打印 Flags 的二进制表示for (int i = 31; i >= 0; i--){printf(" %d", (flags >> i) & 1);  // 右移并与 1 进行按位与操作,提取该位if (i != 0) {printf(" | ");}}printf("\n");
}static void show_mitigations(HANDLE hProc) {PROCESS_MITIGATION_DEP_POLICY dep = { 0 };PROCESS_MITIGATION_ASLR_POLICY aslr = { 0 };PROCESS_MITIGATION_DYNAMIC_CODE_POLICY dynamic_code = { 0 };PROCESS_MITIGATION_STRICT_HANDLE_CHECK_POLICY strict_handle_check = { 0 };PROCESS_MITIGATION_SYSTEM_CALL_DISABLE_POLICY system_call_disable = { 0 };ULONG64 mitigation_options = { 0 };PROCESS_MITIGATION_EXTENSION_POINT_DISABLE_POLICY extension_point_disable = { 0 };PROCESS_MITIGATION_CONTROL_FLOW_GUARD_POLICY cfg = { 0 };PROCESS_MITIGATION_BINARY_SIGNATURE_POLICY signature = { 0 };PROCESS_MITIGATION_FONT_DISABLE_POLICY font = { 0 };PROCESS_MITIGATION_IMAGE_LOAD_POLICY image_load = { 0 };PROCESS_MITIGATION_SYSTEM_CALL_FILTER_POLICY syscall_filter = { 0 };  // win11 NewPROCESS_MITIGATION_PAYLOAD_RESTRICTION_POLICY payload_rtict = { 0 };   // win11 NewPROCESS_MITIGATION_CHILD_PROCESS_POLICY child_proc = { 0 };            // win11 NewPROCESS_MITIGATION_SIDE_CHANNEL_ISOLATION_POLICY side_cnl_isan = { 0 };PROCESS_MITIGATION_USER_SHADOW_STACK_POLICY usw_stack = { 0 };PROCESS_MITIGATION_REDIRECTION_TRUST_POLICY trust_redc = { 0 };PROCESS_MITIGATION_USER_POINTER_AUTH_POLICY upt_auth = { 0 };PROCESS_MITIGATION_SEHOP_POLICY seh_op_policy = { 0 };PROCESS_MITIGATION_ACTIVATION_CONTEXT_TRUST_POLICY activ_ctx_truct = { 0 };  // win11 New/*描述:数据执行防护 (DEP) 的进程缓解策略。typedef struct _PROCESS_MITIGATION_DEP_POLICY {union {DWORD Flags;struct {DWORD Enable : 1;DWORD DisableAtlThunkEmulation : 1;DWORD ReservedFlags : 30;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;BOOLEAN Permanent;} PROCESS_MITIGATION_DEP_POLICY, *PPROCESS_MITIGATION_DEP_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessDEPPolicy, &dep, sizeof(dep));printf("ProcessDEPPolicy:\n");PrintBinaryFlags(dep.Flags);printf("\n Analysis:\n");printf("   Enable                                     %u\n", dep.Enable);printf("   DisableAtlThunkEmulation                   %u\n", dep.DisableAtlThunkEmulation);printf("\n");/*描述:地址空间布局随机化 (ASLR) 的进程缓解策略。typedef struct _PROCESS_MITIGATION_ASLR_POLICY {union {DWORD Flags;struct {DWORD EnableBottomUpRandomization : 1;DWORD EnableForceRelocateImages : 1;DWORD EnableHighEntropy : 1;DWORD DisallowStrippedImages : 1;DWORD ReservedFlags : 28;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_ASLR_POLICY, *PPROCESS_MITIGATION_ASLR_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessASLRPolicy, &aslr, sizeof(aslr));printf("ProcessASLRPolicy:\n");PrintBinaryFlags(aslr.Flags);printf("\n Analysis:\n");printf("   EnableBottomUpRandomization                %u\n", aslr.EnableBottomUpRandomization);printf("   EnableForceRelocateImages                  %u\n", aslr.EnableForceRelocateImages);printf("   EnableHighEntropy                          %u\n", aslr.EnableHighEntropy);printf("   DisallowStrippedImages                     %u\n", aslr.DisallowStrippedImages);printf("\n");/*描述:动态代码执行进程缓解策略。启用后,进程无法生成动态代码或修改现有的可执行代码。typedef struct _PROCESS_MITIGATION_DYNAMIC_CODE_POLICY {union {DWORD Flags;struct {DWORD ProhibitDynamicCode : 1;DWORD AllowThreadOptOut : 1;DWORD AllowRemoteDowngrade : 1;DWORD AuditProhibitDynamicCode : 1;DWORD ReservedFlags : 28;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_DYNAMIC_CODE_POLICY, *PPROCESS_MITIGATION_DYNAMIC_CODE_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessDynamicCodePolicy, &dynamic_code, sizeof(dynamic_code));printf("ProcessStrictHandleCheckPolicy:\n");PrintBinaryFlags(dynamic_code.Flags);printf("\n Analysis:\n");printf("   ProhibitDynamicCode                        %u\n", dynamic_code.ProhibitDynamicCode);printf("   AllowThreadOptOut                          %u\n", dynamic_code.AllowThreadOptOut);printf("   AllowRemoteDowngrade                       %u\n", dynamic_code.AllowRemoteDowngrade);printf("   AuditProhibitDynamicCode                   %u\n", dynamic_code.AuditProhibitDynamicCode);printf("\n");/*描述:如果进程操作无效的句柄,则会收到严重错误。typedef struct _PROCESS_MITIGATION_STRICT_HANDLE_CHECK_POLICY {union {DWORD Flags;struct {DWORD RaiseExceptionOnInvalidHandleReference : 1;DWORD HandleExceptionsPermanentlyEnabled : 1;DWORD ReservedFlags : 30;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_STRICT_HANDLE_CHECK_POLICY, *PPROCESS_MITIGATION_STRICT_HANDLE_CHECK_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessStrictHandleCheckPolicy, &strict_handle_check, sizeof(strict_handle_check));printf("ProcessStrictHandleCheckPolicy:\n");PrintBinaryFlags(strict_handle_check.Flags);printf("\n Analysis:\n");printf("   RaiseExceptionOnInvalidHandleReference     %u\n", strict_handle_check.RaiseExceptionOnInvalidHandleReference);printf("   HandleExceptionsPermanentlyEnabled         %u\n", strict_handle_check.HandleExceptionsPermanentlyEnabled);printf("\n");/*描述:禁用在最底层使用 NTUser/GDI 函数的功能。typedef struct _PROCESS_MITIGATION_SYSTEM_CALL_DISABLE_POLICY {union {DWORD Flags;struct {DWORD DisallowWin32kSystemCalls : 1;DWORD AuditDisallowWin32kSystemCalls : 1;DWORD ReservedFlags : 30;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_SYSTEM_CALL_DISABLE_POLICY, *PPROCESS_MITIGATION_SYSTEM_CALL_DISABLE_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessSystemCallDisablePolicy, &system_call_disable, sizeof(system_call_disable));printf("ProcessSystemCallDisablePolicy:\n");PrintBinaryFlags(system_call_disable.Flags);printf("\n Analysis:\n");printf("   DisallowWin32kSystemCalls                  %u\n", system_call_disable.DisallowWin32kSystemCalls);printf("   AuditDisallowWin32kSystemCalls             %u\n", system_call_disable.AuditDisallowWin32kSystemCalls);printf("\n");/** 描述:返回系统上所有缓解选项的有效位掩码(3333333333333303,看样子第四位是没用到还是啥意思?)。*       掩码:*		      1011110101111010011000100101010000000101010100110111* *       应用程序可以设置许多缓解选项,而无需查询操作系统的缓解选项,*       方法是将按位与掩码组合在一起,一次排除所有不支持的位。*        lpBuffer 参数指向掩码的 ULONG64 位向量,或 ULONG64 位向量的双元素数组。*/GetProcessMitigationPolicy(hProc, ProcessMitigationOptionsMask, &mitigation_options, sizeof(mitigation_options));printf("ProcessMitigationOptionsMask:\n");printf("   MitigationOptions                          %llx\n", mitigation_options);printf("\n");/*描述:阻止启用某些内置第三方扩展点,从而阻止将旧扩展点 DLL 加载到进程中。typedef struct _PROCESS_MITIGATION_EXTENSION_POINT_DISABLE_POLICY {union {DWORD Flags;struct {DWORD DisableExtensionPoints : 1;DWORD ReservedFlags : 31;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_EXTENSION_POINT_DISABLE_POLICY, *PPROCESS_MITIGATION_EXTENSION_POINT_DISABLE_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessExtensionPointDisablePolicy, &extension_point_disable, sizeof(extension_point_disable));printf("ProcessExtensionPointDisablePolicy:\n");PrintBinaryFlags(extension_point_disable.Flags);printf("\n Analysis:\n");printf("   DisableExtensionPoints                     %u\n", extension_point_disable.DisableExtensionPoints);printf("\n");/*描述:控制流防护 (CFG) 的进程缓解策略。typedef struct _PROCESS_MITIGATION_CONTROL_FLOW_GUARD_POLICY {union {DWORD Flags;struct {DWORD EnableControlFlowGuard : 1;DWORD EnableExportSuppression : 1;DWORD StrictMode : 1;DWORD EnableXfg : 1;DWORD EnableXfgAuditMode : 1;DWORD ReservedFlags : 27;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_CONTROL_FLOW_GUARD_POLICY, *PPROCESS_MITIGATION_CONTROL_FLOW_GUARD_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessControlFlowGuardPolicy, &cfg, sizeof(cfg));printf("ProcessControlFlowGuardPolicy:\n");PrintBinaryFlags(cfg.Flags);printf("\n Analysis:\n");printf("   EnableControlFlowGuard                     %u\n", cfg.EnableControlFlowGuard);printf("   EnableExportSuppression                    %u\n", cfg.EnableExportSuppression);printf("   StrictMode                                 %u\n", cfg.StrictMode);printf("   EnableXfg                                  %u\n", cfg.EnableXfg);printf("   EnableXfgAuditMode                         %u\n", cfg.EnableXfgAuditMode);printf("\n");/*描述:可以将映像加载限制为由 Microsoft、Windows 应用商店或Microsoft、Windows 应用商店和 Windows 硬件质量实验室 (WHQL) 签名的映像的进程缓解策略。typedef struct _PROCESS_MITIGATION_BINARY_SIGNATURE_POLICY {union {DWORD Flags;struct {DWORD MicrosoftSignedOnly : 1;DWORD StoreSignedOnly : 1;DWORD MitigationOptIn : 1;DWORD AuditMicrosoftSignedOnly : 1;DWORD AuditStoreSignedOnly : 1;DWORD ReservedFlags : 27;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_BINARY_SIGNATURE_POLICY, *PPROCESS_MITIGATION_BINARY_SIGNATURE_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessSignaturePolicy, &signature, sizeof(signature));printf("ProcessSignaturePolicy:\n");PrintBinaryFlags(signature.Flags);printf("\n Analysis:\n");printf("   MicrosoftSignedOnly                        %u\n", signature.MicrosoftSignedOnly);printf("   StoreSignedOnly                            %u\n", signature.StoreSignedOnly);printf("   MitigationOptIn                            %u\n", signature.MitigationOptIn);printf("   AuditMicrosoftSignedOnly                   %u\n", signature.AuditMicrosoftSignedOnly);printf("   AuditStoreSignedOnly                       %u\n", signature.AuditStoreSignedOnly);printf("\n");/*描述:有关进程的字体加载的缓解策略。启用后,进程无法加载非系统字体。typedef struct _PROCESS_MITIGATION_FONT_DISABLE_POLICY {union {DWORD Flags;struct {DWORD DisableNonSystemFonts     : 1;DWORD AuditNonSystemFontLoading : 1;DWORD ReservedFlags             : 30;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_FONT_DISABLE_POLICY, *PPROCESS_MITIGATION_FONT_DISABLE_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessFontDisablePolicy, &font, sizeof(font));printf("ProcessFontDisablePolicy:\n");PrintBinaryFlags(font.Flags);printf("\n Analysis:\n");printf("   DisableNonSystemFonts                      %u\n", font.DisableNonSystemFonts);printf("   AuditNonSystemFontLoading                  %u\n", font.AuditNonSystemFontLoading);printf("\n");/*描述:有关进程映像加载的策略,该策略确定允许映射到进程的可执行映像的类型。启用后,无法从某些位置加载映像,例如具有低强制签名的远程设备或文件。typedef struct _PROCESS_MITIGATION_IMAGE_LOAD_POLICY {union {DWORD Flags;struct {DWORD NoRemoteImages : 1;DWORD NoLowMandatoryLabelImages : 1;DWORD PreferSystem32Images : 1;DWORD AuditNoRemoteImages : 1;DWORD AuditNoLowMandatoryLabelImages : 1;DWORD ReservedFlags : 27;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_IMAGE_LOAD_POLICY, *PPROCESS_MITIGATION_IMAGE_LOAD_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessImageLoadPolicy, &image_load, sizeof(image_load));printf("ProcessImageLoadPolicy:\n");PrintBinaryFlags(image_load.Flags);printf("\n Analysis:\n");printf("   NoRemoteImages                             %u\n", image_load.NoRemoteImages);printf("   NoLowMandatoryLabelImages                  %u\n", image_load.NoLowMandatoryLabelImages);printf("   PreferSystem32Images                       %u\n", image_load.PreferSystem32Images);printf("   AuditNoRemoteImages                        %u\n", image_load.AuditNoRemoteImages);printf("   AuditNoLowMandatoryLabelImages             %u\n", image_load.AuditNoLowMandatoryLabelImages);printf("\n");/*描述:关于系统调用的进程筛选器缓解策略。typedef struct _PROCESS_MITIGATION_SYSTEM_CALL_FILTER_POLICY {union {DWORD Flags;struct {DWORD FilterId: 4;DWORD ReservedFlags : 28;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_SYSTEM_CALL_FILTER_POLICY, *PPROCESS_MITIGATION_SYSTEM_CALL_FILTER_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessSystemCallFilterPolicy, &syscall_filter, sizeof(syscall_filter));printf("ProcessSystemCallFilterPolicy:\n");PrintBinaryFlags(syscall_filter.Flags);printf("\n Analysis:\n");printf("   FilterId                                   %u\n", syscall_filter.FilterId);printf("\n");/*描述:进行有效负载限制的进程缓解策略。typedef struct _PROCESS_MITIGATION_PAYLOAD_RESTRICTION_POLICY {union {DWORD Flags;struct {DWORD EnableExportAddressFilter     : 1;DWORD AuditExportAddressFilter      : 1;DWORD EnableExportAddressFilterPlus : 1;DWORD AuditExportAddressFilterPlus  : 1;DWORD EnableImportAddressFilter     : 1;DWORD AuditImportAddressFilter      : 1;DWORD EnableRopStackPivot           : 1;DWORD AuditRopStackPivot            : 1;DWORD EnableRopCallerCheck          : 1;DWORD AuditRopCallerCheck           : 1;DWORD EnableRopSimExec              : 1;DWORD AuditRopSimExec               : 1;DWORD ReservedFlags                 : 20;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_PAYLOAD_RESTRICTION_POLICY, *PPROCESS_MITIGATION_PAYLOAD_RESTRICTION_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessPayloadRestrictionPolicy, &payload_rtict, sizeof(payload_rtict));printf("ProcessPayloadRestrictionPolicy:\n");PrintBinaryFlags(payload_rtict.Flags);printf("\n Analysis:\n");printf("   EnableExportAddressFilter                  %u\n", payload_rtict.EnableExportAddressFilter);printf("   AuditExportAddressFilter                   %u\n", payload_rtict.AuditExportAddressFilter);printf("   EnableExportAddressFilterPlus              %u\n", payload_rtict.EnableExportAddressFilterPlus);printf("   AuditExportAddressFilterPlus               %u\n", payload_rtict.AuditExportAddressFilterPlus);printf("   EnableImportAddressFilter                  %u\n", payload_rtict.EnableImportAddressFilter);printf("   AuditImportAddressFilter                   %u\n", payload_rtict.AuditImportAddressFilter);printf("   EnableRopStackPivot                        %u\n", payload_rtict.EnableRopStackPivot);printf("   AuditRopStackPivot                         %u\n", payload_rtict.AuditRopStackPivot);printf("   EnableRopCallerCheck                       %u\n", payload_rtict.EnableRopCallerCheck);printf("   AuditRopCallerCheck                        %u\n", payload_rtict.AuditRopCallerCheck);printf("   EnableRopSimExec                           %u\n", payload_rtict.EnableRopSimExec);printf("   AuditRopSimExec                            %u\n", payload_rtict.AuditRopSimExec);printf("\n");/*描述:进程的子进程缓解策略。typedef struct _PROCESS_MITIGATION_CHILD_PROCESS_POLICY {union {DWORD Flags;struct {DWORD NoChildProcessCreation : 1;DWORD AuditNoChildProcessCreation : 1;DWORD AllowSecureProcessCreation : 1;DWORD ReservedFlags : 29;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_CHILD_PROCESS_POLICY, *PPROCESS_MITIGATION_CHILD_PROCESS_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessChildProcessPolicy, &child_proc, sizeof(child_proc));printf("ProcessChildProcessPolicy:\n");PrintBinaryFlags(child_proc.Flags);printf("\n Analysis:\n");printf("   NoChildProcessCreation                     %u\n", child_proc.NoChildProcessCreation);printf("   AuditNoChildProcessCreation                %u\n", child_proc.AuditNoChildProcessCreation);printf("   AllowSecureProcessCreation                 %u\n", child_proc.AllowSecureProcessCreation);printf("\n");/*描述:有关指定进程的侧信道隔离的策略。从 Windows 10 版本 1809 及更高版本开始支持。typedef struct _PROCESS_MITIGATION_SIDE_CHANNEL_ISOLATION_POLICY {union {DWORD Flags;struct {//// 在用户模式下防止分支目标污染 交错/同时多线程 (cross-SMT)。//DWORD SmtBranchTargetIsolation : 1;// // 将此进程隔离到一个不同的安全域中,甚至与作为相同安全上下文// 运行的其他进程隔离。这可以防止通过跨进程实施的分支目标注入(// 通常这种分支目标注入仅在不同的安全上下文中被禁止)。//// 页面合并仅限于同一安全域内的进程。因此,此标志也有效地将进程// 限制为只能在进程本身内部组合,但公共页面除外(除非受到//   DisablePageCombine 策略的进一步限制)。// DWORD IsolateSecurityDomain : 1;// // 禁用此进程的所有页面组合,即使是进程本身的内部,但常见页面// (0 或 1)除外。// DWORD DisablePageCombine : 1;//// 禁用内存歧义消除 (Memory Disambiguation)//DWORD SpeculativeStoreBypassDisable : 1;// // 防止将此进程的线程与其安全域外的线程安排在同一核心上。// DWORD RestrictCoreSharing : 1;DWORD ReservedFlags : 27;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_SIDE_CHANNEL_ISOLATION_POLICY, *PPROCESS_MITIGATION_SIDE_CHANNEL_ISOLATION_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessSideChannelIsolationPolicy, &side_cnl_isan, sizeof(side_cnl_isan));printf("ProcessSideChannelIsolationPolicy:\n");PrintBinaryFlags(side_cnl_isan.Flags);printf("\n Analysis:\n");printf("   SmtBranchTargetIsolation                   %u\n", side_cnl_isan.SmtBranchTargetIsolation);printf("   IsolateSecurityDomain                      %u\n", side_cnl_isan.IsolateSecurityDomain);printf("   DisablePageCombine                         %u\n", side_cnl_isan.DisablePageCombine);printf("   SpeculativeStoreBypassDisable              %u\n", side_cnl_isan.SpeculativeStoreBypassDisable);printf("   RestrictCoreSharing                        %u\n", side_cnl_isan.RestrictCoreSharing);printf("\n");/*描述:有关进程的用户模式硬件强制 Stack 保护的策略。自 Windows 10 版本 2004 及更高版本开始支持。typedef struct _PROCESS_MITIGATION_USER_SHADOW_STACK_POLICY {union {DWORD Flags;struct {DWORD EnableUserShadowStack : 1;DWORD AuditUserShadowStack : 1;DWORD SetContextIpValidation : 1;DWORD AuditSetContextIpValidation : 1;DWORD EnableUserShadowStackStrictMode : 1;DWORD BlockNonCetBinaries : 1;DWORD BlockNonCetBinariesNonEhcont : 1;DWORD AuditBlockNonCetBinaries : 1;DWORD CetDynamicApisOutOfProcOnly : 1;DWORD SetContextIpValidationRelaxedMode : 1;DWORD ReservedFlags : 22;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_USER_SHADOW_STACK_POLICY, *PPROCESS_MITIGATION_USER_SHADOW_STACK_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessUserShadowStackPolicy, &usw_stack, sizeof(usw_stack));printf("ProcessUserShadowStackPolicy:\n");PrintBinaryFlags(usw_stack.Flags);printf("\n Analysis:\n");printf("   EnableUserShadowStack                      %u\n", usw_stack.EnableUserShadowStack);printf("   AuditUserShadowStack                       %u\n", usw_stack.AuditUserShadowStack);printf("   SetContextIpValidation                     %u\n", usw_stack.SetContextIpValidation);printf("   AuditSetContextIpValidation                %u\n", usw_stack.AuditSetContextIpValidation);printf("   EnableUserShadowStackStrictMode            %u\n", usw_stack.EnableUserShadowStackStrictMode);printf("   BlockNonCetBinaries                        %u\n", usw_stack.BlockNonCetBinaries);printf("   BlockNonCetBinariesNonEhcont               %u\n", usw_stack.BlockNonCetBinariesNonEhcont);printf("   AuditBlockNonCetBinaries                   %u\n", usw_stack.AuditBlockNonCetBinaries);printf("   CetDynamicApisOutOfProcOnly                %u\n", usw_stack.CetDynamicApisOutOfProcOnly);printf("   SetContextIpValidationRelaxedMode          %u\n", usw_stack.SetContextIpValidationRelaxedMode);printf("\n");/*描述:进程的重定向卫士 (RedirectionGuard) 策略。typedef struct _PROCESS_MITIGATION_REDIRECTION_TRUST_POLICY {union {DWORD Flags;struct {DWORD EnforceRedirectionTrust : 1;DWORD AuditRedirectionTrust : 1;DWORD ReservedFlags : 30;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_REDIRECTION_TRUST_POLICY, *PPROCESS_MITIGATION_REDIRECTION_TRUST_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessRedirectionTrustPolicy, &trust_redc, sizeof(trust_redc));printf("ProcessRedirectionTrustPolicy:\n");PrintBinaryFlags(trust_redc.Flags);printf("\n Analysis:\n");printf("   EnforceRedirectionTrust                    %u\n", trust_redc.EnforceRedirectionTrust);printf("   EnforceRedirectionTrust                    %u\n", trust_redc.AuditRedirectionTrust);printf("\n");/*描述:进程的用户指针身份验证策略。typedef struct _PROCESS_MITIGATION_USER_POINTER_AUTH_POLICY {union {DWORD Flags;struct {DWORD EnablePointerAuthUserIp : 1;DWORD ReservedFlags : 31;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_USER_POINTER_AUTH_POLICY, *PPROCESS_MITIGATION_USER_POINTER_AUTH_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessUserPointerAuthPolicy, &upt_auth, sizeof(upt_auth));printf("ProcessUserPointerAuthPolicy:\n");PrintBinaryFlags(upt_auth.Flags);printf("\n Analysis:\n");printf("   EnablePointerAuthUserIp                    %u\n", upt_auth.EnablePointerAuthUserIp);printf("\n");/*描述:结构化异常处理覆盖保护 (SEHOP) 策略。typedef struct _PROCESS_MITIGATION_SEHOP_POLICY {union {DWORD Flags;struct {DWORD EnableSehop : 1;DWORD ReservedFlags : 31;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_SEHOP_POLICY, *PPROCESS_MITIGATION_SEHOP_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessSEHOPPolicy, &seh_op_policy, sizeof(seh_op_policy));printf("ProcessSEHOPPolicy:\n");PrintBinaryFlags(seh_op_policy.Flags);printf("\n Analysis:\n");printf("   EnableSehop                                %u\n", seh_op_policy.EnableSehop);printf("\n");/*描述:进程的激活上下文(ActivationContext) 保护策略。typedef struct _PROCESS_MITIGATION_ACTIVATION_CONTEXT_TRUST_POLICY {union {DWORD Flags;struct {DWORD AssemblyManifestRedirectionTrust : 1;DWORD ReservedFlags : 31;} DUMMYSTRUCTNAME;} DUMMYUNIONNAME;} PROCESS_MITIGATION_ACTIVATION_CONTEXT_TRUST_POLICY, *PPROCESS_MITIGATION_ACTIVATION_CONTEXT_TRUST_POLICY;*/GetProcessMitigationPolicy(hProc, ProcessActivationContextTrustPolicy, &activ_ctx_truct, sizeof(activ_ctx_truct));printf("ProcessActivationContextTrustPolicy:\n");PrintBinaryFlags(activ_ctx_truct.Flags);printf("\n Analysis:\n");printf("   AssemblyManifestRedirectionTrust           %u\n", activ_ctx_truct.AssemblyManifestRedirectionTrust);//printf("\n");
}BOOL EnableDebugPrivilege(BOOL fEnable) {BOOL fOk = FALSE;HANDLE hToken;if (OpenProcessToken(GetCurrentProcess(), TOKEN_ADJUST_PRIVILEGES, &hToken)) {TOKEN_PRIVILEGES tp = { 0 };tp.PrivilegeCount = 1;LookupPrivilegeValue(NULL, SE_DEBUG_NAME, &tp.Privileges[0].Luid);tp.Privileges[0].Attributes = fEnable ? SE_PRIVILEGE_ENABLED : 0;AdjustTokenPrivileges(hToken, FALSE, &tp, sizeof(tp), NULL, NULL);fOk = (GetLastError() == ERROR_SUCCESS);CloseHandle(hToken);}return(fOk);
}// 获取 PE 文件的描述信息
void GetProcessDescription(const wchar_t* filePath) {DWORD verHandle = 0;DWORD verSize = GetFileVersionInfoSizeW(filePath, &verHandle);if (verSize > 0) {LPVOID verData = malloc(verSize);if (GetFileVersionInfoW(filePath, verHandle, verSize, verData)) {LPVOID lpBuffer = NULL;UINT size = 0;if (VerQueryValueW(verData, L"\\StringFileInfo\\040904b0\\FileDescription", &lpBuffer, &size) && size > 0) {printf("[*] Description: %ws\n", (wchar_t*)lpBuffer);}else {printf("[!] No description available.\n");}}else {printf("[!] Unable to get version info, code %u\n", GetLastError());}free(verData);}else {printf("[!] Unable to get version size, code %u\n", GetLastError());}
}int main(int argc, const char* argv[]) {printf("\n");if (argc != 2) {printf("\nGetProcessMitigationPolicy for Win10/11.\n\n");printf("Usage:\n");printf("%s <pid>\n", argv[0]);return 0;}// 启用 SE_DEBUG 特权if (!EnableDebugPrivilege(TRUE)) {printf("[!] AdjustTokenPrivileges Failed.<%d>\n", GetLastError());}// 从命令行参数获取目标进程 PIDDWORD dwTargetPid = 0;dwTargetPid = atoi(argv[1]);printf("[*] TargetPid:%d\n", dwTargetPid);// 访问目标进程HANDLE hProcess;hProcess = OpenProcess(PROCESS_QUERY_LIMITED_INFORMATION, FALSE, dwTargetPid);if (hProcess == NULL) {printf("[!] Unable to open process %u, code %u\n", dwTargetPid, GetLastError());return 0;}// 获取进程名称wchar_t processPath[2048];ZeroMemory(processPath, sizeof(wchar_t) * 2048);DWORD dwSize = 2046;if (QueryFullProcessImageNameW(hProcess, 0, processPath, &dwSize)) {printf("[*] Process Path: %ws\n", processPath); // 输出进程路径// 从路径中提取进程名称wchar_t* processName = wcsrchr(processPath, '\\');if (processName) {printf("[*] Process Name: %ws\n", processName + 1); // 输出进程名称}else {printf("[*] Process Name: %ws\n", processPath); // 如果路径中没有分隔符,直接输出路径}// 获取并输出进程的描述信息GetProcessDescription(processPath);}else {printf("[!] Unable to get process path, code %u\n", GetLastError());}printf("\n");// 解析进程的缓解策略show_mitigations(hProcess);printf("\n");CloseHandle(hProcess);return 0;
}

测试效果截图:

测试效果截图

四、总结

通过本文的介绍和代码示例,开发人员可以有效地获取和分析 Windows 进程的缓解策略设置。通过使用 ​​​​​​​GetProcessMitigationPolicy 函数,可以有效地分析和显示目标进程的各项安全设置。

这些方法在系统安全和软件开发中非常有用,特别是在需要确保应用程序或系统服务的安全性时。开发者可以将这些方法集成到调试工具或安全扫描工具中,进一步增强系统的安全性和稳定性。


原文出处链接:[https://blog.csdn.net/qq_59075481/article/details/142234952]。

本文发布于:2024.09.13,更新于:2024.09.13.

相关文章:

【Windows】获取进程缓解策略设置情况

目录 一、前言 二、主要概念 三、实现步骤 四、总结 原文出处链接&#xff1a;[https://blog.csdn.net/qq_59075481/article/details/142234952] 一、前言 在现代操作系统中&#xff0c;进程缓解策略&#xff08;Process Mitigation Policy&#xff09;提供了一种防御机制…...

语音识别相关概念

声音如何保存成数字信号&#xff1f; 声音是听觉对声波产生的感知&#xff0c;而声波是一种在时间和振幅上连续的模拟量&#xff0c;本质是介质的振动&#xff0c;&#xff0c;比如空气的振动。那么只需要把这个振动信号记录下来&#xff0c;并用一串数字来表达振动信号振动的…...

Iceberg与SparkSQL查询操作整合

前言 spark操作iceberg之前先要配置spark catalogs,详情参考Iceberg与Spark整合环境配置。 Iceberg使用Apache Spark的DataSourceV2 API来实现数据源和catalog。 使用SQL查询 查询的时候表要按照:catalog.数据库.表名的格式 SELECT * FROM prod.db.table; -- catalog: p…...

Linux 上安装 PostgreSQL

Linux 上安装 PostgreSQL PostgreSQL 是一款功能强大的开源关系数据库管理系统,因其稳定性、可扩展性和先进的功能而广受欢迎。在 Linux 系统上安装 PostgreSQL 是一个相对直接的过程,但具体步骤可能会因您使用的 Linux 发行版而异。本文将介绍在几种流行的 Linux 发行版上安…...

WRF-LES与PALM微尺度气象大涡模拟、PALM静态数据预备、PALM驱动数据预报、PALM模拟

查看原文>>>WRF-LES与PALM微尺度气象大涡模拟及ChatGPT在大气科学领域应用 针对微尺度气象的复杂性&#xff0c;大涡模拟&#xff08;LES&#xff09;提供了一种无可比拟的解决方案。微尺度气象学涉及对小范围内的大气过程进行精确模拟&#xff0c;这些过程往往与天气…...

需求分析概述

为什么要进行需求分析呢&#xff1f; 笑话&#xff1a;富翁娶妻 某富翁想要娶老婆&#xff0c;有三个人选&#xff0c;富翁给了三个女孩各一千元&#xff0c;请 她们把房间装满。第一个女孩买了很多棉花&#xff0c;装满房间的1/2。第 二个女孩买了很多气球&#xff0c;装满…...

Java | Leetcode Java题解之第391题完美矩形

题目&#xff1a; 题解&#xff1a; class Solution {public boolean isRectangleCover(int[][] rectangles) {long area 0;int minX rectangles[0][0], minY rectangles[0][1], maxX rectangles[0][2], maxY rectangles[0][3];Map<Point, Integer> cnt new HashM…...

java项目之基于web的人力资源管理系统的设计与实现(源码+文档)

风定落花生&#xff0c;歌声逐流水&#xff0c;大家好我是风歌&#xff0c;混迹在java圈的辛苦码农。今天要和大家聊的是一款基于springboot的基于web的人力资源管理系统的设计与实现。项目源码以及部署相关请联系风歌&#xff0c;文末附上联系信息 。 项目简介&#xff1a; …...

Linux 防火墙:iptables (二)

文章目录 SNAT 原理与应用SNAT 应用环境SNAT 原理SNAT 转换前提条件SNAT 格式SNAT 转换规则配置 DNAT 原理与应用DNAT 应用环境DNAT 原理DNAT 转换前提条件DNAT 格式DNAT 转换规则配置 iptables 规则的备份和还原导出&#xff08;备份&#xff09;所有表的规则导入&#xff08;…...

小目标检测顶会新思路!最新成果刷爆遥感SOTA,参数小了18倍

遥感领域的小目标检测一直是个具有挑战性和趣味性的研究方向&#xff0c;同时也是顶会顶刊的常客。但不得不说&#xff0c;今年关于遥感小目标检测的研究热情尤其高涨&#xff0c;已经出现了很多非常优秀的成果。 比如SuperYOLO方法&#xff0c;通过融合多模态数据并执行高分辨…...

【Ubuntu】虚拟机安装USB摄像头ROS驱动 usb_cam(最新方法)

写在前面&#xff1a; &#x1f31f; 欢迎光临 清流君 的博客小天地&#xff0c;这里是我分享技术与心得的温馨角落。&#x1f4dd; 个人主页&#xff1a;清流君_CSDN博客&#xff0c;期待与您一同探索 移动机器人 领域的无限可能。 &#x1f50d; 本文系 清流君 原创之作&…...

免费的成绩查询微信小程序,让家长轻松掌握学生表现

传统的教学方式在不断地被革新。在成绩查询这一环节&#xff0c;老师们曾经面临着繁琐的手工操作和信息安全的风险。可现如今有一个让成绩查询变得轻松、高效且安全的新工具——易查分。 过去需要花费大量时间来整理成绩&#xff0c;然后通过短信或者打电话的方式告知给家长。以…...

[含视频和源码]CRUD的最佳实践,联动前后端,包含微信小程序,API,HTML等(三)

关说不练假把式&#xff0c;在上一&#xff0c;二篇中介绍了我心目中的CRUD的样子 基于之前的理念&#xff0c;我开发了一个命名为PasteTemplate的项目&#xff0c;这个项目呢后续会转化成项目模板&#xff0c;转化成项目模板后&#xff0c;后续需要开发新的项目就可以基于这…...

如何把我另一个分支上的commit拿过来

在开源过程中&#xff0c;每一次PR都是要经过严格的review的&#xff0c;这期间可能会进行多次修改&#xff0c;补充提交&#xff0c;而且这一般来说不是一个很迅速的过程&#xff0c;此时我们可能会先往后进行开发。我一般会把项目分模块逐步建立分支&#xff0c;当前一个pr合…...

【rpg像素角色】俯视角-行走动画

制作像素角色的俯视角行走动画并不像看上去那么复杂&#xff0c;尤其是在你已经完成了角色的4个方向站立姿势之后&#xff08;其中左右方向可以通过水平翻转实现&#xff09;。接下来&#xff0c;我会一步步为你讲解如何制作行走动画。 1. 理解行走规律 在制作行走动画之前&am…...

Python时间序列分析新技能,轻松掌握时间索引

大家好&#xff0c;在数据分析领域&#xff0c;时间序列数据分析是一项非常重要的技能。Pandas作为Python中强大的数据处理库&#xff0c;在处理时间序列数据时提供了丰富的功能&#xff0c;其中时间索引的应用是时间序列分析中的关键。本文将介绍如何在Pandas中使用时间索引进…...

sklearn-逻辑回归-特征工程示例

sklearn-逻辑回归-特征工程示例 在实际应用场景中&#xff0c;有时候特征的数量会很多&#xff0c;我们出于业务考虑&#xff0c;也出于计算量的考虑&#xff0c;希望对逻辑回归进行特征选择来降维。比如在判断一个人是否会患乳腺癌的时候&#xff0c;医生如果看58个指标来确诊…...

RTMP播放器延迟最低可以做到多少?

技术背景 RTMP播放器的延迟可以受到多种因素的影响&#xff0c;包括网络状况、推流设置、播放器配置以及CDN分发等。因此&#xff0c;RTMP播放器的延迟并不是一个固定的数值&#xff0c;而是可以在一定范围内变化的。 正常情况下&#xff0c;网上大多看到的&#xff0c;针对R…...

细致刨析JDBC ① 基础篇

目录 一、JDBC概述 1.JDBC的概念 ​编辑2.JDBC的核心组成 ① 接口规范: ② 实现规范: 二、JDBC快速入门 1.JDBC搭建步骤 三、核心API理解 1.注册驱动 2.Connection 3.Statement 4.PreparedStatement 5.ResultSet 四、基于Preparedment实现CRUD 1.查询单行单列 2.查询单行…...

Reactive 编程-Loom 项目(虚拟线程)

Reactive 编程与 Loom 项目&#xff08;虚拟线程&#xff09; Java 项目 Loom 是 Oracle 在 JVM 上的一项重大变革&#xff0c;旨在引入 虚拟线程&#xff08;Virtual Threads&#xff09;&#xff0c;以简化并发编程。传统的 Java 线程是重量级的&#xff0c;由操作系统管理&…...

JVM垃圾回收机制全解析

Java虚拟机&#xff08;JVM&#xff09;中的垃圾收集器&#xff08;Garbage Collector&#xff0c;简称GC&#xff09;是用于自动管理内存的机制。它负责识别和清除不再被程序使用的对象&#xff0c;从而释放内存空间&#xff0c;避免内存泄漏和内存溢出等问题。垃圾收集器在Ja…...

Module Federation 和 Native Federation 的比较

前言 Module Federation 是 Webpack 5 引入的微前端架构方案&#xff0c;允许不同独立构建的应用在运行时动态共享模块。 Native Federation 是 Angular 官方基于 Module Federation 理念实现的专为 Angular 优化的微前端方案。 概念解析 Module Federation (模块联邦) Modul…...

【决胜公务员考试】求职OMG——见面课测验1

2025最新版&#xff01;&#xff01;&#xff01;6.8截至答题&#xff0c;大家注意呀&#xff01; 博主码字不易点个关注吧,祝期末顺利~~ 1.单选题(2分) 下列说法错误的是:&#xff08; B &#xff09; A.选调生属于公务员系统 B.公务员属于事业编 C.选调生有基层锻炼的要求 D…...

鱼香ros docker配置镜像报错:https://registry-1.docker.io/v2/

使用鱼香ros一件安装docker时的https://registry-1.docker.io/v2/问题 一键安装指令 wget http://fishros.com/install -O fishros && . fishros出现问题&#xff1a;docker pull 失败 网络不同&#xff0c;需要使用镜像源 按照如下步骤操作 sudo vi /etc/docker/dae…...

AI编程--插件对比分析:CodeRider、GitHub Copilot及其他

AI编程插件对比分析&#xff1a;CodeRider、GitHub Copilot及其他 随着人工智能技术的快速发展&#xff0c;AI编程插件已成为提升开发者生产力的重要工具。CodeRider和GitHub Copilot作为市场上的领先者&#xff0c;分别以其独特的特性和生态系统吸引了大量开发者。本文将从功…...

UR 协作机器人「三剑客」:精密轻量担当(UR7e)、全能协作主力(UR12e)、重型任务专家(UR15)

UR协作机器人正以其卓越性能在现代制造业自动化中扮演重要角色。UR7e、UR12e和UR15通过创新技术和精准设计满足了不同行业的多样化需求。其中&#xff0c;UR15以其速度、精度及人工智能准备能力成为自动化领域的重要突破。UR7e和UR12e则在负载规格和市场定位上不断优化&#xf…...

图表类系列各种样式PPT模版分享

图标图表系列PPT模版&#xff0c;柱状图PPT模版&#xff0c;线状图PPT模版&#xff0c;折线图PPT模版&#xff0c;饼状图PPT模版&#xff0c;雷达图PPT模版&#xff0c;树状图PPT模版 图表类系列各种样式PPT模版分享&#xff1a;图表系列PPT模板https://pan.quark.cn/s/20d40aa…...

Kubernetes 节点自动伸缩(Cluster Autoscaler)原理与实践

在 Kubernetes 集群中&#xff0c;如何在保障应用高可用的同时有效地管理资源&#xff0c;一直是运维人员和开发者关注的重点。随着微服务架构的普及&#xff0c;集群内各个服务的负载波动日趋明显&#xff0c;传统的手动扩缩容方式已无法满足实时性和弹性需求。 Cluster Auto…...

Vue3中的computer和watch

computed的写法 在页面中 <div>{{ calcNumber }}</div>script中 写法1 常用 import { computed, ref } from vue; let price ref(100);const priceAdd () > { //函数方法 price 1price.value ; }//计算属性 let calcNumber computed(() > {return ${p…...

基于江科大stm32屏幕驱动,实现OLED多级菜单(动画效果),结构体链表实现(独创源码)

引言 在嵌入式系统中&#xff0c;用户界面的设计往往直接影响到用户体验。本文将以STM32微控制器和OLED显示屏为例&#xff0c;介绍如何实现一个多级菜单系统。该系统支持用户通过按键导航菜单&#xff0c;执行相应操作&#xff0c;并提供平滑的滚动动画效果。 本文设计了一个…...