SELinux

System/Linux 2012. 3. 9. 00:32




----------------------------------------------------------------------
SELinux 
----------------------------------------------------------------------
각종 리눅스관련 트러블슈팅을 처리하다보면 공부해야할것들이 참 많다. 
요즘 자주 거론되는 문제가 SELinux 관련된 문제들인데, SELinux 라면 아직 못들어본 사람이 꽤 많이 있을것이다. 

SELinux의 내부적인 구현원리 같은 부분은 이 문서에 다루고자 하는 내용이 아니다. 
SELinux의 아키텍처나 코드에 대한 부분을 더 많이 알기위해서는 IBM의 기술문서
(http://www-128.ibm.com/developerworks/kr/library/l-selinux/index.html) 을 참고하거나 
NSA의 홈페이지(http://www.nsa.gov/selinux/)등를 참고하기 바란다. 

필자는 단지 여러분이 시스템을 관리하면서 새롭게 만나게되는 SELinux에 관련된 문제를 이문서를 통해서 해결할수 있기를 바랄뿐이다. 

작성자 : 김형채 



차례 

1. SELInux(Security-Enhanced Linux)란?                       
2. SELinux 정책이란 무엇인가?                                 
3. SELinux 설치여부 확인                                      
4. SELinux 기본설정 - /etc/sysconfig/selinux                  
5. SELinux 서비스 설정 - setenforce                           
6. SELinux 서비스 설정 - chcon                                
7. SELinux 서비스 설정 - setsebool                            
8. 사용중인 정책을 교체하는 방법은?                           
9. SELinux LOG                                                
10. Audit2allow                                               
11. avc: denied                                               
12. 참고문헌 또는 URL                                            

----------------------------------------------------------------------
1. SELInux(Security-Enhanced Linux) 란?  
----------------------------------------------------------------------
SELinux 란 미 국가 보안국 (U.S. National Security Agency)리 오픈소스커뮤니티에 릴리즈한 Linux의 보안 강화 버전(코드 포함)으로서 리눅스 보안 모듈 구조체(Linux Security Modules(LSM) framework)를 이용하여 리눅스 커널에 의무 접근 제어(Mandatory Access Control - MAC)를 구현하는 것이다. Fedora Core3부터 기본으로 적용되기 시작하였고, 현재 대부분의 최신 리눅스 배포판에서 지원되고있다. 

SELinux에 대한 이해를 돕기위해서 DAC, MAC를 잠깐 이야기 해보자. 

표준 리눅스 보안은 Discretionary Access Control - DAC 모델을 따른다. 
DAC 모델에서, 파일과 자원에 대한 결정권은 오직 해당 객체(objects)의 사용자(user id)에게 있고 소유권(ownership)에 따라 이뤄진다. 
각 사용자와 그 사용자에 의해 실행된 프로그램은 자기에게 할당된 객체에 대해 전적으로 자유재량권을 갖는다. 
이러한 상황에서는, 악의 있는 일반 혹은 루트 사용자(예로, setuid와 setgid)가 실행시킨 결함이 있는 소프트웨어를 통해 주어진 객체로 원하는 어떠한 일을 해도 막아낼 방법이 없으며 보안 정책을 시스템 전체에 걸쳐 시행되도록 할 방법이 없다. 

반면에 SELinux하에서 MAC는 모든 주체(subjects - 사용자, 프로그램, 프로세스)와 객체(파일, 디바이스)에 대해서 국부적으로 허가(granular permissions)해 줄 수 있다. 
응용프로그램에서 불필요한 부분은 제외하고 오직 필요한 기능에 대해서만 사용 권한을 안전하게 부여하는것이 가능하다. 

SELinux는 모든 주체 (사용자, 프로그램, 프로세스) 및 객체 (파일과 장치)에 각각 다른 권한을 부여할 수 있게 해줍니다. 
따라서 사용자는 한 응용 프로그램에게 그 프로그램이 제대로 작동하는데 필요한 권한만 안전하게 부여할 수 있다. 


----------------------------------------------------------------------
2. SELinux 정책이란 무엇인가? 
----------------------------------------------------------------------
SELinux 정책은 사용자, 프로그램, 프로세스 그리고 이들의 동작 대상인 파일과 디바이스를 포함한 시스템 전체, 즉, 모든 주체와 객체에 대한 접근 허가(access permissions)를 포함한 패키지를 이야기한다. 
페도라에서 사용가능한 정책 패키지는 strict , targeted 두가지가 있다. 

페도라코어에서 SELinux 정책으로 strict policy 를 적용함으로 인해서 다양한 사용자들이 많은 문제점을 일으킴으로 인해서(일반사용자들이 SELinux를 사용하기 위해서는 수준높은 전문기술이 필요하다) 현재 RHEL4 에서는 보다 완화된 정책패키지 targeted poicy 가 설치시 기본으로 제공된다. 

targeted policy는 자주 문제시되는 부분들만 우선적으로 적용시키고, 나머지는 표준 리눅스 보안과 동일하게 운영되도록 적용한 정책이다. 

현재, targeted policy 에서는 dhcpd, httpd(apache.te), named, nscd, ntpd, portmap, snmpd, squid 그리고 syslogd 데몬에 대해서 관리한다. 이 데몬들에 대한 정책 파일은 /etc/selinux/targeted/src/policy/domains/program에서 찾을 수 있다. 


---------------------------------------------------------------------- 
3. SELinux 설치여부 확인 
----------------------------------------------------------------------
SELinux 를 사용하고 있는지를 확인하는 방법은 보안문맥을 확인하는 방법으로 알 수 있다. 
파일, 사용자, 프로세스등의 문맥을 확인할 때는 -Z 라는 새 옵션을 이용해서 확인할 수 있다. 

ls -lZ /etc/selinux 

-rw-r--r--  root    root   system_u:object_r:selinux_config_t config 
drwxr-xr-x  root    root   system_u:object_r:selinux_config_t targeted 


-Z옵션을 이용해서 보안문맥을 보여주는데 이 결과를 통해서 "system_u" 사용자, "object_r" 역할,  "selinux_config_t" 타입을 확인할수 있다. 이런 문맥으로 SELinux의 정책에 비교해서 허용하거나 거부하게 되므로 문맥이 확인가능하다면 SELinux 를 사용중인 것이다.. 

파일 이외에 프로세스와 사용자에도 각각 아래처럼 보안문맥을 확인할수 있다 


root@example# ps axZ | grep squid 
user_u:system_r:squid_t          3912 ?        Ss     0:00 squid -D 
user_u:system_r:squid_t          3915 ?        S      9:10 (squid) -D 
user_u:system_r:squid_t          3916 ?        Ss     0:01 (unlinkd) 


root@example# id 
uid=0(root) 
gid=0(root)groups=0(root),1(bin),2(daemon),3(sys),4(adm),6(disk),10(wheel) 
context=root:system_r:unconfined_t 


RedHat 의 SELinux 패키지 경우에는 sestatus -v 라는 명령을 이용해서 현재 SELinux의 사용상태를 아래와 같이 확인할수 있다. 

[root@w ~]# sestatus -v 
SELinux status:         enabled
SELinuxfs mount:        /selinux
Current mode:           enforcing
Mode from config file:  enforcing
Policy version:         18
Policy from config file:targeted

Policy booleans:
allow_syslog_to_console inactive
allow_ypbind            inactive
dhcpd_disable_trans     inactive
httpd_builtin_scripting active
httpd_disable_trans     inactive
httpd_enable_cgi        active
httpd_enable_homedirs   active
httpd_ssi_exec          active
httpd_tty_comm          inactive
httpd_unified           active
mysqld_disable_trans    inactive
named_disable_trans     inactive
named_write_master_zonesinactive
nscd_disable_trans      inactive
ntpd_disable_trans      inactive
pegasus_disable_trans   inactive
portmap_disable_trans   inactive
postgresql_disable_transinactive
snmpd_disable_trans     inactive
squid_disable_trans     inactive
syslogd_disable_trans   inactive
use_nfs_home_dirs       inactive
use_samba_home_dirs     inactive
use_syslogng            inactive
winbind_disable_trans   inactive
ypbind_disable_trans    inactive

Process contexts:
Current context:        root:system_r:unconfined_t
Init context:           user_u:system_r:unconfined_t
/sbin/mingetty          user_u:system_r:unconfined_t
/usr/sbin/sshd          user_u:system_r:initrc_t

File contexts:
Controlling term:       root:object_r:initrc_devpts_t
/etc/passwd             system_u:object_r:etc_t
/etc/shadow             system_u:object_r:shadow_t
/bin/bash               system_u:object_r:shell_exec_t
/bin/login              system_u:object_r:bin_t
/bin/sh                 system_u:object_r:bin_t -> system_u:object_r:shell_exec_t
/sbin/agetty            system_u:object_r:sbin_t
/sbin/init              system_u:object_r:init_exec_t
/sbin/mingetty          system_u:object_r:sbin_t
/usr/sbin/sshd          system_u:object_r:sbin_t
/lib/libc.so.6          system_u:object_r:lib_t -> system_u:object_r:shlib_t
/lib/ld-linux.so.2      system_u:object_r:lib_t -> system_u:object_r:ld_so_t


----------------------------------------------------------------------
4 . SELinux 기본설정 - /etc/sysconfig/selinux  
----------------------------------------------------------------------
배포판마다 서비스 설정방법은 차이가 있다. 
필자가 테스트한 레드햇과 페도라 배포판에서는 /etc/sysconfig/selinux 파일에서 SELinux 의 사용가능한 모드를 설정한다. 

/etc/sysconfig/selinux 파일의 내용 

# This file controls the state of SELinux on the system. 
# SELINUX= can take one of these three values: 
#       enforcing - SELinux security policy is enforced. 
#       permissive - SELinux prints warnings instead of enforcing. 
#       disabled - SELinux is fully disabled. 
SELINUX=enforcing 
# SELINUXTYPE= type of policy in use. Possible values are: 
#       targeted - Only targeted network daemons are protected. 
#       strict - Full SELinux protection. 
SELINUXTYPE=targeted 

이 파일에는 두부분의 설정이 있는데 SELINUX 의 상태(enforcing, permissive, disabled)를 설정하는 부분과 활성화시킬 보안정책(strict 또는 targeted 중 하나)을 결정하는 SELINUXTYPE 이라는 부분이 있다. 

disabled ? SELinux 보안 제어를 사용하지 않으려면 disalbed 옵션을 선택한다. 
disalbed 설정은 보안 제어 기능을 끄고 시스템이 보안 정책을 사용하지 않도록 설정한다. 

permissive ? 이것을 선택하면 서비스 거부 메시지를 통보받을 수 있다. permissive 상태로 설정하면 자료와 프로그램에 이름을 할당한 후 로그를 기록하지만 보안 정책을 사용하지는 않는다. permissive 상태는 SELinux를 처음 접하는 경우 처음부터 이 기능을 완전히 활성화하지 않고 우선 이 정책을 사용해서 일반 시스템 작업시 어떠한 영향을 미치는지 알아보려는 경우 좋은 시작점이 될 수 있다. 그러나 경고 옵션을 선택시 가끔씩 보안경고 대상이 아닌 것을 경고 대상으로 탐지하는 오류(false positive)나 경고 대상인 것을 탐지하지 않는 오류(false negative)가 발생할 가능성도 있으니 주의가 필요하다. 

enforcing ? SELinux를 완전히 활성화하시려면 enforcing 옵션을 선택하자. 
enforcing 옵션을 선택하면 추가 시스템 보안을 위해 모든 보안 정책 (예, 허가가 없는 사용자가 특정한 파일이나 프로그램에 접근하는 것을 거부하기)을 사용한다. SELinux가 완전히 실행되어도 아무런 지장을 받지않고 일반적인 시스템 작업을 수행할 수 있다고 자신하시경우 이 옵션을 선택한다. 

----------------------------------------------------------------------
5. SELinux 서비스 설정 - setenforce  
----------------------------------------------------------------------
SELinux의 서비스 상태를 변경해야 하는 필요가 있을때는 직접 /etc/sysconfig/selinux 파일에서 SELINUX=enforcing , 또는 SELINUX=permissive 처럼 수정해서 변경하는 방법도 있지만 setenforce 라는 명령어를 이용할수 있다. 
"setenforce 0" 이라고 명령을 내리는것은  SELINUX=permissive 와 동일한 결과이며, "setenforce 1" 은 enforcing 모드를 의미한다. 
시스템에서 SELinux 를 완전히 사용하지 않으려면 /etc/sysconfig/selinux 파일에서 SELINUX=disabled 처럼 설정하거나 시스템 부팅시에 부트로더의 파라미터로 selinux=0 이라고 주고 부팅하면 된다. (grub 을 사용하는 경우라면 grub 화면에서 e 를 누르고 편집모드로 들어간뒤에 kernel 줄의 맨 뒤에 selinux=0 을 적어주고 ESC, 그리고 b 를 눌러서 부팅하면 된다..) 


sentenforce 명령은 sysadm_r 권한을 갖고 수행해야 한다; 그러기 위해, newrole 명령을 사용하거나, 아니면, su -를 사용하여 root 로 사용자 전환을 하면, 자동으로 sysadm_r 권한을 얻을 수 있다. 

----------------------------------------------------------------------
6. SELinux 서비스 설정 - chcon  
----------------------------------------------------------------------
SELinux 의 보안문맥을 변경해야 하는 경우에는 chcon 이라는 명령을 사용할수 있다. 
아파치를 사용중에 분명히 디렉토리를 생성했는데도 에러가 난다면 아래처럼 http_user_content_t 를 해당 DocumentRoot 에 적용해줌으로 해결해 줄수있다. 

chcon -R -t httpd_user_content_t /home/사용자계정/public_html 

----------------------------------------------------------------------
7. SELinux 서비스 설정 - setsebool 
----------------------------------------------------------------------
[root@ns ~]# cat /etc/selinux/targeted/booleans 
allow_ypbind=1 
dhcpd_disable_trans=0 
httpd_disable_trans=1 
httpd_enable_cgi=1 
httpd_enable_homedirs=1 
httpd_ssi_exec=1 
httpd_tty_comm=0 
httpd_unified=1 
mysqld_disable_trans=0 
named_disable_trans=1 
named_write_master_zones=1 
nscd_disable_trans=1 
ntpd_disable_trans=0 
portmap_disable_trans=0 
postgresql_disable_trans=0 
snmpd_disable_trans=0 
squid_disable_trans=0 
syslogd_disable_trans=0 
winbind_disable_trans=0 
ypbind_disable_trans=0 

  
RHEL4의 경우 전환가능한 시스템의 SELinux 설정값들을 나타내는 파일은 /etc/selinux/targeted/booleans 파일이다. 
파일안의 각 항목은 system-config-securitylevel 이라는 어플리케이션이나 setsebool 이라는 명령을 이용해서 변경시킬수 있으며 setsebools 을 이용하는 경우 -P 옵션을 사용하지 않으면 설정파일은 변경되지 않고 현재의 설정만 바뀌지만 -P 옵션을 같이 사용하면 /etc/selinux/targeted/booleans 파일의 내용까지 같이 변경되어 시스템 리부팅후에도 적용된다


----------------------------------------------------------------------
8. 사용중인 정책을 교체하는 방법은? 
----------------------------------------------------------------------
정책 교체는 가볍게 취할 사안이 아니다. 

연구 목적으로 시험 장비(test machine)에서 새 정책을 시도하는 이외, 생산 시스템(production system)에서는 다른 정책으로 교체하기 전에 현황을 심각하게 고려해야 한다. 

교체 작업은 간단하다. 
이는 매우 안전한 방법이지만, 우선 시험 시스템에서 일차 시도해 보는 것이 바람직하다. 

한 가지 방법은 system-config-securitylevel을 사용하여 정책을 바꾸고 재명명(relabel)하도록 파일 시스템을 설정하는 것이다. 

수작업 절차는 다음과 같다: 

(1) /etc/selinux/config을 편집하고 SELINUXTYPE=policyname으로 정책 유형을 바꾼다. 
(2) 재부팅하여 돌아올 수 있는 지 확인하기위해, SELINUX=permissive모드로 설정한다. 
이렇게 하면, SELinux는 정확한 정책하에서 가동될 것이지만, 만일 부정확한 파일 문맥 명명(labeling)과 같은 문제가 있으면 로그인하도록 할 것이다. 
(3) sysadm_r 역할을 갖춘 root로 파일 시스템을 재명명한다(relabel): 
id -Z 
root:sysadm_r:sysadm_t 
fixfiles relabel 

옵션 -l /path/to/logfile을 사용하여 표준 출력으로 로그를 볼 수 있고, 옵션 -o /path/to/file을 사용하여 검토(checked)되거나 재명명(relabel ed)된 모든 파일 리스트를 저장할 수 있다. 

(4) 시스템을 재부팅한다. 
새 정책하에서의 재시작은 모든 시스템 프로세스가 적절한 문맥에서 시작되고 정책 변경으로 인한 모든 문제가 드러나게 한다. 

(5) sestatus -v 명령으로 발효된 변경사항을 확인한다. 
Permissive 모드로 가동된 새 시스템에서, avc: denied 메시지를 /var/log/messages에서 확인한다. 
이들은 새 정책하에 문제없이 시스템이 가동되도록 해결해야 할 문제들을 표시해 준다. 

(6) 새 정책하에서 시스템이 만족스럽게 돌아갈 때, SELINUX=enforcing 으로 바꿔 실행 권한을 부여한다. 
실시간에 enforcing을 활성화 시키기 위해 재부팅하거나 setenforce 1 을 실행한다. 


----------------------------------------------------------------------
9. SELinux LOG  
----------------------------------------------------------------------
   SELinux 의 로그는 /var/log/messages 파일에 아래처럼 나타난다 

   kernel: audit(1114070701.193:0): avc:  denied  { read } for  pid=24216 
   exe=/usr/libexec/mysqld name=mysql dev=cciss/c0d0p6 ino=16408 
   scontext=user_u:system_r:mysqld_t tcontext=root:object_r:var_lib_t 
   tclass=dir 


이 로그는 아래와 같이 해석할수 있다. 


- 읽기 요청이 거부되었다. 

- PID 24216을 가진 프로세스가 read를 시도한다 

- 해당프로세스는 /usr/libexec/mysqld 이다 

- /dev/cciss/c0d0p6 에서 작동되고 있다 

- inode 는 16408이다. 

- 프로세스의 SELinux 문맥은 user_u:system_r:mysqld_t 이다. 

- tcontext=root:object_r:var_lib_t : 이파일이 읽기를 시도하는 파일은 var_lib_t 타입의 root 소유파일이다 




SELinux LOG 각 항목의 의미 

audit(timestamp) -- This field states that it's an audit message from SELinux and that it was logged at timestamp time (in seconds since Jan. 1st, 1970). 

avc -- This message was from the SELinux access vector cache. Pretty much every message you are likely to see is from this cache. 

denied | accepted -- This field indicates whether the action was denied or accepted. You may see logs of accepted messages in some cases (like reloading the policy). 

{ read | write | unlink | ... } -- This field shows the type of action that was attempted, such as reading a file, writing, unlinking, loading policy, etc. 

for pid= -- This is the process ID that attempted the action. 
exe= -- This is the path to the executable that started the process. 
name= -- This is the name of the target on which the action was attempted. 
dev= -- This is the device on which the target file is located. 
ino= -- This is the inode of the target of the action. 
scontext= -- This is the process's security context. This contains user, role, and type. 
tcontext= -- This is the security context of the target of this action, for example, the file, directory, etc. 
tclass= -- This is the class of the target object, such as directory, file, device node, or something else. 

----------------------------------------------------------------------
10 . Audit2allow  
----------------------------------------------------------------------
정책 작성자에게 유용한 도구는 /usr/bin/audit2allow 인데 이것은 /var/log/messages의  avc 메시지를 SELinux에 의해 사용될 수 있는 규칙으로 번역해준다. 사용이 불가능하다면 policycoreutils 패키지에 속해있으므로 yum install policycoreutils 처럼 설치 가능하다. 

audit2allow명령은 세가지 방법으로 입력을 받을 수 있다. 기본은 표준입력 (stdin)이다. -i 옵션을 사용하면 /var/log/messages 로부터 입력을 읽을 수 있고 -d옵션을 사용하면 dmesg 출력으로부터 입력을 읽을 수 있다.

----------------------------------------------------------------------
11 . avc: denied  
---------------------------------------------------------------------- 
이 메시지는 현재 실행된 SELinux 정책이 그 응용프로그램의 동작을 허락하지 않기 때문이다. 이러한 일에는 여러 가지 사유가 존재한다. 

첫째, 응용프로그램이 접근하려는 파일중 하나가 잘못 명명되어있을 수 있다. 
만일 AVC 메시지가 특정 파일을 참조한다면, ls -alZ /path/to/file 을 수행하여 현재 참조하는 파일명(current label)을 조사해 보라. 
만일 그것이 잘못되어 보이면, restorecon -v /path/to/file 을 시도해보라. 
만일 파일과 관련된 매우 많 은 거부(denials) 상황이 존재하면, fixfiles relabel 을 수행하거나, 반복적으로 디렉토리 경로를 재명명하기 위해서 -R옵션과 함께 restorecon 을 수행하고 싶을 수 있다. 

다른 때에는, 거부(denials) 현상은 정책에 의해 거부되도록 프로그램에 설정을 바꿔서 발생될 수 있다. 
예를 들면, 만일 Apache를 8800포트로 바꾸면, 보안 정책, apache.te,도 관련하여 바꿔야 할 필요가 생긴다. 정책 작성에 관한 상세한 정보가 필요하면, 외부연결 리스트(External Link List)를 보라. 


----------------------------------------------------------------------
12 . 참고문헌 또는 URL 
----------------------------------------------------------------------
Home of the SELinux project -- http://www.nsa.gov/selinux/ 
The Un-Official SELinux FAQ -- http://www.crypt.gen.nz/selinux/faq.html 
SELinux link zoo -- http://www.crypt.gen.nz/selinux/links.html 
Ubuntu Linux SELinux pages -- https://www.ubuntulinux.org/wiki/SELinux 
2005.8 Sys Admin Magazine -- http://www.samag.com/documents/s=9820/sam0508a/0508a.htm 
NSA SELinux FAQ ? http://www.nsa.gov/selinux/info/faq.cfm 
SELinux community page ? http://selinux.sourceforge.net 
UnOfficial FAQ ? http://www.crypt.gen.nz/selinux/faq.html 
Writing SE Linux policy HOWTO ? https://sourceforge.net/docman/display_doc.php?docid=21959&group_id=21266 
Getting Started with SE Linux HOWTO: the new SE Linux (Debian) ? https://sourceforge.net/docman/display_doc.php?docid=20372&group_id=21266


출처 -  http://www.rootman.co.kr/bbs/zboard.php?id=linux&no=1608 






Tuning Your SELinux Policy with Audit2allow(Audit2allow 로 SELinux 정책 튜닝하기)
2005년 8월호의 내용입니다.

출처 : http://www.chtla.com/stories.php?story=05/07/26/5732021

 

Fedora 코어3엔 6개월동안 기본적으로 Security Enhanced Linux (SELinux) 를 탑재하고 있다. 
SELinux는 사용자와 그룹, root가 가지는 일반적인 접근보다 휠씬 낫은 분리된 특권을 가지고 있다. 
기본적인 SELinux의 설정은 몇몇 사용자에게는 쉬게 보이겠지만, 다른 사용자들은 sendmail.cf 파일이 더 쉽게 보여질것이다.(sendmail.cf 파일을 설정하는 것이 더 쉬워 보일것이다.) 
여기서는 audit2allow 툴을 이용해 필요한 정책을 단계적으로 설정하는 것을 보여줄것이다. 


SELinux란? 

SELinux는 프로세스의 접근제어명령(Mandatory Access Controls) 억제하고, 기록하고, 탐지에 필요한 고리(hook)를 제공하는 커널 패치(2.6.0-test 시리즈에서 kernel.org의 메인커널로 흡수된)이다. 
허가와 거부하는 것을 컨트롤 하는 룰은 정책으로 구성된다. 이 정책은 SELinux 프레임워크 아래 관리되는 일들을 명시한 룰들을 포함하고 있다. 

전통적인(지금까지 사용되어진) 퍼미션 모델은 사용자, 그룹, unix 파일 허가로 구성되고, 이 모델은 사용자와 그룹이 파일을 읽고, 쓰고, 실행하는 것을 제어할수 있다. 
하지만 SELinux는 사용자와 역활,타입으로 더 많은(다양한) 퍼미션을 제공하고 있다. 

예를 들어, 전통적인 퍼미션 모델에서 특정포트(1024 포트 밑으로)를 listen 하기 위해서는 해당 프로세스에게 root 권한을 주어야 한다. 
이 프로세스가 권한을 가지게 되면, root로써 모든 권한을 행할수 있게 된다. 
하지만 SELinux 모델에서는 특정 포트를 특정 서버에게만 권한을 주어 접근하게 할수 있으며, 그외는 허용하지 않는다. 

그럼 어떤 리눅스가 SELinux를 지원하는가? 
아래 나열된 배포판을 SELinux를 지원하고 있다. 

- Fedora Core 2 
- Fedora Core 3 
- Red Hat Enterprise Linux 4 
- CentOS 4 
- Debian unstable (kernel support) 
- Hardened Gentoo project 
- SUSE 9.x (kernel support) 
- Ubuntu 

그외 추가로 다른 배포판에서도 SELinux 를 지원할 수도 있다. 그외 배포판은 시스템 문서를 참조해 보자.

왜 SELinux 인가?

SELinux 사용하면 리눅스 서버의 보안을 높일수 있다.
프로세스의 제한적인(?) 콘드롤을 지정할수 있기에 취약점이 있는 소프트웨어를 많은 공격(exploit)으로 부터 막을수 있다.

예를 들어, 일반적인 데몬이 실행되고 있다면 하면.. 특정 tcp 포트를 listen하게 되고, 파일의 입력을 저장하기 위해 프로세스에게 요청하면 config 파일을 읽고 난뒤 입력되는 것의 구문을 조사하고, 소켓에게 그 결과를 반환할것이다.

전형적인 권한(퍼미션) 모델에서는 데몬은 tcp를 열기 위해 root 권한을 가지게 되고, listen 상태로 대기하게 된다. (물론 소켓생성후 root 권한을 없어지는 경우도 있지만)
일반적으로 데몬은 실행한 유저의 권한을 가지고 실행을 하게 된다.
그래서 그 사용자가 소유한 디렉토리가 있다면 어떤 파일이든 읽거나 쓸수 있게 된다. 그 유저의 권한으로 실행되는 parsing process(?) 까지도.

데몬 실행시 root 권한으로 실행을 되게 되면 root가 할수 있는 어떤 것이라도 프로세스는 할수 있다는 것이다.
이때 읽거나 쓰는데 문제가 발생한다면 사용자가 읽을수 있는 파일을 인터넷에 노출시키거나, 다른 프로세스의 파일을 덮었는 일도 있을수 있을것이다.
또는 parsing process(?)에 문제가 발생한다면, 프로세스는 특정 프로세스의 사용자 권한(원격접근이 가능한 권한을 가진)으로 실행이 되거나, 서버에 위헙이 될수 있는 명령어도 실행할수 있게 된다.

이제는 똑같은 상황을 SELinux 하에서 생각해 보자.
우선 데몬에 다른 사용자가는 허가하지 않고, 특정 tcp 포트를 열도록 정책을 설정할 것이다.
프로세스(데몬)는 절대로 root로 실행하지 않고, 허가된 타입의 특정 파일만을 읽고 쓸수 있게 될것이다.
또한 parsing process 는 특정 타입의 파일을 읽고, 쓸수만 있으며, 어떤 shell 명령어도 실행할수 없게 된다.
서버와 parser(?)는 /tmp 디렉토리(이와 비슷한 디렉토리도)밑의 파일은 읽고, 쓸수가 없게 된다. 

이처럼 SELinux를 사용하게 되면 프로그램 에러나 설정문제등으로 인해 위험이 노출되는 것을 줄일수 있다.
SELinux를 사용하더라도 시스템 업데이트나 보안에 대한 좋은 습관등은 갖추고 있어야 한다.
SELinux는 단지 시스템 안정하도록 도와주는 많은 것들중 하나일 뿐음을 잊지 말자.

안전한가?

SELinux는 메인 리눅스 커널로 흡수(포함)되었고, 많은 이들로 부터 검증을 받았다.
소스코드는 GPL로 발표(릴리즈)되었으며, 모든 코드는 검증이 가능하다.
몇몇 사용자들은 NSA가 시스템의 백도어로 SELinux를 사용할수 있다는 의문을 제기하기도 했지만, 백도어는 발견되지 않았다.

파일, 프로세스, 사용자

SELinux는 파일과 프로세스에 "보안 상태(security context)"를 구성하게 된다.
이것은 파일 시스템에서 확장 파일시스템 속성에 의해 쓴여진 파일을 말하는 것이며, 시스템의 파일시스템은 확장속성을 꼭 지원해야 한다.
페도라나 레드햇 배포판에서 ls 명령어는 새로운 옵션인 -- -Z 로 파일의 보안상태를 보여줄것이다.
예를 보자.

# ls -lZ /etc/selinux
-rw-r--r--    root    root   system_u:object_r:selinux_config_t config
drwxr-xr-x  root    root   system_u:object_r:selinux_config_t targeted

이것은 /etc/selinux 밑의 파일과 디렉토리를 출력한 것이다.
보안상태(security context)는 system_u가 사용자(user)이고, object_r은 역활(role)이고, selinux_config_t는 타입(type)을 표시한 것이다.
이처럼 사용자/역활/타입을 체크해 현재 SELinux의 정책과 비교하여 시스템에서 허가할지 거부할지를 결정하게 되는것이다.

역시 ps 명령어 사용시에는 -Z 옵션을 사용하면 해당 프로세스의 보안상태(security context)를 볼수 있다.
예를 들어 squid 웹 프록시 데몬이 특정 포트를 오픈해 놓은 상태라면(다른 사용자는 접근할수 없는 상태) 아래와 같은 결과를 볼수 있다.

# ps axZ | grep squid
user_u:system_r:squid_t          3912 ?        Ss     0:00 squid -D
user_u:system_r:squid_t          3915 ?        S      9:10 (squid) -D
user_u:system_r:squid_t          3916 ?        Ss     0:01 (unlinkd)

위에서도 squid 프로세스의 보안상태(security context)를 볼수 있다.
사용자는 user_u이고, 역활은 system_r이고, 타입은 squid_t이다.

유저는 해당 유저가 무엇을 할수 있는지 역활(role)이 지정되어 있다.
역활(role)에는 해당 유저가 웹서버를 실행하거나 ping 명령어 같은 것을 실행할수 있도록 지정할수 있다.
root로 로그인한 상태에서 id 명령어를 실행하면 아래와 같이 출력하게 된다.

# id
uid=0(root)
gid=0(root)groups=0(root),1(bin),2(daemon),3(sys),4(adm),6(disk),10(wheel)
context=root:system_r:unconfined_t

역시 root도 system_r 역활과 unconfined_t 타입이라는 것을 알수 있다.

설정하기

레드햇과 페도라에서 SELinux 설정은(사용할것인지, 어떤 방식으로 실행을 할것인지를) /etc/sysconfig/selinux 파일로 한다.
다른 배포판은 경로가 틀릴것이다.
아래는 페도라3의 /etc/sysconfig/selinux 파일의 내용이다.

# This file controls the state of SELinux on the system.
# SELINUX= can take one of these three values:
#       enforcing - SELinux security policy is enforced.
#       permissive - SELinux prints warnings instead of enforcing.
#       disabled - SELinux is fully disabled.
SELINUX=enforcing
# SELINUXTYPE= type of policy in use. Possible values are:
#       targeted - Only targeted network daemons are protected.
#       strict - Full SELinux protection.
SELINUXTYPE=targeted

SELINUX 지시자 설정은 비교적 간단하다.
SELinux의 정책을 실행할것인지, 정책을 실행하는 동안 간단히 기록을 할것인지, 아니면 사용하지 않을것인지를 결정한다.
enforcing 을 입력하게 된다면, 정책이 실행될것이다.
다른 단어를 사용할 경우, 정책에서 액션을 지정하지 않았다면 프로세스는 거부를 하게 될것이다.

SELINUXTYPE 은 어떤 정책을 활성화 할것인지를 결정한다.
페도라 코어 3 에서는 두가지 정책을 선택할수 있다.(targeted와 strict)

targeted정책은 몇몇 프로세스에 관한 정책으로, 정책의 범위에서 벗어나 리스트되지 않는 것을 허가하고,
strict 정책은 대부분의 프로세스를 위한 정책으로, 명확히 허가된 것이 아닌라면 거부하게 된다.

서비스를 거의 하지 않거나, 기본설정에서 변경이 거의 없는 상태로 서비스 하는 서버라면, strict 정책을 사용하고, 
그렇지 않다면 targeted 정책을 사용하는 것이 SELinux의 사용이점을 제대로 사용할수 있다.
예를 들어 targeted 정책을 사용한다면, 정책에서 지정된 프로세스들은 SELinux에 의해 감시를 받고, 그외 프로세스는 허가된다.

setenforce 명령어로 enforcing 에서 permissive 방식으로 변경할수도 있다.
setenforce 0 은 permissive 방식이고, setenforce 1은 enforcing 방식이다.
부팅시 SELinux를 비활성화 하면서 커널 명령라인에 selinux=0 를 입력하면 된다.

정책을 변경하기 위해서는 정책 소스 패키지가 꼭 있어야 한다.
페도라 코어3일 경우엔 selinux-policy-targeted-sources 와 selinux-policy-strict-sources 가 소스패키지이다.
이 패키지를 인스톨하려면 아래와 같이 명령어를 주면 된다.

# yum install selinux-policy-targeted-sources selinux-policy-strict-sources 

로그기록

SELinux 로그는 프로세스가 거부 되었을때 기록을 한다.(허거되었을때도 기록이 가능하지만)
기본정책이 거부를 허가로 변경해서도 로그를 기록할수도 있다.
아래는 SELinux의 로그 기록이다.(기본적으로 /var/log/messages에 기록된다.)

kernel: audit(1114070701.193:0): avc:  denied  { read } for  pid=24216 exe=/usr/libexec/mysqld name=mysql dev=cciss/c0d0p6 ino=16408 scontext=user_u:system_r:mysqld_t tcontext=root:object_r:var_lib_t tclass=dir

로그를 분석해 보면..

우선 읽기 요구를 거부하고 있다. (denied {read})
읽기 요구를 하는 프로셋의 ID는 24216이다. (for pid=24216)
프로세스 이름은 /usr/libexec/mysqld 이고, (exe=/usr/libexec/mysql name=mysql)
액션의 타켓은 /dev/cciss/c0d0p6 장치에서 실행되고 있다.)
액션 타켓의 inode는 16408이고, (ino=16408)
프로세스의 SELinux context는 user이고, mysqld 타입이다.(scontext=user_u:system_r:mysqld_t)
읽으려고 하는 파일은 var_lib_t 타입의 루트 소유의 파일이다. (tcontext=root:object_r:var_lib_t)

SELinux의 로그 엔트리의 필드를 살펴보자.

audit(timestamp) : 이 필드는 SELinux의 검사 메세지이며, 타임 스탬프 형식으로 기록한다.
avc : SELinux 벡터 캐시 액세스를 나타나며, 거의 모든 기록은 이 캐시이다.
denied | accepted : 이 필드는 해당 액션이 허가되었는지 거부되었는지를 나타낸다. 종종 허가된 메세지를 볼수도 있다.(정책을 리로드할 경우에)
{ read | write | unlink | ... } : 이 필드는 파일을 읽거나, 쓰거나, unlink하거나, 정책을 로딩하거나 등의 액션의 종류을 출력한다.
for pid= : 접근하는 액션의 프로세스 ID를 나타낸다.
exe= : 실행되는 프로세스의 경로를 나타낸다.
name= : 액션을 시도하는 타켓의 이름을 나타낸다.
dev= : 타켓 파일이 위치한 디바이스를 나타낸다.
ino= : 액션 타켓의 inode를 나타낸다.
scontext= : 프로세스의 보안상태(문맥)을 나타낸다. 사용자, 규칙, 타입을 가지고 있다.
tcontext= : 액션 타켓(파일이나 디렉토리등에 사용되는)의 보안상태(문맥)을 나타낸다. 
tclass= : 타켓 오브젝트(디렉토리, 파일, 디바이스, 노드같은)의 클래스를 나타낸다.

다른 로그를 살펴보자.

kernel: audit(1114800386.039:0): avc:  granted  { load_policy } for
pid=12589 exe=/usr/sbin/load_policy
scontext=root:system_r:unconfined_t
tcontext=system_u:object_r:security_t tclass=security

위 로그는 root에 의해 정책이 리로드 되었음을 알수 있다.(아마 make load 명령어를 사용한듯)
avc가 granted 임을 기억해 두자.

다른 예를 한번 더 보자.

kernel: audit(1114800360.543:0): avc:  denied  { unlink } for
pid=12253 exe=/usr/sbin/named name=example.com dev=hda3 ino=505301
scontext=root:system_r:named_t tcontext=root:object_r:named_zone_t
tclass=file

여기서는 example.com 파일을 named가 unlink 되는 것을 거부했다는 것을 알수 있다.
그것은 /dev/hda3 에 위치하고, inode는 505301 이다.


Audit2allow

mysqld 데몬이 읽으려고 하는 파일이 있을 경우 그 파일을 읽을수 있도록 해 주려면 정책을 어찌 추가해 주어야 할까?
위와 같이 audit 메세지를 허락된 정책라인으로 변경해 주는 audit2allow 라는 훌륭한 툴이 있다.

audit2allow는 페도라나 레드햇 기반의 배포판에 policycoreutils 라는 패키지로 포함되어 있다.
이 패키지는 아래 명령어를 실행하기 전에 인스톨 되어 있어야 한다.
설치되어 있지 않다면

# yum install policycoreutils

로 설치할수 있다.
그래서, audit2allow로 아래 라인을 흉내내어 보자.
(직접 실행을 못해 정확히 무슨 말인지 ㅡ.ㅡ; 테스트후 다시 수정도록 하겠습니다.)

allow mysqld_t var_lib_t:dir read;

이 정책은 mysqld_t 타입의 프로세스는 var_lib_t 타입의 디렉토리를 읽기를 허가한다는 말한다.
이제 정책을 세웠으니, 이것을 리눅스 커널에 로드 시켜보자. 그래야 이 액션이 허가되었음을 알수 있게 된다.
(리눅스 커널에 로드 시켜야 허락된 정책이 적용된다는 뜻이다.)

SELinux 정책소스는  /etc/selinux//src/policy 에 위치한다.
예를 들어 targeted 정책을 사용한다면, 정책 소스의 위치는 /etc/selinux/targeted/src/policy/ 이다.

해당 디렉토리를 보면 Makefile 과 함께 다양한 정책들을 볼수 있을 것이다.
로컬 정책 추가를 위해 /etc/selinux/targeted/src/policy/domains/misc/local.te 파일을 열어 위에서 audit2allow가 준 라인을 추가하자.
이제 커널의 정책을 로드하고, 체크하고, 컴파일 하기 위해 make load 를 실행하자.
그럼 아래와 비슷한 로그를 볼수 있을것이다.

Apr 21 14:34:29 linuxmachine kernel: audit(1114115669.205:0): avc:
granted  { load_policy } for  pid=7648 exe=/usr/sbin/load_policy
scontext=root:system_r:unconfined_t
tcontext=system_u:object_r:security_t tclass=security
Apr 21 14:34:29 linuxmachine kernel: security:  3 users, 4 roles,320 types, 23 bools
Apr 21 14:34:29 linuxmachine kernel: security:  53 classes, 10952 rules

 

Audit2allow 다른 옵션들

Audit2allow는 다른 여러가지 좋은 옵션을 가지고 있다.

audit2allow -l -i /var/log/messages 이처럼 audit2allow를 실행한다면, 실행시간 이후의 메세지와 정책을 리로드한 마지막 시간을 보게 될것이다.
audit2allow -d 를 사용하면, 커널의 dmesg 버퍼를 읽어서 메세지로 보여줄것이다.

복잡한 응용이나 구성을 가지고 있다면, permissive 모드로 실행해 audit2allow 로 모든 avc 메세지를 기록하거나, enforcing 모드로 실행해서 audit2allow -l 로 각각 실행한 후 출력을 체크하자.

 

정책 갱신하기

정책을 갱신할때 변경되는 것이 조절을 필요한지 아닌지 살펴봐 업데이트에 반하는 것이 있는지 체크해야 한다.
때로는 메인 정책에 포함된 관습룰(custom role)를 제거하는 결과를 초래할수도 있다.
local.te 파일만 변경했다면, make load 전에 policy.conf 파일을 grep 해서 새 정책이 있는지 체크할수 있다.

 

주의사항

필요한 룰을 추가할때는 조심하자.
마구잡이로 거부되는 것을 허가하기 위해 룰을 추가하게 되면 침략자가 이용할수 있는 어떤 것을 허가하게 될수도 있다.
정책은 전형적인 사용을 위해 바꿀때, 최소한의 맞춤(변경)이 필요할 것이다.

 

요약

Audit2allow 는 꼭 필요한 SELinux 정책을 변경할때 유용한 툴이다.
새 정책을 쓰지 않고, 거부된 정책 로그 메세지로 새 정책을 생성해 그것을 사용할수 있다.

 

참조

Home of the SELinux project -- http://www.nsa.gov/selinux/ 
The Un-Official SELinux FAQ -- http://www.crypt.gen.nz/selinux/faq.html 
SELinux link zoo -- http://www.crypt.gen.nz/selinux/links.html 
Ubuntu Linux SELinux pages -- https://www.ubuntulinux.org/wiki/SELinux

원문 : http://www.samag.com/documents/s=9820/sam0508a/0508a.htm





현재 설정 확인

#getenforce


일시적으로 끄기

#setenforce 0                


SELinux 설정        

#setenforce 1     


SElinux 끄기

# vi /etc/sysconfig/selinux

SELINUX=permissive

재 부팅









'System > Linux' 카테고리의 다른 글

linux - 소프트웨어 추가 설치하기(RPM, SOURCE CODE, YUM)  (0) 2012.03.25
Centos6에서 resolv.conf 이슈  (0) 2012.03.09
Live CD  (0) 2012.03.07
리눅스 명령어  (2) 2012.03.02
linux - LVM(Linux Volume Manager) 예제  (0) 2011.11.02
Posted by linuxism
,