5

我在检索用户是 LDAP 用户的 Red Hat Enterprise 6 的当前用户信息时遇到问题?

我有一些代码(实际上是安装工具的一部分)需要检索用户名、主目录和其他详细信息。它使用 getpwuid() 调用根据用户 ID 执行此操作。一个简化的细分:

uid_t uid = getuid();
printf("UID = %d\n", uid);

errno = 0;
struct passwd* udetails = getpwuid(uid);

if (udetails != NULL)
{
    printf("User name = %s\n", udetails->pw_name);
}
else
{
    printf("getpwuid returns NULL, errno=%d\n", errno);
}

如果用户是本地用户(在该系统的 /etc/passwd 中),这不会出现问题。

当用户是LDAP认证用户时,调用getuid返回用户ID或当前用户,但调用getpwuid返回0,errno中没有设置错误码。根据文档,这意味着用户不存在。

这应该工作吗?根据 getpwuid 联机帮助页:

getpwnam() 函数返回一个指向结构的指针,该结构包含与用户名名称匹配的密码数据库(例如,本地密码文件/etc/passwd、NIS 和LDAP)中记录的断开字段。

getpwuid() 函数返回一个指向结构的指针,该结构包含密码数据库中与用户 ID uid 匹配的记录的断开字段。

如果当前用户已通过 LDAP 身份验证,是否需要替代调用来获取详细信息?是否有必要在应用程序中打开 LDAP 数据库,还是应该由系统调用处理?

附加:我现在也在一个针对同一个 LDAP 目录进行身份验证的 RHEL 5 机器上进行了尝试。这可能只是 RHEL 6 机器上的配置问题吗?还是更广泛的 RHEL 6 问题?

附加:Basile Starynkevitch 要求的 /etc/nsswitch.conf(已删除注释行):

passwd:     files sss
shadow:     files sss
group:      files sss

hosts:      files dns

bootparams: nisplus [NOTFOUND=return] files

ethers:     files
netmasks:   files
networks:   files
protocols:  files
rpc:        files
services:   files sss

netgroup:   files sss

publickey:  nisplus

automount:  files ldap
aliases:    files nisplus

我猜其中一些应该在某个时候提到ldap?事实上,这表明它根本没有使用 LDAP....

4

3 回答 3

3

问题似乎缺少nss_sss 32 位库(在我的情况下)。我认为对于 redhat 它是 rpm 包:sssd-client.i686.rpm

我使用了以下生成文件:

all: getpwuid_bug-32bit getpwuid_bug-64bit

getpwuid_bug-32bit: getpwuid_bug.c makefile
        $(CC) -Wall -m32 -o $@ $<

getpwuid_bug-64bit: getpwuid_bug.c makefile
        $(CC) -Wall -m64 -o $@ $<

和以下 getpwuid_bug.c

#include <stdlib.h>
#include <stdio.h>
#include <errno.h>
#include <sys/types.h>
#include <unistd.h>
#include <pwd.h>

int main(argc, argv)
     int argc; char **argv;
{
  uid_t uid;
  struct passwd *udetails;

  uid = getuid();
  printf("UID = %d\n", uid);

  errno = 0;
  udetails = getpwuid(uid);

  if (udetails != NULL) {
    printf("User name = %s\n", udetails->pw_name);
  } else {
    printf("getpwuid returns NULL, errno=%d\n", errno);
    return 1;
  }
  return 0;
}

现在输入 make...

然后同时运行

$ ./getpwuid_bug-32bit
UID = 1234
getpwuid returns NULL, errno=0
$ ./getpwuid_bug-64bit
UID = 1234
User name = krico
$

然后如果你strace两个版本的程序,你会看到64位版本立即找到nss_sss

open("/lib64/libnss_sss.so.2", O_RDONLY) = 3

在经历了许多这些之后,32位的一个惨遭失败:

open("/lib/tls/i686/sse2/libnss_sss.so.2", O_RDONLY) = -1 ENOENT (No such file or directory)
stat64("/lib/tls/i686/sse2", 0xfffef338) = -1 ENOENT (No such file or directory)
open("/lib/tls/i686/libnss_sss.so.2", O_RDONLY) = -1 ENOENT (No such file or directory)

所以,我的结论是你需要使用 32 位版本的库安装一些 rpm(例如 sssd-client.i686.rpm)

于 2013-11-19T12:55:28.803 回答
2

我有一个类似的问题,我试图在 x64 debian 上运行 Teamviewer9(也尝试过 Ubuntu)。它不适用于活动目录域中的帐户,Teamviewer 崩溃,因为 getpwuid() 返回 null。我解决了安装 nscd 的问题,如本ubuntu bug中所述。

我花了很多时间来解决这个问题...

于 2014-05-02T19:14:45.397 回答
0

我在 CentOS 8 上遇到了完全相同的问题。@kriko 的回答帮助我解决了它,但我必须这样yum install nss_nis.i686做才能修复它。不是sssd-client.i686

于 2020-12-08T12:13:05.730 回答