使用LOGON32_LOGON_NEW_CREDENTIALS的LogonUser适用于远程不受信任的域计算机

时间:2010-05-26 20:06:03

标签: winapi impersonation

因此,两台机器之间没有信任 - 它们位于不同的域中。

我已使用登录类型 LOGON32_LOGON_NEW_CREDENTIALS 使用LogonUser API成功连接到远程计算机。我能够使用UNC共享检索目录的内容,并创建一个文件流来“下载”该文件。到目前为止一切都很好。

唯一的问题是看起来,LogonUser失败,除非已经打开了会话。让我澄清一下。

我发现ASP.NET MVC页面今天早上没有工作,特别是使用LogonUser从这台远程机器上检索文件列表的页面。我查看日志,我在堆栈跟踪中看到, System.IO .__ Error.WinIOError Directory.GetFiles 上面调用。然后我转发到Web服务器并尝试使用网站使用的相同登录名/密码打开资源管理器中的远程文件夹。它经历了,我可以看到文件。我打开了命令提示符,键入 net use ,我看到有一个打开的远程机器连接。然后我回到页面,突然页面再次运行。

所以,在这一点上,我不确定LogonUser是否按预期工作。如果呼叫要求首先通过其他方式打开网络连接,那么这肯定不能令人满意。

有谁知道可能发生的事情或建议解决方法?

2 个答案:

答案 0 :(得分:1)

我不确定我理解您使用LogonUser的原因。如果您想使用其他用户凭据在本地计算机上执行某项工作,此功能可以帮助您,但它有助于不与另一台计算机建立远程连接。

如果要从远程计算机获取某些信息,而不依赖于计算机之间的现有信任,则应使用WNet或Net(网络管理)功能建立与远程计算机的新连接。因此,您应该使用WNetAddConnection2(请参阅http://msdn.microsoft.com/en-us/library/aa385413%28VS.85%29.aspx)或NetUseAddhttp://msdn.microsoft.com/en-us/library/aa370645%28VS.85%29.aspx)函数。此功能将在目标计算机上进行远程登录并建立新会话(确切地说net use \\computer\share /u:domain\user password做什么)。您不能将新连接映射到本地驱动器。为此,您应该在结构lpLocalName中使用NULL填充NETRESOURCE。作为lpUsernamelpPassword,您应该提供了解目标计算机的任何值。您还可以使用ipc$作为目标共享名称,然后只需与计算机建立会话即可。之后,您可以使用任何其他功能来访问远程共享,目录或文件。要关闭会话,您应使用WNetCancelConnection2NetUseDel

答案 1 :(得分:0)

这是LogonUser到远程计算机的方式。确保您使用的是LOGON32_LOGON_NEW_CREDENTIALS,LOGON32_PROVIDER_WINNT50。然后冒充令牌。如果没有WNetAddConnection2,您应该可以通过这种方式执行大量远程操作。 WNetAddConnection2不是很好,因为很多东西都可以破坏连接。 LogonUser还会在需要时通过多个api调用进行适当的连接。

PXERR impersonate_user(LPCWSTR lpszUserName, LPCWSTR lpszDomain, LPCWSTR lpszPassword)
{
    HANDLE token;

    if(!LogonUserW(lpszUserName, lpszDomain, lpszPassword, LOGON32_LOGON_NEW_CREDENTIALS, LOGON32_PROVIDER_WINNT50, &token))
    {
        return PXERR_IMPERSONATION_FAILURE;
    }

    if(!ImpersonateLoggedOnUser(token))
    {
        CloseHandle(token);
        RevertToSelf();
        return PXERR_IMPERSONATION_FAILURE;
    }

    CloseHandle(token);

    return PXERR_SUCCESS;
}