关于CTF-PWN获得shell后没有读取flag权限的问题

前言

在和学弟的一次日常交流中,发现linux权限设置有个很神奇的设置,可以用来出点有意思的题。主要思路是https://pwn.college/desktop里面的有趣设置

RWS

一、rws权限的概念和特点

rws是Linux文件权限中的一种,它是与set-UID和set-GID(SUID和SGID)特性相关联的权限。SUID和SGID是授予执行权限和组权限的一种特殊权限。SUID使得一个文件在被执行时拥有文件所有者的权限,而SGID则使得一个文件在被执行时拥有文件所在组的权限。SUID和SGID通常与可执行文件相关联,使得某些程序在执行时可以获得超级权限,比如管理员权限。

rws权限是rwx权限中的一种特殊形式,即在执行权限(x)的位置上,将其替换为s。rws权限的全称是set-UID、set-GID和可执行(即rwx权限)。使用rws权限赋予文件的执行者以文件所有者和文件所在组的权限,这使得这个文件可以在执行期间以这些权限运行程序。rws权限还是一种持久性的权限,即一旦授予某个文件,持续有效,不会因为文件移动或者复制而失效。

二、rws权限的使用方法和注意事项

  1. rws权限设置方法:使用chmod命令将文件的执行权限设置为rws权限即可。例如:

chmod 4774 filename

其中4表示SUID,即set-UID;7表示rwx权限,即读、写、执行权限。因此,4774表示文件的所有者拥有读、写、执行等权限,并且将set-UID设置为开启状态。

  1. rws权限的设置需要谨慎。因为rws权限给予执行者极高的权限,不当使用会导致系统不安全。因此,应该仅在必要时才使用rws权限,同时,必须对使用rws权限进行严格的限制和控制。

  2. 建议使用SGID来替代SUID,因为SGID只赋予执行者所在组的权限,比SUID更安全。

  3. rws权限默认只出现在二进制文件和命令文件中,而不出现在普通文件和目录中。因此,普通文件和目录中存在rws权限会被认为是异常操作,会被系统自动拒绝。

  4. 在使用rws权限时,应该了解文件所在目录的权限。如果文件所在的目录拥有其他用户读写权限,那么执行者就可以改变文件所在目录的所有权,因此,应该对目录的权限进行严格限制。

在CTF中的用法

SUID使得一个文件在被执行时拥有文件所有者的权限,于是我们可以得出该文件可以执行文件所有者执行的命令。于是我们实验了一下,实验的环境和权限设置如下

image-20230815003555017

orw实验

我们测试一下能不能在这种权限设置下获得flag,下面是源代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
#include<sys/stat.h>
#include<stdio.h>

int main()
{
FILE *fp;
char ch;
fp = fopen("flag", "r");
if (fp == NULL)
{
printf("Open file failed!");
return -1;
}
while ((ch = fgetc(fp)) != EOF)
{
printf("%c", ch);
}
fclose(fp);
return 0;
}

image-20230815004148929

最后发现有rws的可以得到flag

chmod实验

于是我们再试一下chmod函数

1
2
3
4
5
6
7
8
#include<sys/stat.h>
#include<stdio.h>

int main()
{
chmod("./flag",777);
return 1;
}

image-20230815004011371

可以发现,成功改写了flag权限

getshell实验

再实验一下getshell

1
2
3
4
5
6
7
#include<sys/stat.h>
#include<stdio.h>

int main()
{
system("/bin/sh");
}

image-20230815004427271

实验结果显示,最后我们获取的权限是kali的权限,不是root的权限,所以通过正常的getshell是无法得到flag的,只有通过运行的文件里面的代码才能有root权限,弹出来的shell是没有权限的。

出题

这个方法可以作为一个小tips去出,就是考一个简单的linux权限设置