添加入站规则时必须设置Direction、Enabled和Action三属性,否则抛0x80070057;删除前需用Rules.Item()验证存在性,避免0x80070490;修改规则须获取原引用再改属性,不可同名覆盖。

用 INetFwRule 添加入站规则时,必须设置 Direction 和 Enabled
直接 new 一个 INetFwRule 对象后不设关键属性就调用 FirewallPolicy.Rules.Add(),会抛出 0x80070057(参数错误)。Windows 防火墙 COM 接口非常严格,Direction(方向)、Enabled(是否启用)、Action(允许/阻止)这三项缺一不可。
实操建议:
-
Direction必须是NET_FW_RULE_DIRECTION_.IN或NET_FW_RULE_DIRECTION_.OUT,不能为0或留空 -
Action设为NET_FW_ACTION_.ALLOW或NET_FW_ACTION_.BLOCK,不能用布尔值代替 -
Enabled必须显式设为true或false,哪怕你想加完立刻禁用 - 规则名(
Name)建议带唯一前缀(如"MyApp-HTTP-In"),避免和系统规则冲突
删除规则前先检查是否存在,否则 Rules.Remove() 会抛 0x80070490
防火墙规则名不区分大小写,但完全匹配——"myapp-port80" 和 "MyApp-Port80" 被视为不同规则。直接调用 Rules.Remove("MyApp-Port80") 而不验证存在性,一旦名字拼错或已被删,就会触发 E_ELEMENT_NOT_FOUND 错误(0x80070490)。
安全做法:
- 用
Rules.Item(name)尝试获取规则对象,捕获COMException判断是否存在 - 或遍历
Rules集合,用rule.Name.Equals(name, StringComparison.OrdinalIgnoreCase)精确查找 - 删除后不要假设规则已消失:可再次遍历确认,尤其在自动化脚本中
修改已有规则要用 Rules.Item() 获取再改属性,不能直接 new 同名规则覆盖
Windows 防火墙不支持“覆盖添加”:即使你用相同 Name 新建一个 INetFwRule 并调用 Add(),它不会替换旧规则,而是报 0x800700b7(文件已存在)。真正生效的修改方式,是先通过 Rules.Item(name) 拿到原规则引用,再改其属性(如 LocalPorts、RemoteAddresses),最后无需显式保存——COM 接口会自动持久化。
Windows 命令行编码与兼容规范。涵盖 GBK/UTF-8 编码、PowerShell/pwsh 互操作、Python/Node.js、Git 配置及代码生成规则。适用于 Windows 10/11 + MSYS2/Git Bash 环境下的所有命令行操作。
注意点:
-
LocalPorts改成"8080,8081"是合法的,但写成"8080-8081"会静默失败(只认逗号分隔) - 修改
RemoteAddresses时,"192.168.1.0/24"可用,但"192.168.1.*"不被识别 - 如果规则被组策略锁定(常见于域环境),即使代码执行成功,实际策略仍可能被后台覆盖
需要管理员权限 + COM 初始化,否则 INetFwMgr 创建就失败
调用 Activator.CreateInstance(Type.GetTypeFromCLSID(...)) 创建 INetFwMgr 时,若进程没以管理员身份运行,会返回 null 或抛 Access is denied;更隐蔽的是,若没调用 CoInitializeEx(尤其在非 UI 线程),某些 Windows 版本下 Rules.Add() 表面成功,实际规则未写入磁盘。
必须步骤:
- 程序 manifest 中声明
requireAdministrator,否则 UAC 会拦截 - 在调用任何防火墙 COM 接口前,主线程执行
CoInitializeEx(IntPtr.Zero, COINIT.COINIT_APARTMENTTHREADED) - 不要在 .NET Core/.NET 5+ 的默认线程池线程上操作——它们不保证 COM 上下文,优先切回 STA 主线程
最易被忽略的一点:规则生效有延迟,特别是远程地址范围变更后,有时需等几秒或手动触发 netsh advfirewall firewall reload 才能立即反映。别依赖“Add 后立刻连通”做自动化断言。









