c mysql型別轉換 MYSQL隱式型別轉換

2021-10-18 05:21:45 字數 3073 閱讀 6660

前言

今天看了下團隊發的xctf高校戰疫的wp,這裡先喊一句。楊大樹師傅太強了orz  幾乎沒幫啥忙,簡單的題目都被師傅們秒了,我進度太慢,跟不上,後面難的題目基本動不了。再喊一遍,星盟的師傅tql。再接再厲,希望下次能上師傅們,幫到師傅們解題。

mysql弱型別轉換

這裡本地搭建一下環境(用的老的語句),php7比較高的環境用新的語句

$conn = mysql_connect('127.0.0.1','root','root'); //這裡使用@符號遮蔽出錯資訊

mysql_select_db('test',$conn);

$sql ="select * from people where username = '".$_post["username"]."' and password = '".$_post["password"]."'";

$result = mysql_query($sql);

while($row = mysql_fetch_array($result)){

echo "使用者id:" . $row['id'] . "

";echo "使用者名稱:" . $row['username'] . "

";echo "使用者密碼:" . $row['password'] . "

";mysql_close($conn);

echo "

"; echo "您當前執行的sql語句為:" ;

比如很簡單的一句sql語句

select * from people where username=' 'and password=' ';

當我們在username輸入'-     password傳入'

結果輸出了乙個表的內容,為什麼會這樣呢。是因為mysql存在的隱式型別轉換的問題。

什麼是隱式型別轉換

在mysql中,當操作符與不同型別的運算元一起使用時,會發生型別轉換以使運算元相容。則會發生轉換隱式

也就是說,mysql會根據需要自動將數字轉換為字串,將字串轉換數字。

這裡因為存在-號,隱式型別轉化將' '和' and password = '字串進行了算術運算,轉為成數字型別。

這裡再舉兩個例子

案例一:字串轉換為數字

mysql > select 1+'1';

結果:mysql > 2

案例二: 數字轉換為字串

mysql -> select concat(1024,'andyqian');

結果:'1024,' andyqian';

而通過cast()函式測試後發現字串轉為算數值時會將字串開頭的一串數字作為其轉換後的數值,比如

』02admin』 ==>2

『admin』==>0

』33admin』==>33

這個與php的弱型別問題相似。

所以上面這樣的輸入,其實就會轉化成0-0=0

而username的弱型別轉換值如果為0的話,那麼所有的使用者都將被檢索到

這檢索的時候,將字串型別轉化為數字,admin,yunying都被強制轉化成數字型別,即為0

這裡我們插入新的一行

從這裡就可以看到mysql隱式型別轉換帶的問題。

所以sqlcheckin裡,username必須為admin,但是password可以輸出a'&'1

這裡'a'&'1'執行了位運算

所以這裡password為0,型別轉化後,就可以檢索到username='admin',字串開頭的password的資料行

若password是數字不為0,且是非0開頭的字串的話,就檢索不到,這樣的轉換就是隱式型別轉換的表現

如何避免隱式型別轉換

只有當清楚的知道隱式型別轉換的規則,才能從根本上避免產生隱式型別轉換。mysql也在官網描述了進行隱式型別轉換的一些規則如下:

1. 隱式型別轉換規則:

如果乙個或兩個引數都是null,比較的結果是null,除了null安全的<=>相等比較運算子。對於null <=> null,結果為true。不需要轉換

如果比較操作中的兩個引數都是字串,則將它們作為字串進行比較。

如果兩個引數都是整數,則將它們作為整數進行比較。

如果不與數字進行比較,則將十六進製制值視為二進位制字串

如果其中乙個引數是十進位制值,則比較取決於另乙個引數。 如果另乙個引數是十進位制或整數值,則將引數與十進位制值進行比較,如果另乙個引數是浮點值,則將引數與浮點值進行比較

如果其中乙個引數是timestamp或datetime列,另乙個引數是常量,則在執行比較之前將常量轉換為時間戳。

在所有其他情況下,引數都是作為浮點數(實數)比較的。

2.使用cast函式顯示轉換

select * from people where username=cast(0 as char);

3. 型別一致

這裡說的型別一致,指的是在寫sql時,引數型別一定要與資料庫中的型別一致,避免產生隱式型別轉換,就如剛才在文首時,如果多檢查,寫的sql的引數型別與資料庫中欄位型別一致,也就不會不走索引了,你說是不是?

mysql 函式型別轉換 mysql 型別轉換函式

mysql 型別轉換函式 12.8.cast函式和操作符 binary binary操作符將後面的字串拋給乙個二進位制字串。這是一種簡單的方式來促使逐字節而不是逐字元的進行列比較。這使得比較區分大小寫,即使該列不被定義為 binary或 blob。binary也會產生結尾空白,從而更加顯眼。mysq...

mysql型別轉換c 型別轉換 C 型別轉換

一 簡介 型別轉換 把資料從一種型別轉換另一種型別 我們要求等號兩邊參與運算子必須型別一致,如果不一致,滿足下列條件會發生自動型別轉換或者隱式型別轉換。1.兩種型別相容 例如 int和double 相容 都是數字型別 2.目標型別大於源型別 double int 顯示型別轉換 1.兩種型別相相容 i...

mysql 型別轉換

在對乙個字段型別為varchar的字段使用max函式進行取最大值查詢時,發現取到的值始終是9,而表中實際的最大值是20,當把字段型別改為int時就可以,沒辦法只能轉換後在查詢。用 cast 或者 convert 函式可用來獲取乙個型別的值,並產生另乙個型別的值。例 cast max price as...