Qodana là một nền tảng chất lượng mã của JetBrains. Nền tảng này được thiết kế để đưa phân tích tĩnh phía máy chủ vào công cụ CI ưa thích của bạn. Bằng cách sử dụng các cấu hình và kiểm tra mã giống như PhpStorm và các IDE JetBrains khác thực hiện, nền tảng Qodana giúp đảm bảo kiểm tra chất lượng mã nhất quán cả trong IDE và môi trường CI của bạn.
Chỉ cần một người dùng để khai thác lỗ hổng trong dự án của bạn và vi phạm hệ thống của bạn. Để bảo vệ các chương trình chống lại các đầu vào độc hại từ người dùng bên ngoài (được gọi là “taints”), các nhóm phát triển đã thêm tính năng kiểm tra “taints” vào quy trình phân tích tĩnh của họ.
Trong bản phát hành đầu tiên của năm nay, nhóm Qodana đã cung cấp bản phân tích “taints” cho PHP trong EAP. Tính năng này chỉ khả dụng trong Qodana cho PHP 2023.1 (jetbrains/qodana-php:2023.1-eap). Qodana cho PHP là ứng dụng linter đầu tiên mà JetBrains phát hành, vì vậy, hãng đã quyết định để các nhà phát triển PHP là những người đầu tiên thử nghiệm chức năng bảo mật mới.
Phân tích “taints” là gì?
Một “taint” là bất kỳ giá trị nào có thể gây ra rủi ro bảo mật khi được sửa đổi bởi người dùng bên ngoài. Nếu mã của bạn có lỗi và dữ liệu bên ngoài chưa được xác minh có thể được phân phối trên toàn bộ chương trình của bạn, tin tặc có thể thực thi các đoạn mã này để gây ra lỗi SQL injection, tràn số học, tạo tập lệnh chéo trang, truyền tải đường dẫn, v.v… Thông thường, chúng khai thác những lỗ hổng này để phá hủy hệ thống, chiếm đoạt thông tin đăng nhập và dữ liệu khác, đồng thời thay đổi hành vi của hệ thống.
Là một lớp bảo vệ bổ sung chống lại đầu vào độc hại, các nhóm phát triển thực hiện phân tích “taint” khi họ chạy kiểm tra bảo mật trên bề mặt tấn công của chương trình.
Phân tích “taint” là quá trình đánh giá luồng đầu vào của người dùng không đáng tin cậy trong toàn bộ nội dung của một hàm hoặc phương thức. Mục tiêu cốt lõi của nó là xác định xem đầu vào không lường trước được có thể ảnh hưởng đến việc thực thi chương trình theo những cách độc hại hay không.
Nguồn nhiễm độc là những vị trí mà chương trình có quyền truy cập vào dữ liệu có khả năng bị nhiễm độc. Các điểm chính trong một chương trình dễ bị nhiễm độc đầu vào được gọi là nhiễm độc chìm. Dữ liệu này có thể được truyền tới các phần chìm thông qua các lời gọi hàm hoặc phép gán.
Nếu chạy phân tích “taint” theo cách thủ công, bạn nên phát hiện tất cả những nơi bạn chấp nhận dữ liệu từ người dùng bên ngoài và theo dõi từng phần dữ liệu thông qua hệ thống – dữ liệu bị nhiễm độc có thể được sử dụng trong hàng chục nút. Sau đó, để ngăn chặn sự lây lan vết bẩn, bạn nên thực hiện một trong hai cách tiếp cận được mô tả bên dưới:
- Vệ sinh dữ liệu, tức là chuyển đổi dữ liệu sang trạng thái an toàn. Trong ví dụ bên dưới, chúng tôi đã xóa các thẻ để giải quyết “taint”.
- Xác thực dữ liệu, tức là kiểm tra xem dữ liệu đã thêm có tuân theo mẫu bắt buộc không. Trong ví dụ bên dưới, chúng tôi kích hoạt xác thực cho biến `$email`.
Nói cách khác, quá trình kiểm tra phân tích “taint” theo dõi dữ liệu bị nhiễm độc của người dùng từ nguồn của nó đến phần chứa của bạn và đưa ra cảnh báo khi bạn làm việc với dữ liệu đó mà không làm sạch hoặc xác thực dữ liệu đó.
Cách phân tích “taint” hoạt động trong nền tảng Qodana
Phân tích “taint” được Qodana thực hiện cho PHP bắt đầu từ phiên bản 2023.1 EAP. Chức năng này bao gồm kiểm tra quét mã và làm nổi bật “taint” và lỗ hổng tiềm ẩn, khả năng mở vấn đề trong PhpStorm để giải quyết nó ngay tại chỗ và biểu đồ luồng dữ liệu trực quan hóa luồng “taint”.
Ví dụ 1. SQL injection
Hãy cùng xem một ví dụ về SQL injection và cách Qodana phát hiện ra nó:
Ở đây, nền tảng Qodana cho chúng ta thấy những “taint” sau trong hàm system_admin():
Mark 1-2: Dữ liệu từ đầu vào biểu mẫu người dùng được truy xuất từ mảng toàn cầu $_POST mà không cần làm sạch hoặc xác thực và được gán cho biến $edit. Đây là một “taint”.
Mark 3: Biến bị nhiễm độc $edit được chuyển đến hàm system_save_settings dưới dạng đối số mà không có bất kỳ sự làm sạch thích hợp nào.
Mark 4: Dữ liệu từ biến $edit hiện nằm trong tham số $edit.
Mark 5: Biến $edit được chuyển đến foreach với khóa $filename và giá trị $status. Cả hai biến đều chứa dữ liệu bị nhiễm độc từ biến $edit được nối với chuỗi. Khóa $filename được nối với một chuỗi SQL bị nhiễm độc, sau đó nó sẽ truyền dữ liệu bị nhiễm độc thành một đối số được chuyển đến db_query.
Mark 6: Khóa $filename chứa dữ liệu bị nhiễm độc từ biến $edit nối với chuỗi.
Mark 7: Khóa $filename được nối với một chuỗi SQL bị nhiễm độc.
Mark 8: Chuỗi SQL bị nhiễm độc sẽ truyền dữ liệu bị nhiễm độc thành một đối số được chuyển đến `db_query`
Bây giờ hãy xem xét db_query:
Mark 9: Chuỗi bị nhiễm độc sẽ nằm trong tham số $query.
Mark 10: Tham số này sẽ là đối số của hàm _db_query.
Hãy chuyển sang hàm _db_query:
Mark 11: Dữ liệu bị nhiễm độc nằm trong tham số $ query đầu tiên của hàm _db_query.
Mark 12: Dữ liệu của tham số được chuyển đến hàm mysql_query, đây là hàm chìm.
Toàn bộ luồng dữ liệu ở trên minh họa cách dữ liệu di chuyển từ $_POST[“edit”] sang mysql_query($query) mà không cần bất kỳ quá trình làm sạch hoặc xác thực nào. Điều này cho phép kẻ tấn công thao túng truy vấn SQL được nối với khóa $_POST[“edit”] và kích hoạt SQL injection.
Nền tảng Qodana sẽ phát hiện những rủi ro này trong cơ sở mã của bạn cùng với tất cả các nút sử dụng dữ liệu bị nhiễm độc, vì vậy bạn có thể vệ sinh tất cả dữ liệu bị nhiễm độc một cách kịp thời.
Ví dụ #2. vấn đề XSS
Trong giao diện người dùng Qodana, bạn có thể thấy một biểu đồ trực quan hóa toàn bộ luồng ô nhiễm. Đây là cách Qodana sẽ trực quan hóa lỗ hổng XSS, lỗ hổng này chứa 2 nguồn sẽ được hợp nhất trên Mark 5.
Nguồn 1
Mark 1-2: Dữ liệu từ tệp searchUpdate.pos sẽ được đọc và dữ liệu bị nhiễm độc sẽ được gán cho biến $start.
Nguồn 2
Mark 3-4: Dữ liệu từ các tệp có đường dẫn nằm trong $posFile sẽ được đọc và dữ liệu bị nhiễm độc sẽ được gán cho biến $start.
Mark 5: Trạng thái nhiễm độc được hợp nhất từ tất cả các nhánh có điều kiện trong biến $start sẽ được chuyển thành đối số cho phương thức doUpdateSearchIndex.
Hãy xem bên trong phương thức doUpdateSearchIndex():
Mark 6-8: Tham số $ start sẽ chứa dữ liệu bị nhiễm độc trên lát luồng dữ liệu này và sau đó nó sẽ được chuyển trong một chuỗi được nối làm đối số cho phương thức `đầu ra`.
Hãy nhìn vào bên trong phương thức đầu ra:
Xem thêm: >>> Bảng giá phần mềm JetBrains mới nhất áp dụng từ 1.10.2022
Mark 9: Dữ liệu bị nhiễm độc chứa bên trong chuỗi được truyền sẽ nằm trong tham số $out.
Mark 10: Dữ liệu từ tham số $out sẽ được chuyển sang hàm `print` mà không cần làm sạch. Chức năng này là một phần chìm và gây ra lỗ hổng XSS, có thể bị khai thác.
Ví dụ, để khai thác lỗ hổng bảo mật, kẻ tấn công có thể tải lên một tập lệnh shell thay vì các tệp dự kiến trong các Mark 1 và 2, đồng thời có thể đưa bất kỳ thông tin nào lên trang web do chức năng in không được vệ sinh.
Qodana sẽ cảnh báo bạn về lỗ hổng bảo mật này và đặt nó ở mức độ ưu tiên cao để bạn có thể giải quyết nó càng sớm càng tốt và ngăn chặn việc hack.
Phần kết luận
Phân tích “taint” giúp loại bỏ các bề mặt attack có thể khai thác, do đó, đây là một phương pháp hiệu quả để giảm rủi ro cho phần mềm của bạn. Để tìm hiểu chi tiết về phân tích vết bẩn và Qodana, hãy khám phá tài liệu về Qodana.
Xem thêm: >>> Học Machine Learning với PyCharm trên JetBrains Academy
Theo: Valerie Kuzmina
Nguồn: JetBrains Blog