diff --git a/lib/core/settings.py b/lib/core/settings.py index e3da391bf..72ff2b220 100644 --- a/lib/core/settings.py +++ b/lib/core/settings.py @@ -265,3 +265,6 @@ MYSQL_ERROR_CHUNK_LENGTH = 50 # Do not unescape the injected statement if it contains any of the following SQL words EXCLUDE_UNESCAPE = ("WAITFOR DELAY ", " INTO DUMPFILE ", " INTO OUTFILE ", "CREATE ", "BULK ", "EXEC ", "RECONFIGURE ", "DECLARE ", CHAR_INFERENCE_MARK) + +# Mark used for replacement of reflected values +REFLECTED_VALUE_MARKER = '__REFLECTED_VALUE__' diff --git a/lib/techniques/inband/union/use.py b/lib/techniques/inband/union/use.py index b00fae4ce..2d2c6ab62 100644 --- a/lib/techniques/inband/union/use.py +++ b/lib/techniques/inband/union/use.py @@ -13,6 +13,7 @@ import time from lib.core.agent import agent from lib.core.common import Backend from lib.core.common import calculateDeltaSeconds +from lib.core.common import filterStringValue from lib.core.common import getUnicode from lib.core.common import initTechnique from lib.core.common import isNumPosStrValue @@ -26,6 +27,7 @@ from lib.core.enums import DBMS from lib.core.enums import PAYLOAD from lib.core.exception import sqlmapSyntaxException from lib.core.settings import FROM_TABLE +from lib.core.settings import REFLECTED_VALUE_MARKER from lib.core.unescaper import unescaper from lib.request.connect import Connect as Request from lib.utils.resume import resume @@ -53,6 +55,13 @@ def __oneShotUnionUse(expression, unpack=True): page, headers = Request.queryPage(payload, content=True, raise404=False) content = "%s%s" % (page or "", listToStrValue(headers.headers if headers else None) or "") + reflective = filterStringValue(agent.removePayloadDelimiters(payload), r'[A-Za-z0-9]', r'[^\s]+') + filtered = re.sub(reflective, REFLECTED_VALUE_MARKER, content) + if filtered != content: + warnMsg = "reflective value found and filtered" + logger.warn(warnMsg) + content = filtered + reqCount += 1 if kb.misc.start not in content or kb.misc.stop not in content: