Tác động tiêm html

Sự mô tả

Chèn HTML là một cuộc tấn công tương tự như Cross-site Scripting (XSS). Trong khi ở lỗ hổng XSS, kẻ tấn công có thể tiêm và thực thi mã Javascript, tấn công tiêm HTML chỉ cho phép tiêm một số thẻ HTML nhất định. Khi một ứng dụng không xử lý đúng cách dữ liệu do người dùng cung cấp, kẻ tấn công có thể cung cấp mã HTML hợp lệ, thường thông qua một giá trị tham số và đưa nội dung của chính chúng vào trang. Cuộc tấn công này thường được sử dụng cùng với một số hình thức kỹ thuật xã hội, vì cuộc tấn công đang khai thác lỗ hổng dựa trên mã và lòng tin của người dùng.

Kịch bản tấn công (OWASP)

Kịch bản tấn công có thể xảy ra được trình bày bên dưới.

  • Kẻ tấn công phát hiện ra lỗ hổng tiêm nhiễm và quyết định sử dụng tấn công tiêm nhiễm HTML
  • Kẻ tấn công tạo liên kết độc hại, bao gồm cả nội dung HTML được đưa vào và gửi cho người dùng qua email
  • Người dùng truy cập trang do trang được đặt trong miền đáng tin cậy
  • HTML được đưa vào của kẻ tấn công được hiển thị và hiển thị cho người dùng yêu cầu tên người dùng và mật khẩu
  • Người dùng nhập tên người dùng và mật khẩu, cả hai đều được gửi đến máy chủ của kẻ tấn công

khắc phục

Tập lệnh của bạn sẽ lọc các siêu ký tự từ đầu vào của người dùng

Người giới thiệu

Thử nghiệm chèn HTML (OTG-CLIENT-003)

Tư vấn CERT CA-2000-02 Thẻ HTML độc hại được nhúng trong yêu cầu web của khách hàng

Bưu thiếp từ thế giới hậu XSS

Lỗ hổng liên quan

PHP unserialize() được sử dụng trên đầu vào của người dùng

Việc sử dụng UUID/GUID phiên bản 1 không an toàn

Plugin WordPress WPtouch tạo nonce không an toàn

PHP preg_replace được sử dụng trên đầu vào của người dùng

tiêm XSLT

mức độ nghiêm trọng

Vừa phải

phân loại

CWE-80 CVSS. 3. 0/AV. không áp dụng. L/PR. N/UI. Không áp dụng. U/C. không có. L/A. N

thẻ

Lạm dụng chức năng

Nhiều nhà phát triển web không biết cách truy vấn SQL có thể bị giả mạo và cho rằng truy vấn SQL là một lệnh đáng tin cậy. Điều đó có nghĩa là các truy vấn SQL có thể phá vỡ các biện pháp kiểm soát truy cập, do đó bỏ qua các kiểm tra xác thực và ủy quyền tiêu chuẩn và đôi khi các truy vấn SQL thậm chí có thể cho phép truy cập vào các lệnh cấp hệ điều hành máy chủ

Chèn lệnh SQL trực tiếp là một kỹ thuật mà kẻ tấn công tạo hoặc thay đổi các lệnh SQL hiện có để hiển thị dữ liệu ẩn hoặc ghi đè lên các dữ liệu có giá trị hoặc thậm chí để thực thi các lệnh cấp hệ thống nguy hiểm trên máy chủ cơ sở dữ liệu. Điều này được thực hiện bởi ứng dụng lấy đầu vào của người dùng và kết hợp nó với các tham số tĩnh để tạo truy vấn SQL. Thật không may, các ví dụ sau đây dựa trên những câu chuyện có thật

Do thiếu xác thực đầu vào và kết nối với cơ sở dữ liệu thay mặt cho siêu người dùng hoặc người có thể tạo người dùng, kẻ tấn công có thể tạo siêu người dùng trong cơ sở dữ liệu của bạn

Ví dụ #1 Chia tập kết quả thành các trang. và tạo siêu người dùng (PostgreSQL)

$offset = $argv[0]; // beware, no input validation!
$query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
$result = pg_query($conn, $query);

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
0

Người dùng bình thường nhấp vào các liên kết 'tiếp theo', 'trước đó' trong đó $offset được mã hóa thành URL. Tập lệnh hy vọng rằng $offset sắp tới là một số thập phân. Tuy nhiên, điều gì sẽ xảy ra nếu ai đó cố gắng đột nhập bằng cách thêm một dạng urlencode()'d sau vào URL

0;
insert into pg_shadow(usename,usesysid,usesuper,usecatupd,passwd)
    select 'crack', usesysid, 't','t','crack'
    from pg_shadow where usename='postgres';
--

Nếu điều đó xảy ra, thì tập lệnh sẽ hiển thị quyền truy cập siêu người dùng cho anh ta. Lưu ý rằng
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
1 là cung cấp phần bù hợp lệ cho truy vấn ban đầu và chấm dứt truy vấn đó

Ghi chú

Kỹ thuật phổ biến là buộc trình phân tích cú pháp SQL bỏ qua phần còn lại của truy vấn do nhà phát triển viết với

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
2, đây là dấu hiệu nhận xét trong SQL

Một cách khả thi để có được mật khẩu là phá vỡ các trang kết quả tìm kiếm của bạn. Điều duy nhất kẻ tấn công cần làm là xem liệu có bất kỳ biến đã gửi nào được sử dụng trong các câu lệnh SQL không được xử lý đúng cách không. Các bộ lọc này có thể được đặt phổ biến ở dạng trước để tùy chỉnh các mệnh đề

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
3 và
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
4 trong câu lệnh
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
5. Nếu cơ sở dữ liệu của bạn hỗ trợ cấu trúc
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
6, kẻ tấn công có thể cố gắng thêm toàn bộ truy vấn vào truy vấn ban đầu để liệt kê mật khẩu từ một bảng tùy ý. Sử dụng các trường mật khẩu được mã hóa được khuyến khích mạnh mẽ

Ví dụ #2 Liệt kê các bài báo. và một số mật khẩu (bất kỳ máy chủ cơ sở dữ liệu nào)

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
0

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
0

Phần tĩnh của truy vấn có thể được kết hợp với một câu lệnh
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
5 khác tiết lộ tất cả mật khẩu

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--

Nếu truy vấn này (chơi với
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
3 và
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
2) được gán cho một trong các biến được sử dụng trong $query, con thú truy vấn sẽ thức tỉnh

SQL UPDATE cũng dễ bị tấn công. Các truy vấn này cũng bị đe dọa bằng cách cắt và thêm một truy vấn hoàn toàn mới vào nó. Nhưng kẻ tấn công có thể loay hoay với mệnh đề

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
5. Trong trường hợp này, một số thông tin lược đồ phải được sở hữu để thao tác truy vấn thành công. Điều này có thể có được bằng cách kiểm tra các tên biến biểu mẫu hoặc chỉ đơn giản là cưỡng bức vũ phu. Không có nhiều quy ước đặt tên cho các trường lưu trữ mật khẩu hoặc tên người dùng

Ví dụ #3 Từ việc đặt lại mật khẩu. để đạt được nhiều đặc quyền hơn (bất kỳ máy chủ cơ sở dữ liệu nào)

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
6

Nhưng nếu một người dùng độc hại gửi giá trị
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
7 đến $uid để thay đổi mật khẩu của quản trị viên hoặc chỉ cần đặt $pwd thành
'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
8 để có thêm đặc quyền, thì truy vấn sẽ bị xoắn

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
9

$offset = $argv[0]; // beware, no input validation!
$query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
$result = pg_query($conn, $query);
0

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
0

Một ví dụ đáng sợ về cách các lệnh cấp hệ điều hành có thể được truy cập trên một số máy chủ cơ sở dữ liệu

Ví dụ #4 Tấn công hệ điều hành máy chủ cơ sở dữ liệu (MSSQL Server)

$offset = $argv[0]; // beware, no input validation!
$query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
$result = pg_query($conn, $query);
2

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
0

Nếu kẻ tấn công gửi giá trị $offset = $argv[0]; // beware, no input validation!
$query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
$result = pg_query($conn, $query);
4 tới $prod, thì $query sẽ là

$offset = $argv[0]; // beware, no input validation!
$query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
$result = pg_query($conn, $query);
5

'
union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
--
0

Máy chủ MSSQL thực thi các câu lệnh SQL trong lô bao gồm lệnh thêm người dùng mới vào cơ sở dữ liệu tài khoản cục bộ. Nếu ứng dụng này đang chạy dưới dạng $offset = $argv[0]; // beware, no input validation!
$query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
$result = pg_query($conn, $query);
7 và dịch vụ MSSQLSERVER đang chạy với đủ đặc quyền, thì kẻ tấn công giờ đây sẽ có một tài khoản để truy cập vào máy này

Ghi chú

Một số ví dụ trên được gắn với một máy chủ cơ sở dữ liệu cụ thể. Điều này không có nghĩa là một cuộc tấn công tương tự là không thể đối với các sản phẩm khác. Máy chủ cơ sở dữ liệu của bạn có thể bị tổn thương tương tự theo cách khác

Tác động tiêm html

Hình ảnh lịch sự của » xkcd

kỹ thuật tránh

Mặc dù rõ ràng là kẻ tấn công phải có ít nhất một số kiến ​​thức về kiến ​​trúc cơ sở dữ liệu để tiến hành một cuộc tấn công thành công, nhưng việc thu thập thông tin này thường rất đơn giản. Ví dụ: nếu cơ sở dữ liệu là một phần của mã nguồn mở hoặc gói phần mềm có sẵn công khai khác với cài đặt mặc định, thì thông tin này hoàn toàn mở và có sẵn. Thông tin này cũng có thể được tiết lộ bằng mã nguồn đóng - ngay cả khi nó được mã hóa, làm xáo trộn hoặc biên dịch - và thậm chí bằng chính mã của bạn thông qua việc hiển thị các thông báo lỗi. Các phương thức khác bao gồm người dùng tên bảng và cột chung. Ví dụ: biểu mẫu đăng nhập sử dụng bảng 'người dùng' có tên cột 'id', 'tên người dùng' và 'mật khẩu'

Các cuộc tấn công này chủ yếu dựa trên việc khai thác mã không được viết với mục đích bảo mật. Không bao giờ tin tưởng vào bất kỳ loại thông tin đầu vào nào, đặc biệt là thông tin đến từ phía khách hàng, ngay cả khi nó đến từ hộp chọn, trường nhập ẩn hoặc cookie. Ví dụ đầu tiên cho thấy một truy vấn vô tội vạ như vậy có thể gây ra thảm họa

  • Không bao giờ kết nối với cơ sở dữ liệu với tư cách là siêu người dùng hoặc chủ sở hữu cơ sở dữ liệu. Sử dụng người dùng luôn được tùy chỉnh với các đặc quyền rất hạn chế
  • Sử dụng các câu lệnh đã chuẩn bị với các biến bị ràng buộc. Chúng được cung cấp bởi PDO, MySQLi và các thư viện khác
  • Kiểm tra xem đầu vào đã cho có kiểu dữ liệu mong muốn không. PHP có nhiều loại hàm xác thực đầu vào, từ những hàm đơn giản nhất được tìm thấy trong Hàm biến và Hàm kiểu ký tự (e. g. is_numeric(), ctype_digit() tương ứng) trở đi để hỗ trợ Biểu thức chính quy tương thích với Perl
  • Nếu ứng dụng đợi nhập số, hãy xem xét xác minh dữ liệu bằng ctype_digit() hoặc âm thầm thay đổi loại của nó bằng settype() hoặc sử dụng biểu diễn số của nó bằng sprintf()

    Ví dụ #5 Một cách an toàn hơn để soạn truy vấn cho phân trang

    $offset = $argv[0]; // beware, no input validation!
    $query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
    $result = pg_query($conn, $query);
    8

    $offset = $argv[0]; // beware, no input validation!
    $query  = "SELECT id, name FROM products ORDER BY name LIMIT 20 OFFSET $offset;";
    $result = pg_query($conn, $query);
    9

    '
    union select '1', concat(uname||'-'||passwd) as name, '1971-01-01', '0' from usertable;
    --
    0

  • Nếu lớp cơ sở dữ liệu không hỗ trợ các biến liên kết thì hãy trích dẫn từng giá trị không phải là số do người dùng cung cấp được chuyển đến cơ sở dữ liệu bằng hàm thoát chuỗi dành riêng cho cơ sở dữ liệu (e. g. mysql_real_escape_string(), sqlite_escape_string(), v.v. ). Các hàm chung như addlashes() chỉ hữu ích trong một môi trường rất cụ thể (e. g. MySQL trong bộ ký tự một byte bị vô hiệu hóa NO_BACKSLASH_ESCAPES), vì vậy tốt hơn hết là tránh chúng
  • Không in ra bất kỳ thông tin cụ thể nào về cơ sở dữ liệu, đặc biệt là về lược đồ, bằng các phương tiện công bằng hoặc xấu. Xem thêm Chức năng báo cáo lỗi và xử lý lỗi và ghi nhật ký
  • Bạn có thể sử dụng thủ tục lưu trữ và con trỏ đã xác định trước để truy cập dữ liệu trừu tượng để người dùng không truy cập trực tiếp vào bảng hoặc dạng xem, nhưng giải pháp này có tác động khác

Bên cạnh đó, bạn được hưởng lợi từ việc ghi nhật ký các truy vấn trong tập lệnh của mình hoặc bởi chính cơ sở dữ liệu, nếu nó hỗ trợ ghi nhật ký. Rõ ràng, việc ghi nhật ký không thể ngăn chặn bất kỳ nỗ lực gây hại nào, nhưng có thể hữu ích để truy ngược lại ứng dụng nào đã bị phá vỡ. Bản thân nhật ký không hữu ích, nhưng thông qua thông tin chứa trong đó. Chi tiết hơn nói chung là tốt hơn ít hơn