กำหนดค่าให้ใช้งาน web server (httpd) ใน RHEL 7 ให้รองรับบริการในพอร์ทอื่นได้

Damrongsak Reetanon
3 min readDec 10, 2017

--

โดยปกติ httpd ใน RHEL/CentOS 7 จะให้บริการที่ tcp/80 หรือ tcp/443 โดยที่ SELinux ควบคุมให้ httpd สามารถให้บริการได้เฉพาะพอร์ทที่กำหมดไว้เท่านั้น หากผู้ดูแลระบบกำหนดค่าให้ httpd ให้บริการใน port อื่นที่ไม่ได้ถูกกำหนดให้อนุญาตโดย SELinux ผู้ดูแลระบบอาจเจอข้อผิดพลาดในขณะที่ start httpd ว่า “Permission Denied” ซึ่งสามารถกำหนด policy ของ SELinux ให้อนุญาตให้ใช้งานได้ด้วยคำสั่ง semanage ตามรายละเอียดดังนี้

  • เรียกดูสถานะของ httpd ใน RHEL/CentOS 7 ตามค่าปกติจะให้บริการที่พอร์ท 80
[root@web-server ~]# systemctl status httpd
● httpd.service - The Apache HTTP Server
Loaded: loaded (/usr/lib/systemd/system/httpd.service; enabled; vendor preset: disabled)
Active: active (running) since Sun 2017-12-10 11:13:46 +07; 54s ago
Docs: man:httpd(8)
man:apachectl(8)
Main PID: 1127 (httpd)
Status: "Total requests: 1; Current requests/sec: 0.1; Current traffic: 512 B/sec"
... truncated outputDec 10 11:13:46 web-server.localdomain systemd[1]: Starting The Apache HTTP Server...
Dec 10 11:13:46 web-server.localdomain httpd[1127]: AH00558: httpd: Could not reliably determine the server's fully qualified domain ...essage
Dec 10 11:13:46 web-server.localdomain systemd[1]: Started The Apache HTTP Server.
Hint: Some lines were ellipsized, use -l to show in full.
  • ทดลองสร้างไฟล์ index.html ใน /var/www/html และทดสอบยืนยันการใช้งานด้วยคำสั่ง curl และ คำสั่ง ss
[root@web-server ~]# echo "Hello World" > /var/www/html/index.html
[root@web-server ~]# curl http://localhost
Hello World
[root@web-server ~]# ss -tanp |grep httpd
LISTEN 0 128 :::80 :::* users:(("httpd",pid=1132,fd=4),("httpd",pid=1131,fd=4),("httpd",pid=1130,fd=4),("httpd",pid=1129,fd=4),("httpd",pid=1128,fd=4),("httpd",pid=1127,fd=4))
  • ให้ httpd ให้บริการที่พอร์ท 8088 และ restart httpd
[root@web-server ~]# grep ^Listen /etc/httpd/conf/httpd.conf 
Listen 80
[root@web-server ~]# sed -i 's/^Listen.*/Listen 8088/g' /etc/httpd/conf/httpd.conf [root@web-server ~]# grep ^Listen /etc/httpd/conf/httpd.conf
Listen 8088
[root@web-server ~]# systemctl restart httpd
Job for httpd.service failed because the control process exited with error code. See "systemctl status httpd.service" and "journalctl -xe" for details
  • พบว่า httpd ไม่สามารถ restart ได้ พบข้อความแสดงข้อผิดพลาดว่า “Permission denied”
[root@web-server ~]# systemctl status httpd -l
● httpd.service - The Apache HTTP Server
Loaded: loaded (/usr/lib/systemd/system/httpd.service; enabled; vendor preset: disabled)
Active: failed (Result: exit-code) since Sun 2017-12-10 11:21:57 +07; 38s ago
Docs: man:httpd(8)
man:apachectl(8)
Process: 1197 ExecStop=/bin/kill -WINCH ${MAINPID} (code=exited, status=1/FAILURE)
Process: 1196 ExecStart=/usr/sbin/httpd $OPTIONS -DFOREGROUND (code=exited, status=1/FAILURE)
Main PID: 1196 (code=exited, status=1/FAILURE)
Dec 10 11:21:57 web-server.localdomain httpd[1196]: (13)Permission denied: AH00072: make_sock: could not bind to address [::]:8088
Dec 10 11:21:57 web-server.localdomain httpd[1196]: (13)Permission denied: AH00072: make_sock: could not bind to address 0.0.0.0:8088
Dec 10 11:21:57 web-server.localdomain httpd[1196]: no listening sockets available, shutting down
[root@web-server ~]# ss -tanp |grep httpd
[root@web-server ~]#
  • เนื่องจากใช้งานโดยผู้ใช้ root ในการแก้ไขค่าต่าง ๆ ใน httpd แต่พบข้อความแสดงข้อผิดพลาดว่า “Permission denied” อาจสันนิษฐานได้ว่าน่าจะเกิดจากการทำงานของ SELinux ดังนั้นตรวจสอบการทำงานของ SELinux ได้จาก /var/log/audit/audit.log พบกว่า SELinux ทำงานโดยไม่อนุญาตให้ httpd ทำงานที่ port 8088
[root@web-server ~]# grep -E 'denied.*httpd' /var/log/audit/audit.log 
type=AVC msg=audit(1512879717.507:122): avc: denied { name_bind } for pid=1196 comm="httpd" src=8088 scontext=system_u:system_r:httpd_t:s0 tcontext=system_u:object_r:unreserved_port_t:s0 tclass=tcp_socket
type=AVC msg=audit(1512879717.507:123): avc: denied { name_bind } for pid=1196 comm="httpd" src=8088 scontext=system_u:system_r:httpd_t:s0 tcontext=system_u:object_r:unreserved_port_t:s0 tclass=tcp_socket
  • ติดตั้ง package policycoreutils-python เพือเรียกใช้งาน SELinux Policy Management tool
[root@web-server ~]# yum -y install policycoreutils-python
Loaded plugins: fastestmirror
Loading mirror speeds from cached hostfile
…. truncate output
Installed:
policycoreutils-python.x86_64 0:2.5-17.1.el7
Dependency Installed:
audit-libs-python.x86_64 0:2.7.6-3.el7
checkpolicy.x86_64 0:2.5-4.el7
libcgroup.x86_64 0:0.41-13.el7
libsemanage-python.x86_64 0:2.5-8.el7
python-IPy.noarch 0:0.75-6.el7
setools-libs.x86_64 0:3.3.8-1.1.el7
Complete!
  • เรียกใช้งานคำสั่ง semanage port -l เพื่อตรวจสอบ port ที่กำหนดข้อสิทธิ์ในการให้บริการกับ context ของบริการต่าง ๆ พบว่า SELinux อนูญาตให้ httpd ให้บริการได้ที port 80, 81, 443, 488, 8008, 8009, 8443, 9000 เท่านั้น
[root@web-server ~]# semanage port -l | grep  '^http_port_t'
http_port_t tcp 80, 81, 443, 488, 8008, 8009, 8443, 9000
  • เรียกใช้คำสั่ง semanage เพื่อเพิ่มรายการ port ที่ต้องการให้บริการ ตามตัวอย่างต้องการให้ SELinux อนุญาตให้ httpd ให้บริการที่ port tcp/8088
[root@web-server ~]# semanage port -a -t http_port_t -p tcp 8088
[root@web-server ~]# semanage port -l | grep '^http_port_t'
http_port_t tcp 8088, 80, 81, 443, 488, 8008, 8009, 8443, 9000
  • ทดสอบการใช้งาน httpd ที่ port 8088 อีกครั้ง
[root@web-server ~]# systemctl restart httpd
[root@web-server ~]# ss -tanp |grep httpd
LISTEN 0 128 :::8088 :::* users:(("httpd",pid=1278,fd=4),("httpd",pid=1277,fd=4),("httpd",pid=1276,fd=4),("httpd",pid=1275,fd=4),("httpd",pid=1274,fd=4),("httpd",pid=1273,fd=4))
[root@web-server ~]# curl http://localhost:8088
Hello World

--

--

Damrongsak Reetanon
Damrongsak Reetanon

Written by Damrongsak Reetanon

OpenSource |Cloud Computing|Automation|DevOps

No responses yet