ARM64驱动编译遇C2220、C4013错误,已含intrin.h求解决
解决ARM64驱动编译时的C2220、C4013错误
我来帮你一步步拆解和解决这些问题,核心原因是你把x86/x64架构的寄存器操作代码直接搬到了ARM64平台,而两者的系统寄存器体系完全不同,再加上项目的警告设置放大了问题。
1. 先处理C2220:警告被视为错误
这个错误是因为你的项目开启了“将警告视为错误”的选项,导致C4013这类未定义函数的警告直接变成错误,阻止了目标文件生成。解决方法有两种:
- 临时快速解决:在代码开头添加编译指令禁用特定警告:
#pragma warning(disable:4013) // 临时禁用未定义函数的警告 #pragma warning(disable:2220) // 或者直接禁用“警告视为错误”的全局设置 - 规范解决:打开项目属性 → 配置属性 → C/C++ → 常规,找到“将警告视为错误”选项,设置为“否”。不过驱动开发建议尽量修复警告而非禁用,所以优先处理下面的核心问题。
2. 核心问题:ARM64不支持__readcr0/__writecr0
__readcr0和__writecr0是微软为x86/x64架构提供的内建函数,专门用于读写x86的CR0控制寄存器,但ARM64架构根本没有CR0寄存器,它的系统控制寄存器体系完全不同(比如对应的是SCTLR_EL1等EL级寄存器)。
替换方案(ARM64下的寄存器操作)
如果你是想实现类似x86下修改内存保护(比如关闭写保护)的逻辑,ARM64下需要使用对应架构的内建函数或汇编来读写系统寄存器:
#include <intrin.h> // ARM64下读取SCTLR_EL1寄存器(功能类似x86的CR0) UINT64 sctlr_el1 = __arm_mrs(SCTLR_EL1); // 修改目标位(示例:关闭WXN写保护位,具体位需参考ARM架构手册) sctlr_el1 &= ~(1ULL << 19); // 写回修改后的寄存器 __arm_msr(SCTLR_EL1, sctlr_el1);
⚠️ 注意:这类系统寄存器操作需要在最高特权级执行,Windows驱动中需确保上下文正确,随意修改可能导致系统崩溃,务必参考ARM官方架构手册和Windows DDI文档。
3. 修复代码中的语法错误
你提供的代码片段存在明显的语法混乱:
UINT64 cr0 = __readcr0(); __writecr0( cr0 & *(PUSHORT)place = *(PULONG)(place + 2) = *(PVOID**)(place + 6) = __writecr0( cr0 );
这行把位操作、多个赋值和函数调用混在一起了,需要拆分成清晰的语句(以x86为例,ARM64需替换寄存器操作):
// 修正后的示例代码(x86版本) UINT64 cr0 = __readcr0(); // 假设要关闭CR0的写保护位 cr0 &= ~0x10000; // 拆分赋值操作 *(PUSHORT)place = your_short_value; *(PULONG)(place + 2) = your_long_value; *(PVOID**)(place + 6) = your_ptr_value; // 写回CR0 __writecr0(cr0);
内容的提问来源于stack exchange,提问作者Shen dave
相关产品推荐
相关产品推荐

