免费注册 查看新帖 |

Chinaunix

  平台 论坛 博客 文库
12下一页
最近访问板块 发新帖
查看: 12996 | 回复: 11
打印 上一主题 下一主题

关于setuid权限 [复制链接]

论坛徽章:
1
摩羯座
日期:2014-04-06 10:30:51
跳转到指定楼层
1 [收藏(0)] [报告]
发表于 2010-04-06 22:51 |只看该作者 |倒序浏览
[www@linux test]$ ll
total 8
-rw-r--r-- 1 root root 18 Apr  6 07:15 index.php
-rwsrwxrwx 1 root root 64 Apr  6 08:20 ngx.sh
[www@linux test]$ cat ngx.sh
#!/bin/bash
/usr/local/nginx/sbin/nginx -s reload
echo success!
[www@linux test]$ ./ngx.sh
[alert]: could not open error log file: open() "/usr/local/nginx/logs/error.log" failed (13: Permission denied)
2010/04/06 08:42:25 [warn] 17339#0: the "user" directive makes sense only if the master process runs with super-user privileges, ignored in /usr/local/nginx/conf/nginx.conf:1
2010/04/06 08:42:25 [notice] 17339#0: signal process started
2010/04/06 08:42:25 [alert] 17339#0: kill(16231, 1) failed (1: Operation not permitted)
success!


ngx.sh已经设置了setuid权限。
www用户为什么还是执行不了?

论坛徽章:
0
2 [报告]
发表于 2010-04-07 05:47 |只看该作者
有个概念要明白~SUID只能用在二进制文件上

论坛徽章:
0
3 [报告]
发表于 2010-04-07 09:05 |只看该作者
膜拜 2楼

论坛徽章:
0
4 [报告]
发表于 2010-04-07 09:29 |只看该作者
我觉得,关于setuid权限这个东西,应该详细说明下,很多人都并不够了解。

1. ls -l显示出来的这个叫做suid位,就是如rwS-r-x-r-x这样中的S(故意大写了)。
当S出现在所有用户的执行位时,其他凡是对此文件有执行权的用户执行时权限自动提升为所有者的权限。
LZ的问题是SH不具备suid位的权限,但为什么不能让sh具备suid位权限呢?
很显然,/bin/sh的所属用户是root,当其具备suid位权限的时候,任何能执行/bin/sh的用户都是root。
另:suid位改变的是执行用户的euid,这可以通过简单的程序来看出。

2. 系统api里有setuid(2)以及setgid(2)以及seteuid(2)等系统调用。作用同样是改变程序执行时的所属权限,但这些跟suid位有什么区别呢?
简要说明一下两者的大部分用途:
  * suid位大多用于提升权限;
  * setuid(2)等调用大多用于降低权限;
setuid(2)这些调用是只有root用户才能执行成功的,普通用户执行包含了setuid(2)的程序时,是不会成功的。原因很简单:
如果一个普通用户都能随便更改自己的执行权限到其它用户,那么系统中出现一些问题也不知道是谁干的。

实例程序分析:su工具:
  su工具具备了suid位,程序代码中还包括了setuid(2)等调用,何故?
  su工具用途是用来切换用户权限的,而且可以在任何用户之间切换:
  纯粹的suid位是解决不了多用户权限切换的,总不至于频繁更改程序的所属用户吧。
  而api中的setuid(2)能解决多用户切换问题,可是普通用户没有权限执行啊......
  两者结合呢?让su用户有suid位的权限,再通过setuid(2)切换用户权限,如此:
  先用户执行su的时候具备root权限,再接着有权执行setuid(2)切换到自己想要的用户的权限......
  如果看su的源码,会发现其中有对文件系统mount时时候挂载了suid特性的检测,由此你会了解到setuid特性可以在mount的-o中关闭掉。
  具体可以参考man 2 setuid,man mount等等。

写的乱,希望能帮大家透彻了解这方面的知识。

论坛徽章:
1
摩羯座
日期:2014-04-06 10:30:51
5 [报告]
发表于 2010-04-07 09:39 |只看该作者
先谢谢楼上几位,不过还是没有弄明白。

情况可能又复杂了,因为我是想在PHP程序里reload Nginx。
大致代码是这样
<?
$cmd = '/usr/local/nginx/sbin/nginx -s reload';
shell_exec($cmd);
?>

没想到这么麻烦。

这个搞的很头疼,另外一种方法搞个cron以root执行,定时查看task,有task就执行。
不过这样毕竟不是实时的。

没发现资料里有提供到2进制,用C写了一遍,结果和BASH的一样。

论坛徽章:
0
6 [报告]
发表于 2010-04-07 10:41 |只看该作者
解决思路就不对。

用sudo啊。

用sudo只允许执行php的用户执行nginx这一个命令即可。

不会的话搜索sudo权限规划。

论坛徽章:
0
7 [报告]
发表于 2010-04-07 12:12 |只看该作者
你把脚本置位有什么用?要把这个chomd +s /usr/local/nginx/sbin/nginx 才有用.

论坛徽章:
1
摩羯座
日期:2014-04-06 10:30:51
8 [报告]
发表于 2010-04-07 12:16 |只看该作者
本帖最后由 SeriousCool 于 2010-04-07 12:27 编辑

又出了点问题。。
下面的C代码,设置了sudo,www用户在命令行下执行后可以生效。
PHP以fastcgi模式运行,身份也是www,放在PHP程序里通过浏览器访问,执行后无效。。。

<?
shell_exec('/usr/bin/sudo /home/www/httpdocs/bin/ngx');
?>

#include <unistd.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>

int main(){
        FILE *read_fp;
        char buffer[BUFSIZ + 1];
        int chars_read;
        memset(buffer, '\0', sizeof(buffer));
        read_fp = popen("/usr/local/nginx/sbin/nginx -s reload", "r");
        if (read_fp != NULL){
                chars_read = fread(buffer, sizeof(char), BUFSIZ, read_fp);
                pclose(read_fp);
                exit(EXIT_SUCCESS);
        }
        exit(EXIT_SUCCESS);
}

论坛徽章:
0
9 [报告]
发表于 2010-04-07 12:34 |只看该作者
单纯解决问题个的话,能否把这个:

/usr/local/nginx/logs/error.log

换个路径?

论坛徽章:
0
10 [报告]
发表于 2010-04-07 12:37 |只看该作者
真晕了。

你何必再写个C程序呢?

你直接设置www用户sudo权限只能执行/usr/local/sbin/nginx不就行了么?

将sudo那行设置为NOPASSWD,这个你确认设置了么?
没有设置的话,命令行你能输入密码,非交互的php程序里你能么?

还有针对你的那个多余的C语言程序再警告一句:不要随便使用popen(3)这类依赖IFS和PATH环境变量的东西!
您需要登录后才可以回帖 登录 | 注册

本版积分规则 发表回复

  

北京盛拓优讯信息技术有限公司. 版权所有 京ICP备16024965号-6 北京市公安局海淀分局网监中心备案编号:11010802020122 niuxiaotong@pcpop.com 17352615567
未成年举报专区
中国互联网协会会员  联系我们:huangweiwei@itpub.net
感谢所有关心和支持过ChinaUnix的朋友们 转载本站内容请注明原作者名及出处

清除 Cookies - ChinaUnix - Archiver - WAP - TOP