如何在对 C# .NET 3.5 服务器进行 DCOM 调用时可靠地检查客户端身份?

2024-03-29

我有一个旧的 Win32 C++ DCOM 服务器,我正在重写它以使用 C# .NET 3.5。客户端应用程序位于远程 Windows XP 计算机上,也是用 C++ 编写的。这些客户端必须保持不变,因此我必须在新的 .NET 对象上实现接口。

这已经完成,并且在接口的实现方面正在成功工作,并且从旧客户端到新 .NET 对象的所有调用都正确进行。

但是,我在从 DCOM 客户端获取调用用户的身份时遇到问题。为了尝试识别发起 DCOM 调用的用户,我在服务器上有以下代码......

[DllImport("ole32.dll")]
static extern int CoImpersonateClient();

[DllImport("ole32.dll")]
static extern int CoRevertToSelf();

private string CallingUser
{
    get
    {
        string sCallingUser = null;

        if (CoImpersonateClient() == 0)
        {
            WindowsPrincipal wp = System.Threading.Thread.CurrentPrincipal as WindowsPrincipal;

            if (wp != null)
            {
                WindowsIdentity wi = wp.Identity as WindowsIdentity;

                if (wi != null && !string.IsNullOrEmpty(wi.Name))
                    sCallingUser = wi.Name;
            }

            if (CoRevertToSelf() != 0)
                ReportWin32Error("CoRevertToSelf");
        }
        else
            ReportWin32Error("CoImpersonateClient");

        return sCallingUser;
    }
}

private static void ReportWin32Error(string sFailingCall)
{
    Win32Exception ex = new Win32Exception();
    Logger.Write("Call to " + sFailingCall + " FAILED: " + ex.Message);
}

当我得到CallingUser属性,前几次返回的值是正确的,并且识别出正确的用户名,但是,在 3 或 4 个不同的用户成功拨打电话后(并且情况各不相同,所以我无法更具体),更多的用户似乎被识别为之前拨打过电话的用户。

我注意到,前几个用户的 DCOM 调用在自己的线程上处理(即,来自特定客户端的所有调用都由单个唯一线程处理),然后后续用户由与以下相同的线程处理早期的用户,以及调用后CoImpersonateClient(), the CurrentPrincipal与该线程的初始用户匹配。

为了显示:

用户 Tom 进行由线程 1 处理的 DCOM 调用(CurrentPrincipal正确识别汤姆)

用户 Dick 进行由线程 2 处理的 DCOM 调用(CurrentPrincipal正确识别迪克)

用户 Harry 进行由线程 3 处理的 DCOM 调用(CurrentPrincipal正确识别哈利)

用户 Bob 进行 DCOM 调用,该调用由线程 3 处理(CurrentPrincipal错误地将他识别为哈利)

正如您在此图中所看到的,来自客户端 Harry 和 Bob 的调用正在线程 3 上处理,并且服务器将调用客户端识别为 Harry。

我做错了什么吗? 以这种方式使用模拟有任何警告或限制吗? 有没有更好或不同的方式可以可靠地实现我想要做的事情?

我们将不胜感激所有帮助。


好的,所以我采取了不同的方法,最后想出了一个似乎可行的方法(针对 8 个不同的远程用户进行了测试)。

我放弃了模拟路线,转而使用 ClientBlankets...

[DllImport("ole32.dll")]
static extern int CoQueryClientBlanket(out IntPtr pAuthnSvc, out IntPtr pAuthzSvc,
    [MarshalAs(UnmanagedType.LPWStr)] out StringBuilder pServerPrincName, out IntPtr
    pAuthnLevel, out IntPtr pImpLevel, out IntPtr pPrivs, out IntPtr pCapabilities);

public static string CallingUser
{
    get
    {
        IntPtr pAthnSvc = new IntPtr();
        IntPtr pAthzSvc = new IntPtr();
        StringBuilder pServerPrincName = new StringBuilder();
        IntPtr pAuthnLevel = new IntPtr();
        IntPtr pImpLevel = new IntPtr();
        IntPtr pPrivs = new IntPtr();
        IntPtr pCaps = new IntPtr(4);
        string sCallingUser = string.Empty;

        try
        {
            CoQueryClientBlanket(out pAthnSvc,
                out pAthzSvc,
                out pServerPrincName,
                out pAuthnLevel,
                out pImpLevel,
                out pPrivs,
                out pCaps);
        }
        catch (Exception ex)
        {
            Logger.Write(ex.Message);
        }
        finally
        {
            sCallingUser = System.Runtime.InteropServices.Marshal.PtrToStringAuto(pPrivs);
        }

        return sCallingUser;
    }
}

使用 CoCreateClientBlanket 似乎具有预期的结果,并且无论使用哪个线程来处理消息,我每次都能够可靠地获取调用用户的身份。

本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

如何在对 C# .NET 3.5 服务器进行 DCOM 调用时可靠地检查客户端身份? 的相关文章

  • 安全浮点除法

    我的代码中有一些地方我想确保 2 个任意浮点数 32 位单精度 的除法不会溢出 目标 编译器不保证 足够明确 对 INF INF 的良好处理 并且 不完全保证 IEEE 754 的异常值 可能未定义 并且目标可能会改变 另外 我无法对这几个
  • 在 C# 中查找并写入大于 2GB 的文件

    在 C 中 FileStream的方法 Read Write Seek 采用integer在参数中 在一个上一篇文章 https stackoverflow com questions 5654298 filestream read wri
  • 将阻塞调用包装为异步,以实现更好的线程重用和响应式 UI

    我有一个类负责通过调用遗留类来检索产品可用性 该遗留类本身通过进行 BLOCKING 网络调用在内部收集产品数据 请注意 我无法修改旧版 API 的代码 由于所有产品都是相互独立的 因此我希望并行收集信息 而不会创建任何不必要的线程 也不会
  • 如何显示图片目录中的图像?

    我想显示图片库中的图片 我获取图片并绑定数据 StorageFolder picturesFolder KnownFolders PicturesLibrary IReadOnlyList
  • 修改 CookieAuthenticationOptions LoginPath OnRedirectToReturnUrl 事件

    我的 MVC 6 ASP NET 5 项目中有以下设置 配置方法中的Startup cs app UseCookieAuthentication options gt options AuthenticationScheme Cookie
  • 如何将 Boost 库添加到 XCode 6.0 中的 C++ 程序?

    我在用着XCode6 0并且需 要boost程序库 我已经下载了boost 1 57 0 tar gz from http sourceforge net projects boost files boost 1 57 0 http sou
  • 如何设置 QTableView 中特定单元格的线条样式?

    我正在使用 QT GUI 我正在使用 QTableView 实现一个简单的十六进制编辑控件 我最初的想法是使用一个有十七列的表格 表的每一行都有 16 个十六进制字节 然后在第十七列中显示该数据的 ASCII 表示形式 理想情况下 我想编辑
  • gcc 无效版本(最大)错误添加符号:错误值

    我已经在 Linux x86 x64 上成功构建了几个 32 位静态和共享库 现在我尝试将它们链接到一个可执行文件 但出现以下错误 usr bin ld foo so moddi3 invalid version 21 max 0 foo
  • 如何强制操作系统收回内存? (C++)

    在我的 C 代码中 我分配了大量内存来创建树 然后在每个节点中使用 删除 来释放内存 删除所有内容后 我检查操作系统使用的内存量 发现内存未释放 这是预期的 因为该进程不会立即将内存返回给操作系统 因为它仍然可能会再次使用它 问题是 我在删
  • VS Code 不会构建具有多个 .cpp 源文件的 C++ 程序

    请注意 我在 Ubuntu 17 10 上使用 VS Code 并使用 GCC 编译器 我在构建一个使用附加 cpp 文件的简单程序时遇到问题 我可能在这里遗漏了一些明显的东西 因为我对编程相当陌生 但我会解释到目前为止我所做的事情 这阻止
  • .NET 可移植类库 [可序列化] 属性

    我有一个公共类库 其中包含适用于我的服务器和客户端的许多模型 由于客户端在 Xamarin 下运行 因此公共库必须是可移植类库 PCL 在我的服务器中 这些对象通过 AppDomain Remoting Marshaling 传递 因此据我
  • Arduino C++ 析构函数?

    我知道在Arduino中你不能使用delete 那么什么时候调用 C 类中定义的析构函数呢 同样 如果我想创建一个指向数组的指针 我必须使用malloc and free 当对象被销毁时 析构函数被调用 对于自动 堆栈上 变量 它在离开其作
  • ASP.NET MVC:如何在返回状态代码 404 的同时提供内容? [复制]

    这个问题在这里已经有答案了 可能的重复 如何配置 IIS 以使用自定义内容提供 404 响应 https stackoverflow com questions 2551959 how to configure iis to serve m
  • Mono 的 DNS 刷新超时

    虽然目前Mono项目的ServicePointManager类有DnsRefreshTimeout属性启用到其接口中 相关属性未实现 调用示例 ServicePointManager DnsRefreshTimeout 10 60 1000
  • 为什么指向 int 的指针会转换为 void* 而指向函数的指针会转换为 bool?

    C 标准草案 N3337 对指针转换有以下规定 4 10 指针转换 2 指向的指针 类型的右值cv T 在哪里T是一个对象类型 可以转换为 指向的指针 类型的右值cv void 将 指针转换为cv T 到 指向cv void 指向类型对象的
  • 当我已经定义了变量时,为什么会收到一条错误消息,指示变量不存在?

    我收到一条错误消息 表明MyRandomArray在当前上下文中不存在 如何在 C WinForms 应用程序中跨类访问变量 public void Quiz Load object sender EventArgs e string My
  • 如何编辑 .csproj 文件

    当我使用 NET Framework 4 0 MSBUILD EXE 文件编译 csproj 文件时 出现错误 在 website01 csproj 的当前上下文中找不到 lable01 实际上 我需要添加每个 ASP NET 页面及其代码
  • 链接的 ostream 内部行为及其在 MSVC 上的结果(与 Clang 相比)

    MSVC 与 GCC Clang 的流 内部字符串和操作排序问题 大家好 我最近刚刚开始更认真地使用 MSVC 来完成我的一个跨平台项目 同时通过以下方式测试输出chainedSTD 流 IE 一系列的obj foo lt lt endl
  • 为数据提供有效类型是否会产生副作用?

    假设我有一大块动态分配的数据 void allocate size t n void foo malloc n return foo 我希望使用指向的数据foo作为一种特殊类型 type t 但我想稍后再这样做 而不是在分配期间这样做 为了
  • 编译时检查函数是否使用/未使用 C++

    我想在编译时检查是否有某些函数某堂课使用 未使用 相应地使编译过程失败 通过 例如如果函数F1在代码中的某处调用我希望编译成功 并且 if 函数F2称为我希望它失败 关于如何使用预处理器 模板或任何其他 C 元编程技术来做到这一点 有什么想

随机推荐

  • “yes”这个程序有什么重要用途吗?

    当我第一次遇到yes nix 中的程序我想不出它有什么重要用途 这个程序是如何使用的 yes旨在自动化需要在采取行动之前确认的交互式程序 yes rm ri foo 大致相当于 rm rf foo 不同之处在于 f失败时也会继续
  • Rails 4 jQuery 与 javascript 冲突

    我正在尝试在 Rails 4 中制作一个应用程序 我正在挣扎 我正在尝试合并引导主题 但我遇到了供应商 JavaScript 和其余代码的问题 我认为问题可能与我的 application js 中的 jQuery 以及以 符号开头的供应商
  • 按名称实例化 Java lambda 函数

    我想在 Java 8 中创建一个 lambda 函数 获取它的类名 然后从它的类名再次实例化该函数 这就是我尝试的 import java util function Consumer public class SimpleLambda p
  • ajax 与常规表单数据的安全性

    只是想知道安全性的差异
  • Websphere Application Server 6.1(本地化):覆盖控制台消息的区域设置

    我已经安装了西班牙语版本的 RAD 7 5 基于 Eclipse Ganymede 3 4 0 我正在与Websphere 应用程序服务器 6 1 也是西班牙语 我遇到的问题是所有控制台消息都以西班牙语显示 但在我个人看来 翻译相当差 特别
  • 如何处理来自代理的额外 HTTP 标头?

    我们的环境需要使用出站代理来提供异地服务 通常这不是问题 在 Twilio 的这种情况下 返回的额外标头会破坏客户端 传出标头 POST 2010 04 01 Accounts FOO SMS Messages json HTTP 1 1
  • 如何提取双精度数的尾数

    我想将双精度数的尾数存储在变量中 我发布了一个代码来获取 double 的二进制表示形式 点击这里 https stackoverflow com questions 5670221 binary representation of a f
  • 使用 jQuery.getJson 获取 Web API [重复]

    这个问题在这里已经有答案了 我是 ASP NET Web API 的初学者 使用失败jQuery getJson to get ASP NET Web API 这失败了 var url http localhost 56110 api Va
  • 使用 JS / jQuery 启用/禁用 DOM 元素的事件

    我遇到了一个小问题 我花了很多时间来解决这个问题 与它的功能相比 这个问题相当糟糕 我的 DOM 中有标签 并且我已经使用 jQuery 将多个事件绑定到它们 var a a click data function 有时我想禁用其中一些元素
  • WordPress 重定向问题,标头已发送

    我想知道 根据下面的代码 我想把我的 wp redirect 函数放在哪里 因为它当前所在的位置除了 spazzes 和 sais 之外什么也不做 Warning Cannot modify header information heade
  • 处理器的 mpi 数量错误

    抱歉 我肯定犯了一个愚蠢的错误 但没有成功 我正在编译一个简单的 mpi hello world include
  • Google PageSpeed API dotnet .net

    我已经设置了一个基本的 C 应用程序 以便在我使用 Google Apis Pagespeedonline v2 nuget 包指定的网站上运行 PageSpeed 测试 设置非常简单 我有一个变量可以指定 url 然后将其传递到服务中 C
  • 保留 qw 中的空白

    有什么办法可以保留 qw 中的一些空白吗 例如 my a qw 1234 John Smith 123 Main St 将生成一个包含 6 个元素的数组 有什么方法可以 哦 我不知道 逃离空白以保留其中的一些 就像是 my a qw 123
  • 如何使用维基百科的 API 获取维基百科内容?

    我想获取维基百科文章的第一段 执行此操作的 API 查询是什么 请参阅本节中的MediaWiki API 文档 http www mediawiki org wiki API Properties revisions 2F rv 具体涉及获
  • 使用 knit-ess 进行 Polymode 编织 - 不想在 tex 文件名中包含“编织”

    我对 emacs 还很陌生 并且已经习惯在早期版本中使用 Sweave 现在我一直在使用polymode并使用knitr ess进行编织 但是 我想做两个定制 我希望生成的编织名称与文件名相同 即不是 filename writing te
  • 具有未定义行为的分支是否可以被假定为不可访问并优化为死代码?

    考虑以下陈述 char NULL 0 undefined behavior 它显然会调用未定义的行为 给定程序中存在这样的语句是否意味着整个程序未定义 或者只有当控制流命中该语句时行为才变得未定义 如果用户从不输入号码 以下程序是否会被明确
  • 如何从另一种语言单词创建英文字母字符串?

    我需要找到一种方法将某些语言的单词 翻译 重写为英语 例如 俄语 听起来像privet 用英语讲 含义和语法并不重要 但我希望它听起来更相似 一切都应该用Python编写 我在网上努力查找 但没有找到好的方法 例如 类似这样的事情 tran
  • Cocoa:避免控制绑定中的“持续更新”

    我有几个面板 其中包含NSTextField绑定到属性内的控件文件的所有者目的 如果用户编辑字段然后按Tab 移动到下一个字段 它按预期工作 但是如果用户不按Tab只需按 确定 按钮 新值不会在文件的所有者 object 为了解决这个问题
  • 声明后在 C++ 向量中分配元素

    请参考下面的代码和注释 vector
  • 如何在对 C# .NET 3.5 服务器进行 DCOM 调用时可靠地检查客户端身份?

    我有一个旧的 Win32 C DCOM 服务器 我正在重写它以使用 C NET 3 5 客户端应用程序位于远程 Windows XP 计算机上 也是用 C 编写的 这些客户端必须保持不变 因此我必须在新的 NET 对象上实现接口 这已经完成