【问题标题】:How to ensure correct file permissions如何确保正确的文件权限
【发布时间】:2013-05-19 03:23:12
【问题描述】:

为了保护应用程序不被错误使用,我正在尝试检查其配置文件是否具有正确的权限,以便应用程序可以信任未被其他人修改的文件内容。

我认为以下规则是正确的:

  • 文件不得被其他人写入
  • 文件必须由受信任的用户/组拥有:root 或
  • 文件必须由运行应用程序的有效用户/组拥有(想想 setuid 程序)

这里是一个例子:

#include <stdio.h>
#include <unistd.h>
#include <sys/stat.h>

#include <string.h>
#include <errno.h>

static
int is_secure(const char *name)
{
    struct stat st;

    uid_t euid = geteuid();
    gid_t egid = getegid();

    if (stat(name, &st) != 0) {
        int err = errno;
        fprintf(stderr, "can't stat() '%s': %d (%s)\n", name, err, strerror(err));
        return 0;
    }

    /* writable by other: unsecure */
    if ((st.st_mode & S_IWOTH) != 0) {
        return 0;
    }

    /* not owned by group root and not owned by effective group: unsecure */
    if (st.st_gid != 0 && st.st_gid != egid) {
        return 0;
    }

    /* not owned by user root and not owned by effective user: unsecure */
    if (st.st_uid != 0 && st.st_uid != euid) {
        return 0;
    }

    return 1;
}

int
main(int argc, char *argv[])
{
    int i;

    for(i = 1; i < argc; i++) {
        printf("'%s' : %s\n", argv[i], is_secure(argv[i]) ? "sure" : "unsure");
    }

    return 0;
}

由于我不确定我的假设,有人可以检查我是否在文件权限检查中留下了一些漏洞。

更新

sudo 有一个功能:sudo_secure_path,它只检查一个 uid/gid,但它负责检查组写入位。

问候。

【问题讨论】:

  • 考虑Secure access to files in a directory identified by an environment variable 中的信息。那里的情况更复杂。但是,一些想法是有效的,特别是指向文件的路径也需要是安全的。
  • 乔纳森是对的。通向文件的路径中的每个元素都只能由受信任的用户写入,以确保完全安全。否则,可能会发生奇怪的情况,例如移动路径的组件并将其替换为指向不同但相似的目录结构的指针,完全绕过您的文件,但与重写整个配置文件具有相同的效果。根据配置文件中的内容,它可以帮助攻击者闯入或至少进行更明智的 DOS 攻击,因此最好让文件仅由其所有者/受信任的用户读取。
  • @JosephMyers 谢谢。我应该制作一个更完整的示例:此代码用于检查目录和其中的每个文件。
  • @JonathanLeffler 谢谢。我应该制作一个更完整的示例:此代码用于检查目录和其中的每个文件。
  • 假设配置目录的父目录是安全的。此外,为了提高安全性,函数openat()fstatat()fstat() 用于确保使用检查目录中的文件,而不是其他目录中的文件,移动到应用程序的后面。在打开文件/目录时使用 O_NOFOLLOW 可以防止一些符号链接攻击。

标签: c file security unix permissions


【解决方案1】:

您的规则和代码在我看来是正确的,但您应该注意以下可能仍会影响您的实施的安全风险。

  1. 具有机器物理访问权限或 NFS/SMB 访问权限的攻击者可以使用具有 root 权限的机器挂载文件系统,然后修改您的文件。
  2. 以受信任用户或 root 身份运行的另一个程序中的漏洞可能允许该程序被利用来修改您的文件。
  3. 只要粗心的用户或系统管理员弄乱了文件的权限设置,就会破坏您的安全检查。我在备份和复制到拇指驱动器等过程中看到过这种情况。
  4. 还要确保该文件不可执行。我想不出一个可以在配置文件上利用它的实例,但安全的一般规则是不授予该工作不需要的任何特权。

如您所见,这些问题不受您的代码控制。因此,在向他们保证配置文件的不可篡改之前,您应该确保您的客户了解这些风险。

【讨论】:

  • 感谢您的回答。你的cmets很有趣。整个系统的安全性令人耳目一新。我的威胁模型/安全需求非常狭窄。我只是想确信配置不受不可信任用户(另一个用户)的控制。确保文件内容正确超出了问题的范围,这是另一个整个系统的问题。
【解决方案2】:

我相信你也想检查目录的权限。

如果允许用户写入目录,则用户将能够mv 属于正确用户的另一个文件来替换这个文件。

类似:

sudo touch foo.conf
sudo touch foo.conf-insecure-sample
mv -f foo.conf-insecure-sample foo.conf

【讨论】:

  • 好收获。此处提供的代码中没有显示它,但在实际代码中的各个文件之前也会检查目录。顺便说一句,它不能确保父目录或任何以前的级别是正确的:其他级别不在应用程序的范围内,它与系统相关。
猜你喜欢
  • 2013-11-30
  • 2016-12-25
  • 1970-01-01
  • 1970-01-01
  • 2013-08-23
  • 2011-04-08
  • 2013-02-14
  • 2022-01-20
相关资源
最近更新 更多