บทนำ (Overview)
บทความนี้กล่าวถึงวิธีช่องโหว่ของ Command Injection และชี้ให้เห็นถึง Sourcecode ที่เป็นช่องโหว่ รวมถึงแนวทางในการป้องกันสำหรับผู้พัฒนาระบบ
ขั้นตอน (Steps)
ติดตั้งใช้งาน DVNA
- ติดตั้งได้จากบทความ How to install DVNA (Damn Vulnerable NodeJS Application) on MacOS
- สามารถเรียกใช้งานครั้งต่อไปโดยใช้คำสั่ง
docker ps -a sudo docker start dbcf5b9227c4 sudo docker start f284553da237
- ไปที่หน้า TestSystemConnectivity http://127.0.0.1:9090/app/ping
การโจมตี Command injection
- สามารถติดตามวิธีโจมตีรูปแบบต่าง ๆ ได้จากบทความ
- โปรแกรมอนุญาตให้ใส่เฉพาะ IP address ปลายทางเท่านั้น เพื่อทดสอบว่า Server ดังกล่าวสามารถ Ping ไปถึงได้
- ถ้าใช้คำสั่งอื่น ๆ จะเป็นดังนี้
- ทดลองใช้คำสั่งอื่น แต่คั่นด้วย ; ดังนี้
; ls -l ; id
- จากผลลัพธ์ข้างต้นพบว่าสามารถดึงข้อมูลไฟล์และโฟลเดอร์ปัจจุบัน รวมถึงทราบสิทธิที่ใช้เข้าถึงปัจจุบัน
การหาช่องโหว่บน Sourcecodes
- พยายามค้นหาหน้าจอสำหรับกรอกข้อมูลจากผู้ใช้ จากตัวอย่างเป็นรูปแบบการเขียนโปรแกรมแบบ MVC (Model View Conroller) ส่วนติดต่อผู้ใช้คือ Views จะพบว่าหน้าจอ Test Sytem Connectivity มีส่วนติดต่อผู้ใช้ใน File ชื่อ ping.ejs และในส่วนของ Form สำหรับการ Submit ข้อมูลโดย Method แบบ Post
- ไปที่โฟลเดอร์ Routes เพื่อหา Function ที่ Server ใช้ในการประมวลผลฟังก์ชัน ping พบฟังก์ชันชื่อ appHandler.ping
- ไปที่โฟลเดอร์ core (เป็นส่วนเชื่อมต่อ models ที่ติดต่อกับฐานข้อมูล) เพื่อหาฟังก์ชัน appHandler.ping พบว่าอยู่ในไฟล์ appHandler.js พบฟังก์ชัน ping ดังนี้
- จาก Sourcecode เราพบว่า โปรแกรมรับค่า {address} จากผู้ใช้ req.body.address ซึ่งผ่านหน้า Web browser แล้วนำไปต่อกับคำสั่ง ping ที่เป็นคำสั่งของระบบปฎิบัติการ (OS) ผ่านฟังก์ชัน exec() ทันที ซึ่งทำให้ผู้ใช้สามารถเพิ่มคำสั่ง บน OS ที่เป็นอันตรายได้ โดยใช้คำสั่ง ; หรือ & ขั้นระหว่างคำสั่งถัด ๆ ไป นั้นเอง
exec('ping -c 2 ' + req.body.address, function (err, stdout, stderr) {
การป้องกันและแก้ไขปัญหา
- การตรวจสอบข้อมูลนำเข้าผู้ใช้ สามารถใช้ Libary เช่น https://www.npmjs.com/package/validator ดังนี้
- การตรวจสอบรูปแบบ Field ก่อนนำไปประมวลผล
- การจัดรูปแบบของ Field รูปแบบ E-mail โทรศัพท์ วันที่ รหัสบัตรประชาชน
- รูปแบบของ Field เช่น ตัวเลขอย่างเดียว
- ขนาดของ Field เช่น ไม่เกิน 13 ตัวอักษรเป็นต้น
var validator = require('validator'); validator.isEmail('foo@bar.com'); true
- การกรองอักขระพิเศษก่อนนำไปจัดเก็บ
- การกรองอักขระพิเศษ เช่น ;
sanitizer description whitelist(input, chars) remove characters that do not appear in the whitelist. The characters are used in a RegExp and so you will need to escape some chars, e.g. whitelist(input, '\\[\\]')
.blacklist(input, chars) remove characters that appear in the blacklist. The characters are used in a RegExp and so you will need to escape some chars, e.g. blacklist(input, '\\[\\]')
.
- การกรองอักขระพิเศษ เช่น ;
- การตรวจสอบรูปแบบ Field ก่อนนำไปประมวลผล
- ถ้าโปแกรมจำเป็นต้องให้ผู้ใช้สามารถใช้คำสั่ง OS หรือเข้าถึงโฟลเดอร์หรือไฟล์ได้นั้น จะต้องมีการแยกส่วนข้อมูลที่อนุญาตให้ผู้ใช้เข้าถึง ออกจากส่วนสำคัญของระบบ เช่น ส่วนโปรแกรมหลังบ้าน และไฟล์ system ของระบบ
อ้างอิง