首頁  >  問答  >  主體

使用 mysqli_multi_query 對於成功的 SQL 注入至關重要

我正在嘗試建立 SQL 注入範例,但 MySQL 每次都拒絕第二個查詢,除非我將其變更為 mysqli_multi_query。

<form action="<?php echo $_SERVER['PHP_SELF'];?>" method="post" name="dummyDorm">
        <label>Name: </label>
        <input type="text" name="name"><br>
        <input type="submit" value="Submit">
    </form>

    <?php 
        if($_SERVER["REQUEST_METHOD"] == "POST")
        {
            $name = $_POST['name'];
            $conn = mysqli_connect("localhost", "root", "", "testDB");
            if (mysqli_connect_errno()){
                echo "failed to connect" . mysqli_connect_error();
                die();
            }
            else
            {

                $sql = "SELECT * FROM users WHERE name = '{$name}'";
                var_dump($sql);
                if (mysqli_query($conn, $sql))
                {
                    echo "Success";
                } 
                else {
                    echo "Error: " . $sql . "<br>" . mysqli_error($conn);
                }

                mysqli_close($conn);
            }

        }
    ?>

該表單實際上並沒有執行任何操作,我只是想示範使用 SQL 注入可以編輯資料。我想在輸入“DROP TABLE testTable”的地方執行注入。我的 MySQL 看起來像這樣:

DROP DATABASE IF EXISTS testDB;
CREATE DATABASE testDB;
USE testDB;

CREATE TABLE users
(
    userID INT AUTO_INCREMENT PRIMARY KEY,
    name VARCHAR(255)
)engine=innodb;

CREATE TABLE testTable
(
    test VARCHAR(10)
)engine=innodb;

INSERT INTO users VALUES(null, "user01");

進入註入時:';刪除表測試表 --

輸出如下: 錯誤:SELECT * FROM users WHERE name = '';刪除表格測試表 --' 您的 SQL 語法有錯誤;檢查與您的 MySQL 伺服器版本相對應的手冊,以了解在第 1 行「DROP TABLE testTable --」附近使用的正確語法

我繼續瀏覽教程,他們使用 MySQLi_query 並且它工作正常,但我必須將其更改為 Mysqli_multi_query 才能完成註入。

謝謝

P粉925239921P粉925239921283 天前427

全部回覆(1)我來回復

  • P粉795311321

    P粉7953113212023-12-16 00:48:03

    確實mysqli_query()不允許多重查詢。為此,您需要 mysqli_multi_query(),並且如果您避免使用使用該函數,您可以免受依賴執行多個查詢的 SQL 注入攻擊,例如 DROP TABLE 範例。

    但是,除了 DROP TABLE 之外,SQL 注入還可能導致其他類型的危害。

    我可以使用其他參數來存取您的 PHP 頁面的 URL,這些參數允許我控制您的 SQL 查詢的邏輯:

    讀取表中的所有行:

    ?name=x' OR 'x'='x

    讀取另一個表:

    ?name=x' UNION ALL SELECT ... FROM othertable WHERE 'x'='x

    執行拒絕服務攻擊,用萬億行臨時表殺死您的資料庫伺服器:

    ?name IN (SELECT 1 FROM othertable CROSS JOIN othertable CROSS JOIN othertable CROSS JOIN othertable CROSS JOIN othertable CROSS JOIN othertable CROSS JOIN othertable) AND 'x'='x

    SQL 注入不一定是惡意攻擊。這可能是對合法字串的無意使用,從而導致意外的 SQL 語法:

    ?name=O'Reilly

    SQL 注入的修復眾所周知且簡單:使用參數化查詢。

    查看mysqli_prepare()手冊或流行的完整範例Stack Overflow 問題,例如 如何防止 PHP 中的 SQL 注入?

    回覆
    0
  • 取消回覆