You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过编程为DCOM Config添加用户并配置访问权限(基于WIX)

自定义DCOM访问权限:WIX集成 + 编程实现方案

我之前处理过类似的DCOM权限配置需求,WIX本身没有内置元素直接支持修改DCOM Config的权限,所以得靠自定义操作来实现;而编程添加用户到访问权限列表,用WMI或者Windows API都能搞定,下面分两部分给你详解:

一、在WIX安装程序中配置DCOM权限

要在WIX安装流程中自定义DCOM访问权限,核心是编写托管自定义操作(C#)——WMI操作在C#里更易处理,也能很好地集成到WIX的安装逻辑中:

1. 编写C#自定义操作代码

利用System.Management和System.Security.AccessControl命名空间,操作WMI的DCOM配置类,通过修改安全描述符添加用户权限。示例代码如下:

using System;
using System.Management;
using System.Security.AccessControl;
using System.Security.Principal;
using Microsoft.Deployment.WindowsInstaller;

public class DcomPermissionActions
{
    [CustomAction]
    public static ActionResult AddUserToDcomAccess(Session session)
    {
        try
        {
            // 替换为你的DCOM组件CLSID
            string targetClsid = "{YOUR-COMPONENT-CLSID-HERE}";
            // 替换为要添加的用户(格式:DOMAIN\UserName 或 .\LocalUser)
            string userToAdd = "DOMAIN\\JohnDoe";

            // 连接到本地WMI服务的DCOM应用设置类
            var dcomClass = new ManagementClass("Win32_DCOMApplicationSetting");
            var dcomInstances = dcomClass.GetInstances();

            foreach (ManagementObject dcomObj in dcomInstances)
            {
                if (dcomObj["CLSID"].ToString().Equals(targetClsid, StringComparison.OrdinalIgnoreCase))
                {
                    // 获取当前的访问安全描述符
                    var getAccessParams = dcomObj.InvokeMethod("GetAccessSecurity", null, null);
                    byte[] originalSd = getAccessParams["Descriptor"] as byte[];

                    // 解析安全描述符并添加用户权限
                    var sd = new RawSecurityDescriptor(originalSd, 0);
                    var ntAccount = new NTAccount(userToAdd);
                    var sid = ntAccount.Translate(typeof(SecurityIdentifier)) as SecurityIdentifier;

                    // 添加允许本地和远程访问的ACE(权限掩码:0x1=本地访问,0x2=远程访问)
                    var ace = new CommonAce(
                        AceFlags.None,
                        AccessControlType.Allow,
                        0x1 | 0x2,
                        sid,
                        false,
                        null);

                    sd.DiscretionaryAcl.InsertAce(0, ace);

                    // 转换回二进制安全描述符并设置回去
                    byte[] newSd = new byte[sd.BinaryLength];
                    sd.GetBinaryForm(newSd, 0);

                    var setAccessParams = dcomObj.GetMethodParameters("SetAccessSecurity");
                    setAccessParams["Descriptor"] = newSd;
                    dcomObj.InvokeMethod("SetAccessSecurity", setAccessParams, null);

                    session.Log($"Successfully added user {userToAdd} to DCOM access permissions for CLSID {targetClsid}");
                    break;
                }
            }

            return ActionResult.Success;
        }
        catch (Exception ex)
        {
            session.Log($"Error modifying DCOM permissions: {ex.Message}\n{ex.StackTrace}");
            return ActionResult.Failure;
        }
    }
}

2. 集成到WIX项目

  • 把编译好的C# DLL添加到WIX项目,定义Binary元素:
<Binary Id="DcomPermissionCA" SourceFile="..\DcomPermissionCustomAction\bin\Release\DcomPermissionCustomAction.dll" />
  • 注册自定义操作,修改系统权限需要管理员权限,所以设置Execute="deferred"和Impersonate="no":
<CustomAction Id="AddUserToDcomAccess" BinaryKey="DcomPermissionCA" DllEntry="AddUserToDcomAccess" Execute="deferred" Impersonate="no" />
  • 在安装序列中添加操作,确保在COM组件注册完成后执行(放在InstallFinalize之前):
<InstallExecuteSequence>
    <Custom Action="AddUserToDcomAccess" After="InstallFinalize">NOT Installed</Custom>
</InstallExecuteSequence>

二、独立编程添加用户到DCOM Config访问权限

如果是单独的程序(非WIX安装场景),同样可以复用上面的核心逻辑,或者用VBScript脚本做自动化:

C#独立程序版本

直接提取上面的核心逻辑,去掉WIX的Session相关代码,换成控制台日志即可:

// 省略命名空间和引用,核心逻辑和AddUserToDcomAccess方法一致
// 把session.Log替换为Console.WriteLine即可

VBScript版本(适合脚本自动化)

Const LOCAL_ACCESS = 1
Const REMOTE_ACCESS = 2

strTargetCLSID = "{YOUR-COMPONENT-CLSID}"
strUser = "DOMAIN\JaneDoe"

Set objWMIService = GetObject("winmgmts:\\.\root\cimv2")
Set colDCOMApps = objWMIService.ExecQuery( _
    "SELECT * FROM Win32_DCOMApplicationSetting WHERE CLSID = '" & strTargetCLSID & "'")

For Each objDCOMApp In colDCOMApps
    ' 获取当前安全描述符
    Set objOutParams = objDCOMApp.GetAccessSecurity()
    arrOriginalSD = objOutParams.Descriptor
    
    ' 注:VBScript处理安全描述符较繁琐,推荐调用C#控制台程序或使用ADSI方法修改
    ' 此处假设已得到修改后的安全描述符数组arrModifiedSD
    Set objInParams = objDCOMApp.Methods_("SetAccessSecurity").InParameters.SpawnInstance_()
    objInParams.Descriptor = arrModifiedSD
    objDCOMApp.ExecMethod_ "SetAccessSecurity", objInParams
    
    WScript.Echo "Successfully added user " & strUser & " to DCOM access permissions"
Next

重要注意事项

  • 管理员权限:不管是WIX安装还是独立程序,都需要以管理员身份运行,否则没有修改DCOM权限的权限。
  • CLSID准确性:必须使用目标DCOM组件的正确CLSID,可在注册表HKCR\CLSID路径下找到对应组件的标识。
  • 权限掩码:根据需求设置正确的权限掩码,除了本地/远程访问,还可添加LAUNCH(0x4)或ACTIVATE(0x8)权限。

内容的提问来源于stack exchange,提问作者BassetMan

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.20 09:00:54