1. 程式人生 > >Mysql報錯注入原理分析(count()、rand()、group by)

Mysql報錯注入原理分析(count()、rand()、group by)

可以看到floor(rand(0)*2)是有規律的,而且是固定的,這個就是上面提到的由於是確定性才導致的報錯,那為何會報錯呢,我們接著往下看。

0x05 count與group by的虛擬表

使用select count(*) from `T-Safe` group by x;這種語句的時候我們經常可以看到下面類似的結果:

可以看出 test12的記錄有5條

與count(*)的結果相符合,那麼mysql在遇到select count(*) from TSafe group by x;這語句的時候到底做了哪些操作呢,我們果斷猜測mysql遇到該語句時會建立一個虛擬表(實際上就是會建立虛擬表),那整個工作流程就會如下圖所示:

  1. 先建立虛擬表,如下圖(其中key是主鍵,不可重複):

2.開始查詢資料,取資料庫資料,然後檢視虛擬表存在不,不存在則插入新記錄,存在則count(*)欄位直接加1,如下圖:

由此看到 如果key存在的話就+1, 不存在的話就新建一個key。

那這個和報錯有啥內在聯絡,我們直接往下來,其實到這裡,結合前面的內容大家也能猜個一二了。

0x06 floor(rand(0)*2)報錯

其實mysql官方有給過提示,就是查詢的時候如果使用rand()的話,該值會被計算多次,那這個“被計算多次”到底是什麼意思,就是在使用group by的時候,floor(rand(0)*2)會被執行一次,如果虛表不存在記錄,插入虛表的時候會再被執行一次,我們來看下floor(rand(0)*2)報錯的過程就知道了,從0x04可以看到在一次多記錄的查詢過程中floor(rand(0)*2)的值是定性的,為011011…(記住這個順序很重要),報錯實際上就是floor(rand(0)*2)被計算多次導致的,具體看看select count(*) from TSafe group by floor(rand(0)*2);的查詢過程:

1.查詢前預設會建立空虛擬表如下圖:

2.取第一條記錄,執行floor(rand(0)*2),發現結果為0(第一次計算),查詢虛擬表,發現0的鍵值不存在,則floor(rand(0)*2)會被再計算一次,結果為1(第二次計算),插入虛表,這時第一條記錄查詢完畢,如下圖:

3.查詢第二條記錄,再次計算floor(rand(0)*2),發現結果為1(第三次計算),查詢虛表,發現1的鍵值存在,所以floor(rand(0)*2)不會被計算第二次,直接count(*)加1,第二條記錄查詢完畢,結果如下:

4.查詢第三條記錄,再次計算floor(rand(0)*2),發現結果為0(第4次計算),查詢虛表,發現鍵值沒有0,則資料庫嘗試插入一條新的資料,在插入資料時floor(rand(0)*2)被再次計算,作為虛表的主鍵,其值為1(第5次計算),然而1這個主鍵已經存在於虛擬表中,而新計算的值也為1(主鍵鍵值必須唯一),所以插入的時候就直接報錯了。

5.整個查詢過程floor(rand(0)*2)被計算了5次,查詢原資料表3次,所以這就是為什麼資料表中需要3條資料,使用該語句才會報錯的原因。

0x07 floor(rand()*2)報錯

由0x05我們可以同樣推理出不加入隨機因子的情況,由於沒加入隨機因子,所以floor(rand()*2)是不可測的,因此在兩條資料的時候,只要出現下面情況,即可報錯,如下圖:

最重要的是前面幾條記錄查詢後不能讓虛表存在0,1鍵值,如果存在了,那無論多少條記錄,也都沒辦法報錯,因為floor(rand()*2)不會再被計算做為虛表的鍵值,這也就是為什麼不加隨機因子有時候會報錯,有時候不會報錯的原因。如圖:

當前面記錄讓虛表長成這樣子後,由於不管查詢多少條記錄,floor(rand()*2)的值在虛表中都能找到,所以不會被再次計算,只是簡單的增加count(*)欄位的數量,所以不會報錯,比如floor(rand(1)*2),如圖:

在前兩條記錄查詢後,虛擬表已經存在0和1兩個鍵值了,所以後面再怎麼弄還是不會報錯。

總之報錯需要count(*),rand()、group by,三者缺一不可。

上一頁    

相關推薦

Mysql注入原理分析(count()rand()group by)

可以看到floor(rand(0)*2)是有規律的,而且是固定的,這個就是上面提到的由於是確定性才導致的報錯,那為何會報錯呢,我們接著往下看。 0x05 count與group by的虛擬表 使用select count(*) from `T-Safe` group by x;這種語句的時候我們經

Mysql 注入原理探索

我們一般使用的報錯語句: 1 select count(*),concat((select version()),floor(rand()*2))a from information_schema.tables group by a; concat:為聚合函式,連線字串功能

Mysql注入簡單測試模型

測試Mysql環境:Mysql 5.7.12-log Mysql Community Server(GPL) 1、收集內建函式 http://dev.mysql.com/doc/refman/5.7/en/dynindex-function.html 2、整理列表 select A

sql注入注入原理解析

sql注入報錯注入原理詳解 前言 我相信很多小夥伴在玩sql注入報錯注入時都會有一個疑問,為什麼這麼寫就會報錯?曾經我去查詢的時候,也沒有找到滿意的答案,時隔幾個月終於找到搞清楚原理,特此記錄,也希望後來的小夥伴能夠少走彎路 0x01

MySQL注入方法整理

mysql暴錯注入方法整理,通過floor,UpdateXml,ExtractValue,NAME_CONST,Error based Double Query Injection等方法。 報錯注入:(and後不能直接跟select,可以加()) 1.報錯注入floor-

十種MySQL注入

以下均摘自《程式碼審計:企業級Web程式碼安全架構》一書 1.floor() select * from test where id=1 and (select 1 from (select count(*),concat(user(),floor(rand(0)*

MySQL】ERROR 1558 (HY000): Column count of mysql.user is wrong. Expected 43, found 39.

found src 正常 err erro count blog 查找 版本 原文參考:http://wuzhuti.cn/2348.html 之前在centos6.4系統安裝的是自帶的mysql 5.1版本,後來升級到了5.6版本,執行以下命令報錯 在網上查找原因說說因

經典的MySQL Duplicate entry注入

SQL注射取資料的方式有多種: 利用union select查詢直接在頁面上返回資料,這種最為常見,一個前提是攻擊者能夠構造閉合的查詢。  Oracle中利用監聽UTL_HTTP.request發起的HTTP請求,把QuerySet反彈回攻擊者的主機。當然,HTTP伺

Mac navicat連線mysql:2059mysql及navicat徹底解除安裝

報錯資訊:2059 - Authentication plugin ‘caching_sha2_password’ cannot be loaded: dlope 使用homebrew安裝的是mysql8,在navicat測試連線時報錯,這是因為mysql8的加

mysql DuplicateKeyException分析與解決

在做資料庫同步的時候,發現一個錯誤,mysql報錯如下: org.springframework.dao.DuplicateKeyException: ### Error updating database. Cause: com.mysql.jdbc.exce

MySQL主從檢驗一致性工具pt-table-checksum的案例分析

問題】 有同事反饋我們改造過的MySQL5.7.23版本,使用pt-table-checksum工具比較主從資料庫的一致性時報錯 Unsafe statement written to the binary log using statement format since BINLOG_FORMAT

win10安裝mysql——項識別為 cmdlet函式腳 本檔案或可執行程式的名稱。請檢查名稱的拼寫,如果包括路徑,請確保路徑正確,然後再試一次。

今天在win10安裝mysql資料庫服務,發現報錯: 無法將……項識別為 cmdlet、函式、指令碼檔案或可執行程式的名稱。請檢查名稱的拼寫,如果包括路徑,請確保路徑正確,然後再試一次。 然後我

CentOS7虛擬機器安裝MysqlMysql解決方案

一、安裝 首先在虛擬機器中安裝mysql,具體安裝在哪一個資料夾自己定義,樓主是在opt資料夾下安裝的 安裝mysql過程: 如果中間出現問題,可以嘗試解除安裝mysql,然後重新安裝 解除安裝mysql: 二、啟動 1.首先啟動Mysql,看看是否已經安

MySQL Server has gone away原因彙總分析 • cenalulu's Tech Blog

本文將總結和彙總MySQL Server has gone away這類報錯發生的原因 背景:在平時和開發的交流 以及 在論壇回答問題的或稱中會發現這個問題被問及的頻率非常高。 程式中報錯: MySQL server has gone away 是什麼意思? 如何避免? 因此,感覺有

MySql原因分析Unknown column ‘xxx’ in ‘where clause’

在更新資料庫時曾經碰到過類似於Unknown column ‘xxx’ in ‘where clause’的問題。 單從字面理解,我們很容易得出列名不存在的結論,但是,很多時候起始並不是由於列名出

MYSQL高版本注入技巧-利用NAME_CONST注入

 and (select count(*) from mysql.user)>0/* 1、檢視MYSQL版本 and+exists(select*from+(select*from(select+name_const(@@version,0))a+join(select+name_const(

MySQL:Last_Errno: 1008 | Last_SQL_Errno: 1008

mysqlMySQL主從復制不能同步,查看slave狀態,報錯如下:mysql> show slave status \G *************************** 1. row *************************** Slave_IO_Sta

mysqlMulti-statement transaction required more than 'max_binlog_cache_size' bytes of storage

.cn nbsp 導致 variable ria sed size log more mysql報錯Multi-statement transaction required more than ‘max_binlog_cache_size‘ bytes of storage

解決mysql:- Expression #1 of ORDER BY clause is not in GROUP BY clause and contains nonaggregated column 'information_schema.PROFILING.SEQ'

_for tran contains column schema mysql eat table express mysql執行報錯: - Expression #1 of ORDER BY clause is not in GROUP BY clause and cont