Proper support for --union-cols

This commit is contained in:
Bernardo Damele 2011-01-17 22:57:33 +00:00
parent 35fb50a6ee
commit c2a358561f
3 changed files with 93 additions and 37 deletions

View File

@ -55,8 +55,8 @@ from lib.core.threads import getCurrentThreadData
from lib.core.unescaper import unescaper from lib.core.unescaper import unescaper
from lib.request.connect import Connect as Request from lib.request.connect import Connect as Request
from lib.request.templates import getPageTemplate from lib.request.templates import getPageTemplate
from lib.techniques.inband.union.use import configUnion
from lib.techniques.inband.union.test import unionTest from lib.techniques.inband.union.test import unionTest
from lib.techniques.inband.union.use import configUnion
def unescape(string, dbms): def unescape(string, dbms):
if string is None: if string is None:
@ -100,6 +100,14 @@ def checkSqlInjection(place, parameter, value):
stype = test.stype stype = test.stype
clause = test.clause clause = test.clause
if stype == 3 and test.request.columns == "[COLSTART]-[COLSTOP]":
if conf.uCols is None:
continue
else:
configUnion()
title = title.replace("[COLSTART]", str(conf.uColsStart))
title = title.replace("[COLSTOP]", str(conf.uColsStop))
# Skip test if the user's wants to test only for a specific # Skip test if the user's wants to test only for a specific
# technique # technique
if conf.technique and isinstance(conf.technique, int) and stype != conf.technique: if conf.technique and isinstance(conf.technique, int) and stype != conf.technique:
@ -383,13 +391,20 @@ def checkSqlInjection(place, parameter, value):
# current test settings for proper unescaping # current test settings for proper unescaping
kb.misc.forcedDbms = dbms kb.misc.forcedDbms = dbms
if conf.uCols is not None and test.request.columns != "[COLSTART]-[COLSTOP]":
debugMsg = "skipping test '%s' because custom " % title
debugMsg += "UNION columns range was provided"
logger.debug(debugMsg)
continue
configUnion(test.request.char, test.request.columns)
if not getIdentifiedDBMS(): if not getIdentifiedDBMS():
warnMsg = "using unescaped version of the test " warnMsg = "using unescaped version of the test "
warnMsg += "because of zero knowledge of the " warnMsg += "because of zero knowledge of the "
warnMsg += "back-end DBMS" warnMsg += "back-end DBMS"
logger.warn(warnMsg) logger.warn(warnMsg)
configUnion(test.request.char, test.request.columns)
reqPayload, vector = unionTest(comment, place, parameter, value, prefix, suffix) reqPayload, vector = unionTest(comment, place, parameter, value, prefix, suffix)
if isinstance(reqPayload, basestring): if isinstance(reqPayload, basestring):

View File

@ -32,6 +32,41 @@ from lib.utils.resume import resume
reqCount = 0 reqCount = 0
def __configUnionChar(char):
if char.isdigit() or char == "NULL":
conf.uChar = char
elif not char.startswith("'") or not char.endswith("'"):
conf.uChar = "'%s'" % char
def __configUnionCols(columns):
if "-" not in columns or len(columns.split("-")) != 2:
raise sqlmapSyntaxException, "--union-cols must be a range with hyphon (e.g. 1-10)"
columns = columns.replace(" ", "")
conf.uColsStart, conf.uColsStop = columns.split("-")
if not conf.uColsStart.isdigit() or not conf.uColsStop.isdigit():
raise sqlmapSyntaxException, "--union-cols must be a range of integers"
conf.uColsStart = int(conf.uColsStart)
conf.uColsStop = int(conf.uColsStop)
if conf.uColsStart > conf.uColsStop:
errMsg = "--union-cols range has to be from lower to "
errMsg += "higher number of columns"
raise sqlmapSyntaxException, errMsg
def configUnion(char=None, columns=None):
if isinstance(conf.uChar, basestring):
__configUnionChar(conf.uChar)
elif isinstance(char, basestring):
__configUnionChar(char)
if isinstance(conf.uCols, basestring):
__configUnionCols(conf.uCols)
elif isinstance(columns, basestring):
__configUnionCols(columns)
def unionUse(expression, direct=False, unescape=True, resetCounter=False, unpack=True, dump=False): def unionUse(expression, direct=False, unescape=True, resetCounter=False, unpack=True, dump=False):
""" """
This function tests for an inband SQL injection on the target This function tests for an inband SQL injection on the target
@ -236,38 +271,3 @@ def unionUse(expression, direct=False, unescape=True, resetCounter=False, unpack
logger.debug(debugMsg) logger.debug(debugMsg)
return value return value
def __configUnionChar(char):
if char.isdigit() or char == "NULL":
conf.uChar = char
elif not char.startswith("'") or not char.endswith("'"):
conf.uChar = "'%s'" % char
def __configUnionCols(columns):
if "-" not in columns or len(columns.split("-")) != 2:
raise sqlmapSyntaxException, "--union-cols must be a range with hyphon (e.g. 1-10)"
columns = columns.replace(" ", "")
conf.uColsStart, conf.uColsStop = columns.split("-")
if not conf.uColsStart.isdigit() or not conf.uColsStop.isdigit():
raise sqlmapSyntaxException, "--union-cols must be a range of integers"
conf.uColsStart = int(conf.uColsStart)
conf.uColsStop = int(conf.uColsStop)
if conf.uColsStart > conf.uColsStop:
errMsg = "--union-cols range has to be from lower to "
errMsg += "higher number of columns"
raise sqlmapSyntaxException, errMsg
def configUnion(char, columns):
if isinstance(conf.uChar, basestring):
__configUnionChar(conf.uChar)
elif isinstance(char, basestring):
__configUnionChar(char)
if isinstance(conf.uCols, basestring):
__configUnionCols(conf.uCols)
elif isinstance(columns, basestring):
__configUnionCols(columns)

View File

@ -2082,6 +2082,28 @@ Formats:
<!-- UNION query tests --> <!-- UNION query tests -->
<test>
<title>MySQL NULL UNION query - [COLSTART] to [COLSTOP] columns</title>
<stype>3</stype>
<level>1</level>
<risk>1</risk>
<clause>1,2,3,4,5</clause>
<where>1</where>
<vector>[UNION]</vector>
<request>
<payload/>
<comment>#</comment>
<char>NULL</char>
<columns>[COLSTART]-[COLSTOP]</columns>
</request>
<response>
<union/>
</response>
<details>
<dbms>MySQL</dbms>
</details>
</test>
<test> <test>
<title>MySQL NULL UNION query - 1 to 3 columns</title> <title>MySQL NULL UNION query - 1 to 3 columns</title>
<stype>3</stype> <stype>3</stype>
@ -2192,6 +2214,25 @@ Formats:
</details> </details>
</test> </test>
<test>
<title>Generic NULL UNION query - [COLSTART] to [COLSTOP] columns</title>
<stype>3</stype>
<level>1</level>
<risk>1</risk>
<clause>1,2,3,4,5</clause>
<where>1</where>
<vector>[UNION]</vector>
<request>
<payload/>
<comment>--</comment>
<char>NULL</char>
<columns>[COLSTART]-[COLSTOP]</columns>
</request>
<response>
<union/>
</response>
</test>
<test> <test>
<title>Generic NULL UNION query - 1 to 3 columns</title> <title>Generic NULL UNION query - 1 to 3 columns</title>
<stype>3</stype> <stype>3</stype>