使用 Net.Tcp 端口共享服务时拒绝访问 [英] Access denied when using Net.Tcp Port Sharing Service

查看:28
本文介绍了使用 Net.Tcp 端口共享服务时拒绝访问的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这个问题与在特定凭据下启动进程有关一个 Windows 服务,但这是一个不同的问题.

This question is related to Starting processes under specific credentials from a Windows service, but it's a different problem.

我已使用特定凭据从系统会话 (0) 中的 Windows 服务启动了一个进程,但它无法侦听端口共享 URL.它在 Windows Server 2008 机器上使用Worker"域帐户.

I've started a process from a Windows service in the System session (0) under specific credentials, but it is unable to listen to a port sharing URL. It's using a "Worker" domain account on a Windows Server 2008 machine.

我的 SMSvcHost.exe.config 文件:http://pastie.org/私人/jxed8bdft0eir5uc371pq

我也重新启动了服务和机器,但它仍然给我这个异常:

I've restarted the services and the machine as well, but it's still giving me this exception:

System.ServiceModel.CommunicationException: The service endpoint failed to listen on the URI 'net.tcp://localhost:5400/Agent/384' because access was denied.  Verify that the current user is granted access in the appropriate allowAccounts section of SMSvcHost.exe.config. ---> System.ComponentModel.Win32Exception: Access is denied
   at System.ServiceModel.Activation.SharedMemory.Read(String name, String& content)
   at System.ServiceModel.Channels.SharedConnectionListener.SharedListenerProxy.ReadEndpoint(String sharedMemoryName, String& listenerEndpoint)

我的 ProcessHelper 代码,用于启动进程:http://pastie.org/私人/iytqehsdfujrgil1decda.我正在调用 StartAsUserFromService 方法.

My ProcessHelper code that starts the process: http://pastie.org/private/iytqehsdfujrgil1decda. I'm calling the StartAsUserFromService method.

我想配置中的 SID 和进程运行的帐户之间的链接以某种方式没有建立.但为什么?

I suppose the link between the SID in the config and the account the process is running under is somehow not being made. But why?

我已经仔细检查了我正在编辑的配置是否被服务使用.我已经尝试明确添加系统帐户和所有人,但它仍然给我一个访问被拒绝的错误.就好像它根本不看那个配置.

I've double-checked that the config I'm editing is used by the service. I've tried adding the System account and Everyone explicitly, but it's still giving me an access denied error. It's like it's not looking at that config at all.

如何找到缺少的权限?

我在机器上重新安装了 .NET 4.5.1 和所有 Windows 更新,但仍然没有运气.

I reinstalled .NET 4.5.1 on the machine and all the Windows updates, still no luck.

这是复制用户令牌以允许其使用端口共享的正确方法吗?特别是 SecurityDescriptor 位?

Is this the correct way of duplicating a user token to allow it to use port sharing? Specifically the SecurityDescriptor bit?

private static ImpersonationResult ImpersonateUser(string domain, string username, string password)
{
    IntPtr token = IntPtr.Zero;
    IntPtr primaryToken = IntPtr.Zero;

    try
    {
        // Get token
        bool bImpersonated = LogonUser(
            username,
            domain,
            password,
            (int)LogonType.NetworkClearText,
            (int)LogonProvider.Default,
            ref token);

        if (!bImpersonated)
        {
            throw new Exception(string.Format("Failed to impersonate identity. Error code: {0}", Marshal.GetLastWin32Error()));
        }

        SecurityDescriptor sd = new SecurityDescriptor();
        IntPtr ptr = Marshal.AllocCoTaskMem(Marshal.SizeOf(sd));
        Marshal.StructureToPtr(sd, ptr, false);
        InitializeSecurityDescriptor(ptr, 1);
        sd = (SecurityDescriptor)Marshal.PtrToStructure(ptr, typeof(SecurityDescriptor));

        // Set up security
        bool bDecriptorSet = SetSecurityDescriptorDacl(
            ref sd,
            true,
            IntPtr.Zero,
            false);

        if (!bDecriptorSet)
        {
            throw new Exception(string.Format("Failed to set security descriptor. Error code: {0}", Marshal.GetLastWin32Error()));
        }

        SecurityAttributes processAttributes = new SecurityAttributes();
        processAttributes.lpSecurityDescriptor = ptr;
        processAttributes.nLength = (uint)Marshal.SizeOf(sd);
        processAttributes.bInheritHandle = true;

        // Duplicate token
        bool bTokenDuplicated = DuplicateTokenEx(
            token,
            0,
            ref processAttributes,
            (int)SecurityImpersonationLevel.SecurityImpersonation,
            (int)TokenType.TokenPrimary,
            ref primaryToken);

        if (!bTokenDuplicated)
        {
            throw new Exception(string.Format("Failed to duplicate identity token. Error code: {0}", Marshal.GetLastWin32Error()));
        }

        SecurityAttributes threadAttributes = new SecurityAttributes();
        threadAttributes.lpSecurityDescriptor = IntPtr.Zero;
        threadAttributes.nLength = 0;
        threadAttributes.bInheritHandle = false;

        // Got the token
        return new ImpersonationResult()
            {
                Token = primaryToken,
                ProcessAttributes = processAttributes,
                ThreadAttributes = threadAttributes
            };
    }
    finally
    {
        FreeToken(token);
    }
}

private static void FreeToken(IntPtr token)
{
    if (token != IntPtr.Zero)
    {
        CloseHandle(token);
    }
}

这是我启用端口共享的过程的 app.config 部分:http://pastie.org/private/8ekqeps4d7rmo7hnktsw

Here's the app.config bit of my process that enables port sharing: http://pastie.org/private/8ekqeps4d7rmo7hnktsw

这是启动进程的服务的 app.config 位:http://pastie.org/private/nqqcwz8bvjb5fzp48yavbw.使用端口共享没有问题,因为它在系统帐户下运行.

Here's an app.config bit of the service that starts the process: http://pastie.org/private/nqqcwz8bvjb5fzp48yavbw. It has no problems using Port Sharing because it's running under the System account.

端口共享服务本身是启用的,我已经提到我已经重新启动了几次机器.

The Port Sharing service itself is enabled, and I already mentioned that I've restarted the machine several times.

应用服务器"角色没有安装,但是当我去添加它时,TCP端口共享角色已经打勾并变灰,所以一定是其他东西安装了它.它是否随 .NET 4.5.1 一起提供?

The "Application Server" role is not installed, but when I go to add it, the TCP Port Sharing Role is already ticked and greyed out, so something else must have installed it. Does it come with .NET 4.5.1?

推荐答案

事实证明是登录类型导致权限无法与端口共享服务一起正常工作.我将其更改为 LogonType.Batch 并开始工作.

It turns out that the logon type was causing the permissions to not work correctly with the Port Sharing Service. I changed it to LogonType.Batch and it started working.

完整代码:

ProcessHelper:http://pastie.org/private/dlkytj8rbigs8ixwtg

TokenImpersonationContext:http://pastie.org/private/nu3pvpghoea6pwwlvjuq

这篇关于使用 Net.Tcp 端口共享服务时拒绝访问的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆