【问题标题】:WinAPI NetUserGetInfo() fails with NERR_UserNotFound error code on Active Directory domainWinAPI NetUserGetInfo() 在 Active Directory 域上失败并出现 NERR_UserNotFound 错误代码
【发布时间】:2015-06-11 04:41:47
【问题描述】:

我正在从本地服务应用程序运行以下代码。目的是在调用 LoadUserProfile() 以加载该用户的配置文件之前获取用户配置文件的路径,然后再调用 CreateProcessAsUser() 以代表该用户运行用户模式进程。

请注意,此问题与 LoadUserProfile() 或 CreateProcessAsUser() 无关。

发生的事情是这样的。当下面的代码在作为 Active Directory 域的一部分的 Windows XP w/SP3 上运行时,单个用户通过本地控制台登录(该用户的会话 ID 在下面使用),NetUserGetInfo() API 失败。另请注意,它在任何其他情况下都可以正常工作:

//'dwSessID' = session ID of the user to retrieve a user profile path for
LPTSTR pUserName = NULL;
DWORD dwcbSzUserName = 0;
if(!WTSQuerySessionInformation(WTS_CURRENT_SERVER_HANDLE, dwSessID, WTSUserName, &pUserName, &dwcbSzUserName))
{
    //Error
    return false;
}

USER_INFO_4* pUI4 = NULL;
DWORD dwNetStatus;
if((dwNetStatus = NetUserGetInfo(NULL, pUserName, 4, (BYTE**)&pUI4)) == NERR_Success)
{
    PROFILEINFO pfi = {0};
    pfi.dwSize = sizeof(pfi);
    pfi.lpUserName = pUserName;
    pfi.dwFlags = PI_NOUI;
    pfi.lpProfilePath = pUI4->usri4_profile;

    LoadUserProfile(hToken, &pfi);

    //And so on
}
else
{
    //On that specific machine I get here with 'dwNetStatus' = 2221, 
    //or NERR_UserNotFound, that according to MSDN is 
    //"The user name could not be found."
    //Also note that GetLastError is not used for this API.
}

有人能建议为什么 NetUserGetInfo() 在特定机器上会失败,以及如何修复此代码吗?

PS。我知道 NetUserGetInfo 的 MSDN 声明 Active Directory 域上的 ACL 可能存在问题,但它没有指定如何设置...

【问题讨论】:

  • 只是一个想法 - 您是否在多台 XP/SP3 机器上使用不同的用户帐户尝试过它?可能想要消除俗气的构建或配置文件。
  • 不,这不是特定的机器。我没有为 NetUserGetInfo() 工作设置 ACL 中的某些内容。我也欢迎任何绕过该 API 的想法?
  • 可以使用 DirectoryServices 查询 AD 吗? forums.asp.net/t/1415018.aspx/1
  • 这是针对原生 C/C++ 项目的。
  • 抱歉 - 直接 LDAP 查询怎么样?目录服务只是 LDAP 的包装器。 ADSI 是接口。

标签: c++ active-directory network-programming winapi


【解决方案1】:

如果我阅读NetUserGetInfo 的文档,了解您编码的数据的信息级别 4 。它写成 4 级返回有关用户帐户的详细信息和附加属性。 此级别仅在服务器上有效。据我了解,这不是你的情况。你验证WTSQuerySessionInformation返回的pUserName的值吗。

【讨论】:

  • 是的,WTSQuerySessionInformation 返回的 pUserName 是一个用户名,类似于“user123”。不是空字符串。
【解决方案2】:

正如 JPBlanc 所说,级别 4 的 NetUserGetInfo 仅在服务器上有效。

另一个问题是您检索到登录用户的名称,而不是用户所属的域。

【讨论】:

  • 伙计们,你们一直在指出我做得不对的地方……我知道……样本在 100% 的情况下都无法正常工作。你能给我“正确”的方式来检索用户个人资料的路径吗?
  • 我给了你一个提示:它可能与用户登录的域有关。你检查是否是这个问题?您是否检查了问题是否只是在这台机器上您使用来自不同域的用户登录?关于第 4 级问题:尝试在该 DC 上查询 DC 和 NetUserGetInfo。
【解决方案3】:

注意到您正在使用 LPTSTR 类型的 pUserName 调用 NetUserGetInfo。 有时它不起作用(如果您将编译您的项目以默认使用 ANSII 字符串)。

考虑将字符串类型更改为 LPWSTR。

【讨论】:

    猜你喜欢
    • 2018-02-11
    • 1970-01-01
    • 1970-01-01
    • 2016-04-01
    • 2018-09-04
    • 2012-01-22
    • 1970-01-01
    • 1970-01-01
    • 2019-04-22
    相关资源
    最近更新 更多