我目前的理解是,您必须手动使用restorecon才能将所需的上下文应用于新创build的文件或目录,除非您对从其父目录inheritance的上下文感到满意。
我想知道是否有可能自动应用上下文创build基于其path而不必运行restorecon 。
我用googlesearch了一下,发现了Dan Walsh的这篇文章 ,他提到了使用inotify改变创build上下文的restorecond 。 他也指出了这个明显的问题(比赛条件)。 如果孩子不应该从父目录inheritance它的上下文,这是自动解决重新上下文问题的唯一方法吗?
一个问题是restorecond似乎没有像/etc/selinux/targeted/contexts/files/file_contexts那样处理条目,也就是说没有正则expression式,并且它不能recursion地工作,所以/etc/selinux/restorecond.conf不能包含类似的东西
/var/www(/.*)?/logs(/.*)?
要么
/var/www/*
甚至
/var/www/*/logs
有没有办法解决这个问题?
编辑:
根据@迈克尔的答案,这应该工作OOTB,如果各自的规则存在,但它不:
# rm -rf /var/www/foo # semanage fcontext -a -t httpd_log_t '/var/www/foo/logs' # grep '/var/www.*logs' /etc/selinux/targeted/contexts/files/file_contexts* /etc/selinux/targeted/contexts/files/file_contexts:/var/www(/.*)?/logs(/.*)? system_u:object_r:httpd_log_t:s0 /etc/selinux/targeted/contexts/files/file_contexts.local:/var/www/foo/logs system_u:object_r:httpd_log_t:s0 # matchpathcon /var/www/foo/logs /var/www/foo/logs system_u:object_r:httpd_log_t:s0 # mkdir -p /var/www/foo/logs # touch /var/www/foo/logs/quux # ls -alZ /var/www/foo/logs* drwxr-xr-x. root root unconfined_u:object_r:httpd_sys_content_t:s0 . drwxr-xr-x. root root unconfined_u:object_r:httpd_sys_content_t:s0 .. -rw-r--r--. root root unconfined_u:object_r:httpd_sys_content_t:s0 quux # restorecon -vR /var/www/foo restorecon reset /var/www/foo/logs context unconfined_u:object_r:httpd_sys_content_t:s0->unconfined_u:object_r:httpd_log_t:s0 restorecon reset /var/www/foo/logs/quux context unconfined_u:object_r:httpd_sys_content_t:s0->unconfined_u:object_r:httpd_log_t:s0
内核通过以下过程确定新创build的文件的文件types。
在绝大多数情况下,新文件inheritance父目录types。 有时候这是不可取的 – 所以政策制定者可以根据谁在做标签的条件以及为了过渡到另一种types而创build规则。
这是通过type_transition语句在策略中控制的,但通常情况下,策略filetrans_pattern将调用filetrans_patternmacros。
在内核中,这些决定不是基于path,而是基于types(尽pipe在较新策略中存在一个小例外)。
一个规则通常是这样的;
type_transition httpd_t var_log_t:file httpd_var_log_t;
在这个例子中,规则规定。 如果执行文件创build的进程/用户是httpd_t并且其中创build对象的目录是var_log_t并且该对象被分类为file ,则新文件必须标记为httpd_var_log_t 。
这当然有一些限制,这是在Apache中创build.htaccess文件(在/ var / www / html)中的一个很好的例子。 在这个例子中,创build一个文件types与其父目录相同types的默认策略适用,但实际上这个文件的正确types是httpd_sys_htacess_t而不是httpd_sys_htacess_t的默认值。
这是一个已知的问题多年,最终通过允许策略编写者指定转换适用于策略的文件名来修复 – 不幸的是,这个function在EL6中是不可用的。
在你的具体情况 – 正如你所提到的,有一些解决方法涉及restorecond。 除此之外,您应该理想地将数据分成不同的types,方法是将它们放在单独的子目录中,其中子目录是具有充分标记的types。 如果仍然无法实现,并且restorecond是不可能的 – 唯一的解决方法是在创build后在文件上运行restorecon的后期修复。
即使是更新的命名文件转换也有问题,因为最终它不支持globbing或regex,这严重限制了它的function,以专门命名的文件(如.htaccess)。
就目前而言,没有内核机制像restorecon及其正则expression式正确标记文件那样灵活。
在文件创build时正确标记的问题在Fedora 16中被称为文件名转换 (尽pipe你也可以将其命名为“命名文件转换”),其定义基本上是这样的:
通过文件名转换function,策略编写者可以编写考虑文件名的规则,而不是文件path。 这是文件path的基本名称。 由于内核在创build对象时知道包含目录的标签,创build对象的进程标签和对象名称。 我们现在可以编写一个策略规则,指出如果unconfined_t进程在名为etc_t的目录中创build名为resolv.conf的文件,则该文件应该标记为resolv.conf。
众所周知,创build对象时被标记的方式可能因创build对象的过程而异(以cp vs mv为例)。 另外,标签对象的默认方式是通过inheritance:对象获得父目录的标签。
虽然这很方便,但并不总是正确的,系统pipe理员必须使用restorecon + restorecond + semanage fcontext -a -t (的组合)手动更正这种情况。
这是问题名称文件转换尝试更正,通过让
策略编写者可以通过在策略中编写一个规则来覆盖这个规则,如果一个types为a_t的进程在一个名为b_t的目录中创build一个“file”类的对象,该对象将被创build为c_t。
显然,自定义位置不存在已命名的文件转换。 你可以find现有的,例如:
# sesearch -ASCT -s unconfined_t | grep Found ... Found XX named file transition filename_trans: ...
因此,为了解决您的问题,您需要事先知道哪个用户(SELinux用户)将创build哪个文件/目录以及在哪里,然后编写包括文件转换的自定义策略。 在上面链接的Fedora项目wiki页面中有几个例子。
这不是一个问题,你只是从错误的方向接近它。
如果你想要自己的文件上下文,只需使用semanage fcontext创build自己的文件上下文。 这确实接受正则expression式。
这是一个常见的例子,用于重定位Apache服务文件的目录 :
semanage fcontext -a -t httpd_sys_content_t "/volume1/web(/.*)?"
随意适应这个你自己的需要。