Hỏi & Đáp#
1. Lỗ hổng Path Traversal là gì và nó khác biệt như thế nào so với các loại lỗ hổng ứng dụng web khác? Giải thích khái niệm path traversal, bao gồm cách kẻ tấn công thao túng đầu vào (input) để truy cập hoặc thao tác với các file nằm ngoài thư mục dự kiến.#
Định nghĩa & Khái niệm: Path Traversal (còn được gọi là Directory Traversal) là một lỗ hổng bảo mật web cho phép kẻ tấn công đọc các file tùy ý trên máy chủ chạy ứng dụng. Các file này có thể bao gồm mã nguồn ứng dụng, file cấu hình, thông tin xác thực (credentials) ở backend, và các file hệ điều hành nhạy cảm như
/etc/passwdtrên Linux hoặcwin.initrên Windows.Sự khác biệt so với các lỗ hổng khác:
Tầng mục tiêu (Target Layer): Không giống như SQL Injection (nhắm vào engine cơ sở dữ liệu) hay Cross-Site Scripting (nhắm vào trình duyệt web của client), Path Traversal nhắm trực tiếp vào hệ thống file cục bộ của máy chủ (local filesystem) bằng cách lợi dụng việc xử lý input không an toàn trong các thao tác file cấp hệ thống.
Thực thi vs. Trích xuất: Khác với Command Injection hay Remote Code Execution (RCE), Path Traversal tiêu chuẩn là một lỗi tiết lộ file tùy ý (arbitrary file disclosure). Nó không trực tiếp thực thi mã, mặc dù kẻ tấn công có thể leo thang lên RCE nếu tận dụng được quyền ghi hoặc các kỹ thuật log poisoning (đầu độc log).
Cơ chế thao túng của kẻ tấn công: Các ứng dụng thường sử dụng input do người dùng cung cấp để xây dựng đường dẫn file nhằm tải nội dung động (ví dụ:
image?filename=46.jpg). Nếu server truyền tham số này vào các API của filesystem mà không kiểm tra (validate):Relative Traversal (Dịch chuyển tương đối): Kẻ tấn công chèn các chuỗi “dot-dot-slash” (
../hoặc..\) để thoát khỏi thư mục gốc dự kiến (/var/www/html/) và di chuyển ngược lên cây thư mục hệ thống:filename=../../../../etc/passwd.Absolute Traversal (Dịch chuyển tuyệt đối): Kẻ tấn công cung cấp một đường dẫn file trực tiếp từ thư mục gốc của hệ điều hành, bỏ qua hoàn toàn thư mục cơ sở dự kiến của ứng dụng:
filename=/etc/passwd.
2. Mô tả quá trình khai thác lỗ hổng Path Traversal trong một ứng dụng web. Các phương pháp hoặc kỹ thuật phổ biến nào được kẻ tấn công sử dụng để thao túng file path, và những phương pháp này làm suy yếu bảo mật của máy chủ như thế nào?#
- Phương pháp luận & Quy trình khai thác:
- Trinh sát & Lập bản đồ bề mặt: Xác định các endpoint của ứng dụng có tương tác với filesystem (ví dụ: các tham số như
file=,path=,filename=,doc=, hoặc các API endpoint phục vụ file tĩnh). - Kiểm thử hành vi & Dò bộ lọc: Gửi các payload tương đối cơ bản (
../) để quan sát phản hồi từ server. Xác định xem ứng dụng có cắt bỏ (strip) chuỗi, chặn request hay trả về các lỗi filesystem cụ thể không. - Bypass & Thực thi: Triển khai các kỹ thuật né tránh nâng cao để vượt qua các bộ lọc phòng thủ và trích xuất file mục tiêu.
Các kỹ thuật Bypass phổ biến:
Absolute Path Bypass (Bypass bằng đường dẫn tuyệt đối): Khi ứng dụng chặn hoặc cắt bỏ các chuỗi
../nhưng không bắt buộc input phải bắt đầu bằng thư mục gốc (base directory prefix), kẻ tấn công truyền trực tiếp đường dẫn tuyệt đối của hệ thống (ví dụ:/etc/passwdhoặcC:\Windows\win.ini).Nested Traversal Sequences (Chuỗi lồng nhau): Sử dụng
....//hoặc....\/khi cơ chế phòng thủ cơ bản cắt bỏ../nhưng không thực hiện đệ quy (non-recursively).URL Encoding / Double Encoding: Mã hóa các ký tự đường dẫn (
%2e%2e%2fhoặc%252e%252e%252f) để vượt qua Web Application Firewall (WAF) hoặc các bộ lọc làm sạch input yếu kém (chỉ giải mã input một lần).Null Byte Injection: Thêm
%00vào cuối (ví dụ:../../etc/passwd%00.png) để bypass các bước kiểm tra backend cũ vốn chỉ xác minh xem chuỗi có kết thúc bằng một file extension cụ thể hay không.Path Validation Bypass: Sử dụng thư mục gốc dự kiến làm tiền tố (prefix) nếu bộ lọc chỉ kiểm tra xem input có bắt đầu bằng một thư mục hợp lệ hay không (ví dụ:
filename=/var/www/images/../../../../etc/passwd).Tác động bảo mật đối với máy chủ:
Tiết lộ thông tin (Information Disclosure): Phơi bày hoàn toàn kiến trúc ứng dụng, các file cấu hình (
.env,web.config), và các secret của database/API được hardcode.Xâm phạm hệ thống (System Compromise): Đọc các tài khoản người dùng OS (
/etc/passwd), private key SSH (id_rsa), hoặc các log hệ thống nhạy cảm.Leo thang lên RCE: Kẻ tấn công có thể kết hợp việc đọc/ghi file tùy ý với log poisoning (chèn payload PHP/JSP vào access log của Apache/Nginx rồi dùng traversal để đọc/thực thi chúng) hoặc ghi đè file cấu hình để chiếm quyền điều khiển toàn bộ server.
Khai thác File path traversal, bộ lọc traversal sequence bị bypass bằng absolute path#
Mục tiêu Lab#
Mục tiêu của bài lab PortSwigger Web Security Academy này là khai thác lỗ hổng Path Traversal trong chức năng tải hình ảnh sản phẩm của một trang thương mại điện tử. Ứng dụng đã chặn các chuỗi relative traversal tiêu chuẩn (../), nhưng không xác minh xem đường dẫn được yêu cầu có nằm trong base directory (thư mục gốc dự kiến) hay không. Bằng cách gửi một đường dẫn tuyệt đối (absolute file path), tôi sẽ cố gắng bypass bộ lọc và trích xuất nội dung của file /etc/passwd trên server.
Bước 1: Mở ứng dụng lab#
Tôi mở lab PortSwigger có tên File path traversal, traversal sequences blocked with absolute path bypass. Trang chủ là một cửa hàng trực tuyến hiển thị nhiều sản phẩm với hình ảnh được tải động từ máy chủ:
Điều này xác nhận rằng bề mặt tấn công của lab có khả năng liên quan đến cơ chế trích xuất file để phục vụ các tài nguyên tĩnh (static assets) của ứng dụng.
Bước 2: Mở hình ảnh sản phẩm để xác định endpoint mục tiêu#
Tiếp theo, tôi mở một hình ảnh sản phẩm trong tab mới để kiểm tra URL và xác định cách backend trích xuất file:
Cấu trúc URL cho thấy ứng dụng sử dụng một endpoint cụ thể với tham số filename để load ảnh:
| |
Vì server trực tiếp lấy input từ người dùng qua tham số filename để truy cập filesystem, đây chính là mục tiêu chính để kiểm thử lỗ hổng path traversal.
Bước 3: Kiểm thử các payload relative path traversal tiêu chuẩn#
Trước khi thử bypass bộ lọc bảo mật, tôi kiểm thử các chuỗi relative path traversal tiêu chuẩn để hiểu cách ứng dụng xử lý input độc hại. Tôi sửa đổi tham số filename trên URL để yêu cầu file /etc/passwd bằng các chuỗi ../:
| |
Thay vì trả về nội dung file, server đã từ chối request và phản hồi với một thông báo lỗi rõ ràng:
| |
Hành vi này cho thấy ứng dụng có triển khai một bộ lọc bảo mật chủ động chặn hoặc cắt bỏ các chuỗi relative traversal (../), khiến việc tra cứu trên filesystem ở backend bị thất bại. Tuy nhiên, thông báo lỗi này không chứng minh được rằng backend giới hạn truy cập file an toàn trong thư mục web root — nó chỉ cho thấy bản thân chuỗi ../ không hợp lệ hoặc đã bị cắt bỏ.
Bước 4: Bypass bộ lọc bằng absolute file path#
Sau khi quan sát thấy các chuỗi relative traversal bị chặn, tôi kiểm tra xem ứng dụng có validate thư mục gốc (base directory) của file được yêu cầu hay không. Khi một bộ lọc chỉ kiểm tra các pattern tương đối cụ thể như ../, nó thường có thể bị bypass bằng cách cung cấp trực tiếp một đường dẫn tuyệt đối (absolute path) từ thư mục gốc của filesystem (root).
Tôi thay đổi tham số để trỏ tới absolute path của file mục tiêu, bỏ qua hoàn toàn việc sử dụng chuỗi ../:
| |
Bước 5: Quan sát kết quả trích xuất file thành công#
Sau khi gửi request với absolute path, server đã chấp nhận input mà không kích hoạt bộ lọc relative path. Ứng dụng trả về thành công nội dung thô (raw) của file chứa tài khoản người dùng Linux:
| |
Điều này xác nhận rằng mặc dù ứng dụng đã chủ động chặn các chuỗi ../, nhưng nó lại thất bại trong việc ép buộc (enforce) giới hạn truy cập trong base directory, cho phép truy xuất file tùy ý từ server.
Bước 6: Xác nhận hoàn thành lab#
Sau khi trích xuất nội dung file /etc/passwd, tôi quay lại banner của lab. Trạng thái lab tự động cập nhật thành Solved:
Xác nhận cuối cùng cho thấy việc khai thác bộ lọc không hoàn thiện thông qua kỹ thuật absolute path bypass đã phơi bày thành công các file hệ điều hành quan trọng, hoàn thành bài lab.
Phân tích lỗ hổng (Vulnerability explanation)#
Nguyên nhân cốt lõi của lỗ hổng này là một bộ lọc phòng thủ không hoàn thiện kết hợp với việc sử dụng trực tiếp input của người dùng trong các thao tác filesystem. Ứng dụng cố gắng ngăn chặn path traversal bằng cách chặn hoặc cắt bỏ các chuỗi relative traversal (../). Tuy nhiên, mã backend truyền trực tiếp filename được cung cấp vào filesystem API mà không kiểm tra xem đường dẫn được phân giải có thực sự bắt đầu bằng base directory dự kiến hay không (ví dụ: /var/www/images/). Hậu quả là, việc truyền vào một đường dẫn tuyệt đối như /etc/passwd sẽ bypass hoàn toàn bộ lọc chuỗi tương đối và cho phép truy cập file không giới hạn.
Tác động bảo mật (Security impact)#
Tác động được chứng minh ở đây là tiết lộ thông tin tùy ý (arbitrary information disclosure). Trong kịch bản thực tế, kẻ tấn công khai thác lỗ hổng này có thể đọc các file hệ thống nhạy cảm, mã nguồn ứng dụng, file cấu hình chứa thông tin đăng nhập database, hoặc các biến môi trường (environment variables). Việc lộ lọt này có thể dẫn đến việc kiểm soát toàn bộ máy chủ, truy cập mạng trái phép, hoặc leo thang đặc quyền.
Các tác động tiềm ẩn bao gồm:
- Phơi bày các tài khoản người dùng hệ thống và cấu hình hệ điều hành.
- Rò rỉ các secret bị hardcode, API keys, và thông tin xác thực database từ các file cấu hình.
- Tiết lộ mã nguồn ứng dụng độc quyền và logic nghiệp vụ (business logic).
- Truy cập vào các log nhạy cảm của ứng dụng hoặc server, có thể chứa session token hoặc dữ liệu người dùng.
- Tạo bước đệm cho các cuộc tấn công sâu hơn, chẳng hạn như Remote Code Execution (RCE), nếu kết hợp với lỗ hổng log poisoning hoặc ghi file tùy ý (arbitrary file write).
Khuyến nghị khắc phục (Remediation recommendations)#
Để ngăn chặn lỗ hổng path traversal, ứng dụng tuyệt đối không bao giờ được truyền raw user input trực tiếp vào các filesystem API. Các biện pháp kiểm soát bảo mật nên dựa trên các design pattern an toàn thay vì chỉ dùng blacklist (danh sách đen) để chặn các ký tự hoặc chuỗi cụ thể.
Các biện pháp phòng thủ được khuyến nghị bao gồm:
- Tránh truyền filename do người dùng kiểm soát trực tiếp vào filesystem; thay vào đó, hãy sử dụng các tham chiếu đối tượng gián tiếp (indirect object references - ví dụ: ánh xạ ID trong database tới các file).
- Nếu bắt buộc phải sử dụng user input, hãy validate input đó dựa trên một strict whitelist (danh sách trắng nghiêm ngặt) chỉ cho phép các filename chứa ký tự chữ và số (alphanumeric) hoặc các giá trị được mong đợi.
- Ép buộc giới hạn nghiêm ngặt trong base directory bằng cách sử dụng các API chuẩn hóa đường dẫn tích hợp sẵn (built-in path canonicalization API, như
realpath()trong PHP hoặcPath.GetFullPath()trong C#) để phân giải đường dẫn tuyệt đối, sau đó xác minh xem nó có bắt đầu chính xác bằng base directory dự kiến hay không. - Không bao giờ chỉ dựa vào việc chặn hoặc cắt bỏ các ký tự như
../hoặc/, vì các bộ lọc này thường xuyên bị bypass bằng các cách biểu diễn đường dẫn (path representations) thay thế. - Chạy web server account với nguyên tắc đặc quyền tối thiểu (principle of least privilege), đảm bảo nó chỉ có quyền đọc (read access) đối với các thư mục public cần thiết và không thể truy cập các file cấp hệ thống như
/etc/passwd.
Kết luận#
Bài lab này đã minh chứng một lỗ hổng Path Traversal gây ra bởi bộ lọc input không hoàn thiện tại endpoint tải hình ảnh. Dù ứng dụng đã chặn các chuỗi relative traversal tiêu chuẩn (../), nó lại thất bại trong việc giới hạn truy cập trong base directory. Bằng cách thay thế tham số filename bằng đường dẫn tuyệt đối /etc/passwd, tôi đã bypass được giới hạn và trích xuất thành công nội dung của file hệ thống, hoàn thành bài lab.