CallNamedPipe 和 NamedPipeServerStream,访问被拒绝?

Posted

技术标签:

【中文标题】CallNamedPipe 和 NamedPipeServerStream,访问被拒绝?【英文标题】:CallNamedPipe & NamedPipeServerStream, access denied? 【发布时间】:2009-07-24 01:00:26 【问题描述】:

我正在尝试在托管和非托管进程之间进行一些 IPC。我已经选择了命名管道。

我正在使用NamedPipeServerStream 在托管代码中启动一个线程:

using (NamedPipeServerStream stream = new NamedPipeServerStream("MyPipe", PipeDirection.In))

  while (true)
  
    stream.WaitForConnection();
    stream.Read(buffer, 0, size);
    //Handle buffer values
  

在非托管方面我使用CallNamedPipe:

CallNamedPipe(TEXT("\\\\.\\pipe\\MyPipe"), NULL, 0, pData, dataSize, NULL, NMPWAIT_WAIT_FOREVER);

但是,CallNamedPipe 失败,GetLastError 为 5(拒绝访问)。知道为什么吗?

【问题讨论】:

【参考方案1】:

这是获胜的代码行:

NamedPipeServerStream pipeServer = new NamedPipeServerStream("MyPipe", PipeDirection.InOut, 1, PipeTransmissionMode.Message, PipeOptions.None)

它应该是双面的,即使你只是将它用于传出数据

【讨论】:

【参考方案2】:

我的猜测是您在两个不同的帐户下运行进程。由于您使用的是使用默认安全性的 NamedPipeStream 构造函数,因此其他用户无权访问。这可以通过使用带有 PipeSecurity 实例的构造函数来解决。然后明确地授予其他帐户访问权限。

编辑:我刚刚注意到您正在将管道创建为方向为单向管道。但我相信 CallNamedPipe 尝试打开管道以进行读取和写入,并且在连接到单向管道时会失败管道。

编辑 2:该构造函数还创建了一个字节类型的管道,而 CallNamedPipe 只能连接到消息类型的管道。所以你必须使用另一个构造函数。

【讨论】:

出于测试目的,我尝试在同一进程中运行两个代码路径,效果相同。无论如何,我会调查 PipeSecurity。【参考方案3】:

有时,当命名管道打开和关闭很多时,可能会收到拒绝访问,类似于此处描述的错误: Named Pipe Remoting Exceptions。解决方案似乎是在短暂延迟后重试创建命名管道。

【讨论】:

以上是关于CallNamedPipe 和 NamedPipeServerStream,访问被拒绝?的主要内容,如果未能解决你的问题,请参考以下文章

小数据中的 NamedPipe 与 TCP/IP

ReadFile 使用 NamedPipe 块虽然使用重叠

WCF NamedPipe CommunicationException - “管道已结束。 (109,0x6d)。“

管道和命名管道

Windows API——进程和线程函数

API 进程线程函数