mirror of
https://github.com/sqlmapproject/sqlmap.git
synced 2024-11-22 17:46:37 +03:00
Implements ARRAY_AGG for PostgreSQL
This commit is contained in:
parent
73d0c67a80
commit
a5852390f7
|
@ -18,7 +18,7 @@ from lib.core.enums import OS
|
||||||
from thirdparty.six import unichr as _unichr
|
from thirdparty.six import unichr as _unichr
|
||||||
|
|
||||||
# sqlmap version (<major>.<minor>.<month>.<monthly commit>)
|
# sqlmap version (<major>.<minor>.<month>.<monthly commit>)
|
||||||
VERSION = "1.4.10.23"
|
VERSION = "1.4.10.24"
|
||||||
TYPE = "dev" if VERSION.count('.') > 2 and VERSION.split('.')[-1] != '0' else "stable"
|
TYPE = "dev" if VERSION.count('.') > 2 and VERSION.split('.')[-1] != '0' else "stable"
|
||||||
TYPE_COLORS = {"dev": 33, "stable": 90, "pip": 34}
|
TYPE_COLORS = {"dev": 33, "stable": 90, "pip": 34}
|
||||||
VERSION_STRING = "sqlmap/%s#%s" % ('.'.join(VERSION.split('.')[:-1]) if VERSION.count('.') > 2 and VERSION.split('.')[-1] == '0' else VERSION, TYPE)
|
VERSION_STRING = "sqlmap/%s#%s" % ('.'.join(VERSION.split('.')[:-1]) if VERSION.count('.') > 2 and VERSION.split('.')[-1] == '0' else VERSION, TYPE)
|
||||||
|
|
|
@ -135,11 +135,17 @@ def _oneShotUnionUse(expression, unpack=True, limited=False):
|
||||||
else:
|
else:
|
||||||
retVal = getUnicode(retVal)
|
retVal = getUnicode(retVal)
|
||||||
elif kb.jsonAggMode:
|
elif kb.jsonAggMode:
|
||||||
|
if Backend.isDbms(DBMS.PGSQL):
|
||||||
|
output = extractRegexResult(r"(?P<result>%s.*%s)" % (kb.chars.start, kb.chars.stop), page or "")
|
||||||
|
if output:
|
||||||
|
retVal = output
|
||||||
|
else:
|
||||||
output = extractRegexResult(r"(?P<result>%s.*?%s)" % (kb.chars.start, kb.chars.stop), page or "")
|
output = extractRegexResult(r"(?P<result>%s.*?%s)" % (kb.chars.start, kb.chars.stop), page or "")
|
||||||
if output:
|
if output:
|
||||||
|
output = output[len(kb.chars.start):-len(kb.chars.stop)]
|
||||||
try:
|
try:
|
||||||
retVal = ""
|
retVal = ""
|
||||||
for row in json.loads(output[len(kb.chars.start):-len(kb.chars.stop)]):
|
for row in json.loads(output):
|
||||||
retVal += "%s%s%s" % (kb.chars.start, row, kb.chars.stop)
|
retVal += "%s%s%s" % (kb.chars.start, row, kb.chars.stop)
|
||||||
except:
|
except:
|
||||||
pass
|
pass
|
||||||
|
@ -248,16 +254,24 @@ def unionUse(expression, unpack=True, dump=False):
|
||||||
# Set kb.partRun in case the engine is called from the API
|
# Set kb.partRun in case the engine is called from the API
|
||||||
kb.partRun = getPartRun(alias=False) if conf.api else None
|
kb.partRun = getPartRun(alias=False) if conf.api else None
|
||||||
|
|
||||||
if Backend.getIdentifiedDbms() in (DBMS.MYSQL, DBMS.ORACLE) and expressionFields:
|
if expressionFieldsList and len(expressionFieldsList) > 1 and "ORDER BY" in expression.upper():
|
||||||
|
# Removed ORDER BY clause because UNION does not play well with it
|
||||||
|
expression = re.sub(r"(?i)\s*ORDER BY\s+[\w,]+", "", expression)
|
||||||
|
debugMsg = "stripping ORDER BY clause from statement because "
|
||||||
|
debugMsg += "it does not play well with UNION query SQL injection"
|
||||||
|
singleTimeDebugMessage(debugMsg)
|
||||||
|
|
||||||
|
if Backend.getIdentifiedDbms() in (DBMS.MYSQL, DBMS.ORACLE, DBMS.PGSQL) and expressionFields:
|
||||||
match = re.search(r"SELECT\s*(.+?)\bFROM", expression, re.I)
|
match = re.search(r"SELECT\s*(.+?)\bFROM", expression, re.I)
|
||||||
if match and not (Backend.isDbms(DBMS.ORACLE) and FROM_DUMMY_TABLE[DBMS.ORACLE] in expression):
|
if match and not (Backend.isDbms(DBMS.ORACLE) and FROM_DUMMY_TABLE[DBMS.ORACLE] in expression):
|
||||||
kb.jsonAggMode = True
|
kb.jsonAggMode = True
|
||||||
if Backend.isDbms(DBMS.MYSQL):
|
if Backend.isDbms(DBMS.MYSQL):
|
||||||
_ = expression.replace(expressionFields, "CONCAT('%s',JSON_ARRAYAGG(CONCAT_WS('%s',%s)),'%s')" % (kb.chars.start, kb.chars.delimiter, expressionFields, kb.chars.stop), 1)
|
query = expression.replace(expressionFields, "CONCAT('%s',JSON_ARRAYAGG(CONCAT_WS('%s',%s)),'%s')" % (kb.chars.start, kb.chars.delimiter, expressionFields, kb.chars.stop), 1)
|
||||||
else:
|
elif Backend.isDbms(DBMS.ORACLE):
|
||||||
_ = expression.replace(expressionFields, "'%s'||JSON_ARRAYAGG(%s)||'%s'" % (kb.chars.start, ("||'%s'||" % kb.chars.delimiter).join(expressionFieldsList), kb.chars.stop), 1)
|
query = expression.replace(expressionFields, "'%s'||JSON_ARRAYAGG(%s)||'%s'" % (kb.chars.start, ("||'%s'||" % kb.chars.delimiter).join(expressionFieldsList), kb.chars.stop), 1)
|
||||||
_ = re.sub(r"(?i)\s*ORDER BY ROWNUM", "", _)
|
elif Backend.isDbms(DBMS.PGSQL):
|
||||||
output = _oneShotUnionUse(_, False)
|
query = expression.replace(expressionFields, "ARRAY_AGG('%s'||%s||'%s')::text" % (kb.chars.start, ("||'%s'||" % kb.chars.delimiter).join("COALESCE(%s::text,' ')" % field for field in expressionFieldsList), kb.chars.stop), 1)
|
||||||
|
output = _oneShotUnionUse(query, False)
|
||||||
value = parseUnionPage(output)
|
value = parseUnionPage(output)
|
||||||
kb.jsonAggMode = False
|
kb.jsonAggMode = False
|
||||||
elif Backend.isDbms(DBMS.MSSQL) and kb.dumpColumns:
|
elif Backend.isDbms(DBMS.MSSQL) and kb.dumpColumns:
|
||||||
|
@ -267,13 +281,6 @@ def unionUse(expression, unpack=True, dump=False):
|
||||||
value = parseUnionPage(output)
|
value = parseUnionPage(output)
|
||||||
kb.rowXmlMode = False
|
kb.rowXmlMode = False
|
||||||
|
|
||||||
if expressionFieldsList and len(expressionFieldsList) > 1 and "ORDER BY" in expression.upper():
|
|
||||||
# Removed ORDER BY clause because UNION does not play well with it
|
|
||||||
expression = re.sub(r"(?i)\s*ORDER BY\s+[\w,]+", "", expression)
|
|
||||||
debugMsg = "stripping ORDER BY clause from statement because "
|
|
||||||
debugMsg += "it does not play well with UNION query SQL injection"
|
|
||||||
singleTimeDebugMessage(debugMsg)
|
|
||||||
|
|
||||||
# We have to check if the SQL query might return multiple entries
|
# We have to check if the SQL query might return multiple entries
|
||||||
# if the technique is partial UNION query and in such case forge the
|
# if the technique is partial UNION query and in such case forge the
|
||||||
# SQL limiting the query output one entry at a time
|
# SQL limiting the query output one entry at a time
|
||||||
|
|
Loading…
Reference in New Issue
Block a user