分享
 
 
 

囚禁你的精灵(daemon)进程

王朝other·作者佚名  2006-11-24
窄屏简体版  字體: |||超大  

简介

chroot牢笼(jail)概念综述

Postfix精灵进程分析

一个禁锢(jail)HOWTO:icecast

第一步:把icecast安装在牢笼(jail)环境中

第二步:配置牢笼(jail)环境

第三步:为这个精灵建立一个chroot包装

那些地方不能用牢笼环境

结论

简介

我们经常会听说计算机遭到基于Internet的远程攻击。通常位于攻击最前线的是一些服务器软件,例如:WEB、邮件和DNS,这些服务通常是通过监控进程(daemon,也可以叫作精灵进程)来提供的。这些服务即使是位于防火墙之后,也需要面对各种探测和攻击,以至让攻击者获得系统访问权限。大多数的恶意攻击者都会在系统安装rootkit,以便能够进行通常的系统操作。

一般情况下,这些rootkit和病毒需要使用目标系统的可执行文件、动态连接库以及配置文件。比如:一个安装在linux主机上的rootkit可能需要访问/bin/sh或者能够读写/etc目录下的系统配置文件。而且一旦系统被攻击者侵入,攻击者获得了root权限,就可以运行修改任何自己需要的文件。最近的lion、ramen蠕虫对BIND的攻击就可以证明以上观点。

但是如果你对精灵进程(daemon)进行限制,只允许其访问必要的文件,而不能访问整个文件系统,又将如何呢?这样就可以使我们的安全不再依赖于daemon软件开发人员的安全水平。

幸运的是,UNIX系统能够提供这样一种机制实现上面这种想法。在最近的BIND攻击中,Thaumaturgix, Inc的IT管理员William Cox提出了“在chrooted的环境中运行服务器进程,减小你的暴露程度(The best way to limit your exposure is to run the server in a 'chrooted' environment))。这种chrooted环境通常叫作一个chroot牢笼(jail),实际上这种概念已经存在了很长时间了,但是一直没有被软件开发人员和系统管理人员充分利用。

chroot牢笼(jail)概念综述

实现一个chroot jail包括两种方式:

限制进程只能访问整个文件系统的一个子集。

以较低的权限运行服务进程。

这两种方式是由一些标准的系统调用来提供的。首先,是chroot(),这个系统调用能够限制进程对文件系统的访问。即使某个进程是以root的权限运行的,它对文件/目录的访问也都是相对于chroot()系统调用限制的整个文件系统的子目录。

例如,如果一个进程以/var/sample/jail为参数执行了chroot()系统调用,现在它要访问一个文件:/etc/passwd,但是操作系统最后会把这个访问请求替换为对 /var/sample/jail/etc/passwd的访问。chroot系统调用只能以root权限调用。

降低进程权限的系统调用主要包括:setuid()、setgid()和setgroups()。setuid()指定进程的实际和有效用户权限;而setgid()指定进程的实际和有效组权限。setuid()系统非常重要,一旦通过它进入较低的权限运行,进程将无法自己重新获得root权限。setgroups()定义进程的追加组成员关系。除此之外,还有一些其它的相关系统调用,用户可以从自己系统的手册页中获得相关文档。

其它种类的操作系统可能还有另外的进程束缚方法。例如在FreeBSD中就有一个jail()函数。为了使你更好地体会到jailing的好处,我将通过一个典型的rootkit加以说明,在不同的权限下以及有没有被限制在jail环境中rootkit对系统的危害是不同的。在此,要时刻记住一件事情,当一个服务被侵入,攻击者就能够拥有服务进程所具有的权限。请看下面这个表格:

+-----------------+---------------------------------------\

| | | |

| | running as root | running non-root |

| | | |

+-----------------+-------------------+-------------------|

| | | |

| entire fs | (a) | (c) |

| | | |

|-----------------+-------------------+-------------------|

| | | |

| jailed fs | (b) | (d) |

| | | |

+---------------------------------------------------------/

运行于(a)类(进程以root权限运行并且可以访问整个文件系统)状态下的进程是rootkit的首选目标,侵入这样的服务,攻击者可以修改二进制可执行文件,例如:/bin/ps、/bin/netstat等,打开特权网络端口,读取任意的系统文件包括:/etc/shadow文件。最糟糕的是,他们能够对系统进行完全的破坏,比如:rm -rf /。运行于这种状态,最为常见的一个例子就是sendmail(http://www.sendmail.org。

如果服务进程处于(b)类(root权限、牢笼环境)状态下,一般的rootkit就可能无法正常操作,因为它们一般需要一个shell(/bin/sh)和一些基本的命令,例如:/bin/rm和/bin/cp。然而,在这种状态下,rootkit照样可以打破牢笼(jail)。因为服务进程以root权限运行,攻击者可以通过攻击代码直接执行一些允许root执行的操作(例如:直接引用牢笼之外文件系统的索引节点)。因此,这种状态虽然比(a)类状态安全(门槛高的多),但是也无法对服务提供足够的保护。

服务进程处于(c)类(非root权限,可以访问整个文件系统)状态下,对整个系统的威胁比(a)状态小,因为毕竟攻击者无法直接获得root权限。但是,如果服务进程处于这种状态下,攻击者一旦侵入这个服务,就可以执行一些命令,获得一个shell进行交互,然后很可能通过本地攻击获得root权限。即使攻击者不能获得root权限,也可以访问到系统的绝大多数配置文件和其它信息,例如:用户的电子邮件帐户信息(大量的垃圾邮件将蜂拥而至)。

最后,处于(d)类(非root权限,jail环境)状态下的服务进程受到的限制最为苛刻,这样攻击者根本没有机会执行shell,也不可能获得大量的系统信息。而且,对系统进行的所有破坏都被限制在jail环境中。在这种状态下,最大的威胁就是攻击者在这个jail环境中防止一个可以被jail环境之外的进程访问的可执行文件,从而使攻击代码扩散出jail环境。因此,你应该经常监视你的牢笼,看一下里面的囚犯是否逃出来了:P。

下面我们将举一个现实的例子进行说明。

Postfix精灵进程分析

Postfix(http://www.postfix.org)是一个邮件传输代理(Mail Transfer Agent)。它允许用户收/发SMTP邮件,把给本地用户的邮件投递到用户主机。Postfix是sendmail的一个变通,作者Wietse Venema对安全问题倾注了很大的关注。这个软件是一个非常典型的所谓守纪律精灵(disciplined daemon),可以安装在一个chroot牢笼(jail)环境中。我相信理解了Postfix是如何工作的,你就可以实现一个简单的安全精灵(daemon)。

Postfix从一个叫作master的程序开始执行,master以root权限启动,然后继续以root权限运行。不过,master本身非常小,其作用这是spawn进程,这些进程大部分会被放在一个chroot牢笼(jail)环境中执行实际的工作。通过这种方式,以root权限运行的代码数量非常有限。

下面我们看一看master是怎样和smtpd进行交互的。master一旦检测到一个向25号端口(SMTP的监听端口)的连接,它就会执行smtpd。下面我们就看一下postfix使用的一些jailing方法,这些代码在src/util/chroot_uid.c文件中。在讲述过程中,我们把/var/spool/postfix作为chroot牢笼(jail)环境的根目录:

+-----------------------------+-----------------+--------------------\

| | user/group | filesystem |

+-----------------------------+-----------------+--------------------|

| master is run on startup | root/root | / |

|-----------------------------+-----------------+--------------------|

| master opens port 25 | root/root | / |

|-----------------------------+-----------------+--------------------|

| master detects connection | root/root | / |

|-----------------------------+-----------------+--------------------|

| master forks smtpd | root/root | / |

|-----------------------------+-----------------+--------------------|

| master continues execution | root/root | / |

|-----------------------------+-----------------+--------------------|

| smtpd inherits permissions | root/root | / |

|-----------------------------+-----------------+--------------------|

| smptd calls setgid() | root/postfix | / |

|-----------------------------+-----------------+--------------------|

| smptd calls initgroups()* | root/postfix | / |

|-----------------------------+-----------------+--------------------|

| smtpd calls chroot() | root/postfix | /var/spool/postfix |

|-----------------------------+-----------------+--------------------|

| smptd calls setuid() | postfix/postfix | /var/spool/postfix |

|-----------------------------+-----------------+--------------------|

| smtpd processes connection | postfix/postfix | /var/spool/postfix |

|-----------------------------+-----------------+--------------------|

| smtpd continues listening | postfix/postfix | /var/spool/postfix |

+-----------------------------+-----------------+--------------------/

* initgroups()类似于setgroups();设置多重组成员关系。

最后,smtpd进程的状态如下所示(503是postfix用户/组的ID):

#cat /proc/ status

Name: smtpd

State: S (sleeping)

Pid: 1301

PPid: 665

TracerPid: 0

Uid: 503 503 503 503

Gid: 503 503 503 503

FDSize: 256

Groups: 503

[...]

处理完这个连接后,smtpd精灵会继续监听SMTP连接,如果在指定的时间内没有连接,就超时退出。

从上面的过程你可以对进程状态的演变有一个大体的了解。在整个生命周期中,smtpd从(a)状态开始,接着进入(b)状态,然后快速地进入(d)状态,最后在(d)状态中运行。实际上,这是把进程放到正确的chroot牢笼(jail)环境的标准步骤。

一个jail HOWTO:icecast

理解了这些背景知识非常有用,但是怎样对一个精灵进程进行禁锢?而且,对一个精灵进程进行禁锢,是否还要取决于精灵进程本身是否愿意?为了回答这些问题,我将讲述一个实际的精灵禁锢过程,虽然它比较简单,但是其作者并没有给出一个精灵禁锢文档。不过请注意:一些流行的精灵系统例如:BIND,已经有了如何创建一个chroot牢笼环境的文档。

在我们的例子中,我选择的程序叫作icecast(http://www.icecast.org)。icecast是一个音频流中继服务器,它从一个基于网络的客户程序(例如:winamp)获得音频流,然后接收一定数量听众的连接,让这些听众收听连续的音频流。我想在自己的机器上运行这个程序,但是我恐怕这个服务程序存在安全缺陷,所以想对其进行限制。

我们看一下这个服务起始的权限,3这个精灵进程打开两个不需root权限的端口,一个用于接收音频流,而另一个等待客户程序的连接。在运行过程中,还可以通过一个本地控制台对其进行维护,不过这不是必须的。除此之外,在运行过程中icecast还要维护一个日志文件。

这个程序以非root权限运行,这很好。但是,如果不对其进行禁锢(jail),在理论上如果它被攻击者侵入,让攻击者获得了一个shell,攻击者就可以窥探我的系统,甚至通过其它的本地攻击获得root权限。因此,我要对icecast进行禁锢(jail)。

下面是我们的禁锢过程:

把这个精灵安装到指定的目录,在保证它能够正常运行的情况下,为其分配尽可能小的文件访问权限。把所有不必要的东西从这个牢笼(jail)目录删除。

对这个牢笼环境进行必要的配置。这个环境一般包括:精灵运行的动态连接库文件,一个本地的/dev/null设备,可能还需要一些本地的时间信息。

如果必要,还要建立一个执行chroot和放弃教高权限的函数包装(wrapper)。如果这个精灵能够想postfix的子进程那样自己实现上述功能,你就可以不必自己来做了。要注意:一定要把这些包装(wrapper)放在牢笼(jail)环境之外。

第一步:把icecast安装在牢笼(jail)环境中

首先,我们把所有icecast的文件安装到/usr/local/icecast目录,在我们的例子中,/usr/local/icecast是icecast牢笼(jail)的根目录。你安装牢笼(jail)环境的地方非常重要,可能应该是一个只读的文件系统。

下面是其安装目录的内容,icecast安装目录的所有者是root

drwxr-xr-x 2 root root 4096 May 6 14:38 bin

drwxr-xr-x 2 root root 4096 May 19 18:43 conf

drwxr-xr-x 2 root root 4096 May 6 14:38 doc

drwxr-xr-x 2 root root 4096 May 6 14:41 logs

drwxr-xr-x 2 root root 4096 May 19 16:41 static

drwxr-xr-x 2 root root 4096 May 6 14:38 templates

功过阅读icecast的文档和一些实验,我们知道icecast正常运行需要以下的文件/目录权限:

可执行:bin/icecast

可写:logs目录

可读:conf、static和templates目录

现在,我决定建立一个叫icecast的用户,使用这个用户来运行icecast。在执行这个服务时,需要向logs目录中写入日志,而我又不想让任何人都能够写这个目录,因此才建立这个新的用户。

#useradd icecast -s /bin/false

然后,你应该在/etc/passwd中发现如下条目,而且这个帐户处于锁定状态,无法登录:

icecast:x:505:505::/usr/local/icecast:/bin/false

现在,我们需要决定需要那些文件以及它们应该放在哪里。首先,我们需要改变logs子目录的权限,还可以把没有必要的子目录doc删除。

icecast不象postfix的子进程,能够自己调用chroot系统调用,因此为了在执行chroot包装(wrapper)程序之后,能够执行icecast,我们需要把bin/icecast可执行文件放在这个牢笼(jail)环境中。然后,我们需要编写一个chroot包装程序,把他放在牢笼(jail)环境之外。

除此之外,icecast还需要在conf目录配置文件。我们假设icecast已经被安装在/usr/local/icecast目录中。

第二步:配置牢笼(jail)环境

这一步的目标是找出icecast运行需要的动态连接库并把它们安装到这个牢笼(jail)环境,这一部分可能因系统而异。没有这些动态连接库,icecast将无法执行,而且这个原因显示的执行错误信息也让人摸不着头脑,比如:/bin/icecast: File Not Found

在Linux系统中,你可以运行ldd程序来查看icecast需要的动态连接库以及它们在文件系统的位置。例如(所有的命令我们都是在/usr/local/icecast目录下执行的):

$ ldd bin/icecast

libm.so.6 => /lib/i686/libm.so.6 (0x40022000)

libpthread.so.0 => /lib/i686/libpthread.so.0 (0x40046000)

libc.so.6 => /lib/i686/libc.so.6 (0x4005b000)

/lib/ld-linux.so.2 => /lib/ld-linux.so.2 (0x40000000)

现在,我们把这些动态连接库都复制到这个牢笼(jail)的相似位置:

# mkdir -p lib/i686

# cp -pi /lib/i686/libm.so.6 /lib/i686/libpthread.so.0 /lib/i686/libc.so.6 lib/i686

# cp -pi /lib/ld-linux.so.2 lib

这样,这些动态连接库就被复制到了牢笼(jail)的/lib目录下,也就是说bin/icecast能够在牢笼中执行了。

不过,这样还不够,在任何的牢笼环境中都建立一个/dev/null设备是一个非常不错的想法:

# mkdir dev

# mknod -m 666 dev/null c 1 3

这一步要谨慎,并确信你已经正确地建立了设备节点。

许多服务可能需要系统的/etc/localtime文件。最后,我们需要把/etc/localtime文件复制到/usr/local/icecast/etc/目录中,并填加一个到/usr/local/icecast/usr/lib/zoneinfo的符号连接:

# mkdir etc

# mkdir usr/lib

[1] [2] 下一页

 
 
 
免责声明:本文为网络用户发布,其观点仅代表作者个人观点,与本站无关,本站仅提供信息存储服务。文中陈述内容未经本站证实,其真实性、完整性、及时性本站不作任何保证或承诺,请读者仅作参考,并请自行核实相关内容。
2023年上半年GDP全球前十五强
 百态   2023-10-24
美众议院议长启动对拜登的弹劾调查
 百态   2023-09-13
上海、济南、武汉等多地出现不明坠落物
 探索   2023-09-06
印度或要将国名改为“巴拉特”
 百态   2023-09-06
男子为女友送行,买票不登机被捕
 百态   2023-08-20
手机地震预警功能怎么开?
 干货   2023-08-06
女子4年卖2套房花700多万做美容:不但没变美脸,面部还出现变形
 百态   2023-08-04
住户一楼被水淹 还冲来8头猪
 百态   2023-07-31
女子体内爬出大量瓜子状活虫
 百态   2023-07-25
地球连续35年收到神秘规律性信号,网友:不要回答!
 探索   2023-07-21
全球镓价格本周大涨27%
 探索   2023-07-09
钱都流向了那些不缺钱的人,苦都留给了能吃苦的人
 探索   2023-07-02
倩女手游刀客魅者强控制(强混乱强眩晕强睡眠)和对应控制抗性的关系
 百态   2020-08-20
美国5月9日最新疫情:美国确诊人数突破131万
 百态   2020-05-09
荷兰政府宣布将集体辞职
 干货   2020-04-30
倩女幽魂手游师徒任务情义春秋猜成语答案逍遥观:鹏程万里
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案神机营:射石饮羽
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案昆仑山:拔刀相助
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案天工阁:鬼斧神工
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案丝路古道:单枪匹马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:与虎谋皮
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:李代桃僵
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案镇郊荒野:指鹿为马
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:小鸟依人
 干货   2019-11-12
倩女幽魂手游师徒任务情义春秋猜成语答案金陵:千金买邻
 干货   2019-11-12
 
推荐阅读
 
 
 
>>返回首頁<<
 
靜靜地坐在廢墟上,四周的荒凉一望無際,忽然覺得,淒涼也很美
© 2005- 王朝網路 版權所有