我正在尝试将我的 uid 更改为 0 作为具有该CAP_SETUID功能的非 root 用户。我有以下程序:
#include <sys/types.h>
#include <unistd.h>
#include <stdio.h>
#include <sys/capability.h>
#include <sys/prctl.h>
int main(int argc, char *argv[])
{
printf("cap setuid in bset: %d\n", prctl(PR_CAPBSET_READ, CAP_SETUID, 0, 0, 0));
printf("%s\n", cap_to_text(cap_get_file(argv[0]), NULL));
printf("%s\n", cap_to_text(cap_get_proc(), NULL));
printf("uid: %d\n", (int) getuid());
setresuid(0, 0, 0);
printf("uid: %d\n", (int) getuid());
return 0;
}
Run Code Online (Sandbox Code Playgroud)
我将 setuid 功能分配如下:
sudo /sbin/setcap cap_setuid=ep ./capsetuid
Run Code Online (Sandbox Code Playgroud)
我得到以下输出
cap setuid in bset: 1
= cap_setuid+ep
=
uid: 1000
uid: 1000
Run Code Online (Sandbox Code Playgroud)
我希望第二个 printf() 也能显示出这种CAP_SETUID能力。不知何故,我的进程没有获得 …
试图设置cap_setgid,cap_setuid,cap_setpcap.
#include <sys/types.h>
#include <sys/capability.h>
int main()
{
cap_t caps;
caps = cap_get_proc();
cap_value_t cap_list[2];
cap_list[0] = CAP_SETUID;
cap_list[1] = CAP_SETGID;
cap_set_flag(caps, CAP_EFFECTIVE, 2, cap_list, CAP_SET);
cap_set_flag(caps, CAP_INHERITABLE, 2, cap_list, CAP_SET);
cap_set_proc(caps);
cap_free(caps);
setgid(65534);
setuid(65534);
cap_get_proc();
setgid(0);
setuid(0);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
执行是在root用户下进行的.跟踪程序显示了这一点
capget({_LINUX_CAPABILITY_VERSION_3, 0}, NULL) = 0
capget({_LINUX_CAPABILITY_VERSION_3, 0}, {CAP_CHOWN|CAP_DAC_OVERRIDE|CAP_DAC_READ_SEARCH|CAP_FOWNER|CAP_FSETID|CAP_KILL|CAP_SETGID|CAP_SETUID|CAP_SETPCAP|CAP_LINUX_IMMUTABLE|CAP_NET_BIND_SERVICE|CAP_NET_BROADCAST|CAP_NET_ADMIN|CAP_NET_RAW|CAP_IPC_LOCK|CAP_IPC_OWNER|CAP_SYS_MODULE|CAP_SYS_RAWIO|CAP_SYS_CHROOT|CAP_SYS_PTRACE|CAP_SYS_PACCT|CAP_SYS_ADMIN|CAP_SYS_BOOT|CAP_SYS_NICE|CAP_SYS_RESOURCE|CAP_SYS_TIME|CAP_SYS_TTY_CONFIG|CAP_MKNOD|CAP_LEASE|CAP_AUDIT_WRITE|CAP_AUDIT_CONTROL|CAP_SETFCAP, CAP_CHOWN|CAP_DAC_OVERRIDE|CAP_DAC_READ_SEARCH|CAP_FOWNER|CAP_FSETID|CAP_KILL|CAP_SETGID|CAP_SETUID|CAP_SETPCAP|CAP_LINUX_IMMUTABLE|CAP_NET_BIND_SERVICE|CAP_NET_BROADCAST|CAP_NET_ADMIN|CAP_NET_RAW|CAP_IPC_LOCK|CAP_IPC_OWNER|CAP_SYS_MODULE|CAP_SYS_RAWIO|CAP_SYS_CHROOT|CAP_SYS_PTRACE|CAP_SYS_PACCT|CAP_SYS_ADMIN|CAP_SYS_BOOT|CAP_SYS_NICE|CAP_SYS_RESOURCE|CAP_SYS_TIME|CAP_SYS_TTY_CONFIG|CAP_MKNOD|CAP_LEASE|CAP_AUDIT_WRITE|CAP_AUDIT_CONTROL|CAP_SETFCAP, 0}) = 0
capset({_LINUX_CAPABILITY_VERSION_3, 0}, {CAP_CHOWN|CAP_DAC_OVERRIDE|CAP_DAC_READ_SEARCH|CAP_FOWNER|CAP_FSETID|CAP_KILL|CAP_SETGID|CAP_SETUID|CAP_SETPCAP|CAP_LINUX_IMMUTABLE|CAP_NET_BIND_SERVICE|CAP_NET_BROADCAST|CAP_NET_ADMIN|CAP_NET_RAW|CAP_IPC_LOCK|CAP_IPC_OWNER|CAP_SYS_MODULE|CAP_SYS_RAWIO|CAP_SYS_CHROOT|CAP_SYS_PTRACE|CAP_SYS_PACCT|CAP_SYS_ADMIN|CAP_SYS_BOOT|CAP_SYS_NICE|CAP_SYS_RESOURCE|CAP_SYS_TIME|CAP_SYS_TTY_CONFIG|CAP_MKNOD|CAP_LEASE|CAP_AUDIT_WRITE|CAP_AUDIT_CONTROL|CAP_SETFCAP, CAP_CHOWN|CAP_DAC_OVERRIDE|CAP_DAC_READ_SEARCH|CAP_FOWNER|CAP_FSETID|CAP_KILL|CAP_SETGID|CAP_SETUID|CAP_SETPCAP|CAP_LINUX_IMMUTABLE|CAP_NET_BIND_SERVICE|CAP_NET_BROADCAST|CAP_NET_ADMIN|CAP_NET_RAW|CAP_IPC_LOCK|CAP_IPC_OWNER|CAP_SYS_MODULE|CAP_SYS_RAWIO|CAP_SYS_CHROOT|CAP_SYS_PTRACE|CAP_SYS_PACCT|CAP_SYS_ADMIN|CAP_SYS_BOOT|CAP_SYS_NICE|CAP_SYS_RESOURCE|CAP_SYS_TIME|CAP_SYS_TTY_CONFIG|CAP_MKNOD|CAP_LEASE|CAP_AUDIT_WRITE|CAP_AUDIT_CONTROL|CAP_SETFCAP, CAP_SETGID|CAP_SETUID|CAP_SETPCAP}) = 0
setgid(65534) = 0
setuid(65534) = 0
capget({_LINUX_CAPABILITY_VERSION_3, 0}, NULL) = 0
capget({_LINUX_CAPABILITY_VERSION_3, 0}, …Run Code Online (Sandbox Code Playgroud) 我正在尝试使用 capsh 授予自己一个对某个用户没有任何功能的 shell。这样我就可以测试与非 root 相关但仅具有某些功能的安全内容。
基本上我想让一个 shell 运行与此类似的东西。这将模拟测试程序运行的状态。
capsh --print
Current: =
Bounding set =
Securebits: 00/0x0/1'b0
secure-noroot: no (unlocked)
secure-no-suid-fixup: no (unlocked)
secure-keep-caps: no (unlocked)
uid=10101(u0_a101)
gid=10101(u0_a101)
groups=9997(everybody),50101(all_a101)
Run Code Online (Sandbox Code Playgroud)
然后我希望能够再次运行 capsh 来授予用户一些功能和/或更改 uid/gid(如果可能的话)。
如果有人有好的参考,我还没有找到任何关于 capsh 的好的教程。
较新版本的 docker(我认为 1.2 及更高版本)有一个 --cap-add功能。
这提供了对功能功能的细粒度控制,而无需打开所有内容 --privileged=true.
我用谷歌搜索过,但找不到功能列表及其含义。任何人都可以帮忙吗?
计算任何进程的最小 Linux 功能集的最佳方法是什么?
假设您正在强化操作系统,并且其中一些工具可能需要CAP_NET_ADMIN和相关的网络权限,而其他工具可能需要CAP_SYS_NICE。应该有一种方法来告诉每个可执行文件真正需要哪些功能。
我正在创建一个 Docker 容器,我不想为其保留“特权”标志。这是为了使其更安全并更好地控制。我的容器主要从事以下任务(这将帮助我定义其资源访问范围并相应地实施访问控制) 1. 在容器上挂载 gluster 文件系统 2. 运行 SSH 守护进程以接受传入的 SSH 连接 3. 运行一些通常可用的 bash 命令
我在运行 docker 容器时使用“--cap-add=SYS_ADMIN”选项来实现此目的。然而,由于 SYS_ADMIN 添加了比我需要的更多的权限(如下所列)。如何仅实现 SYS_ADMIN 功能的子集?
系统管理员:
执行一系列系统管理操作,包括:quotactl(2)、mount(2)、umount(2)、swapon(2)、swapoff(2)、sethostname(2) 和 setdomainname(2)。
执行特权系统日志(2)
操作(自 Linux 2.6.37 起,应使用 CAP_SYSLOG 来允许
此类操作)。执行VM86_REQUEST_IRQ vm86(2)命令;
对任意 System V IPC 对象执行IPC_SET 和 IPC_RMID 操作
对可信和安全扩展属性执行操作(请参阅
attr(5))
使用ioprio_set(2)进行赋值
IOPRIO_CLASS_RT 和(Linux 2.6.25 之前)IOPRIO_CLASS_IDLE I/O
调度类。
传递套接字凭据时伪造 UID。
在打开文件的系统调用中(例如,accept(2)、execve(2)、open(2)、pipe( 2))。
我正在尝试制作一个程序,该程序使用原始套接字正确运行,具有Linux功能的非root用户.该计划如下:
#include <netinet/ip.h>
int main()
{
int sd = socket(PF_INET, SOCK_RAW, IPPROTO_TCP);
if(sd < 0)
{
perror("socket() error");
return 1;
}
return 0;
}
Run Code Online (Sandbox Code Playgroud)
如果我编译它并以非root身份运行它,我会收到错误,如预期的那样:
[user@localhost ~]$ make socket
cc socket.c -o socket
[user@localhost ~]$ ./socket
socket() error: Operation not permitted
Run Code Online (Sandbox Code Playgroud)
如果我添加该cap_net_raw功能,作为一种有效且允许的功能,它可以工作.
[user@localhost ~]$ sudo setcap cap_net_raw+ep socket
[sudo] password for user:
[user@localhost ~]$ ./socket
[user@localhost ~]$
Run Code Online (Sandbox Code Playgroud)
现在,我想用pam_cap.so它来制作它,以便只有特定的用户才能运行这个程序cap_net_raw,而不是每个人.我/etc/security/capability.conf是:
cap_net_raw user
Run Code Online (Sandbox Code Playgroud)
我/etc/pam.d/login是(注意我也尝试过,/etc/pam.d/sshd但似乎也没有用):
#%PAM-1.0
auth [user_unknown=ignore success=ok ignore=ignore default=bad] pam_securetty.so …Run Code Online (Sandbox Code Playgroud) 我想给几个文件赋予Linux功能(例如CAP_NET_ADMIN)。我正在使用 Yocto,我的文件系统应该是只读的,并且在刷新软件后不得更改(这意味着通常可以使用 setcap 的 pkg_postinst 是不可能的)。
有没有其他方法可以在启动目标后不更改文件结构的情况下为文件提供功能?
我打算使用“setcap”对 Yocto 映像中包含的二进制文件设置一些功能。由于某种原因,这里提到的解决方案对我不起作用: Linux features with yocto 。我已经通过在 rootfs 创建目录中的二进制文件上运行“getcap”来检查这一点:
getcap ${IMAGE_ROOTFS}/usr/bin/mybinary
Run Code Online (Sandbox Code Playgroud)
不返回任何内容。我也没有在最终运行的 SD 卡映像中找到这些功能。
接下来我尝试使用 IMAGE_PREPROCESS_COMMAND 的方法。我将 setcap 命令封装在小型 shell 函数中,例如:
my_setcap_function() {
sudo setcap cap_ipc_owner+ep ${IMAGE_ROOTFS}/usr/bin/mybinary
}
Run Code Online (Sandbox Code Playgroud)
并将函数名称附加到 IMAGE_PREPROCESS_COMMAND。这有效到现在在 {IMAGE_ROOTFS} 目录中的二进制文件上运行 getcap 确实显示了正确的上限设置。但是我仍然没有获得最终运行的 SD 卡映像中的功能。
此外,如果我使用 -o 循环将 rootfs ext4(用于创建最终的 sdcard 映像)安装在目录上,我看不到二进制文件的功能。在我看来,当使用 mkfs.ext4 创建 ext4 时,这些功能会以某种方式丢失。
我必须将 sudo 附加到 setcap,否则它会抱怨“无法设置 CAP_SETFCAP 有效功能:不允许操作”。虽然我的理解是 IMAGE_PREPROCESS_COMMAND 命令是使用 fakeroot 运行的,所以不需要这个 sudo 。
所以,总结一下我的问题:
我正在使用 Yocto Krogoth,目前无法升级。
已经运行的进程需要特权指令,例如使用 SO_RCVBUFFORCE 套接字选项。该进程作为普通用户进程运行。
如何赋予这个过程能力/权限?基于文件的功能设置仍然是一个梦想吗?
我已经尝试了/usr/sbin/setpcapslibcap 包和cap_set_proc()api 中的实用程序,但该CAP_SETPCAP功能在系统上被阻止(基于 Fedora 4 和 2.6.20 内核的遗留系统),因此它无法为不同的自我授予/删除功能过程。
考虑过为该进程设置临时 root uid,但是有没有办法更改外部已运行进程的有效 UID?setuid()// ...函数seteuid()只能修改当前进程(谁在调用该函数)。
linux ×9
c ×2
docker ×2
privileges ×2
yocto ×2
capsh ×1
containers ×1
ext4 ×1
pam ×1
permissions ×1
security ×1
sockets ×1