mirror of
https://github.com/sqlmapproject/sqlmap.git
synced 2025-12-09 06:01:29 +00:00
refactoring (class names should always be Capital cased)
This commit is contained in:
@@ -11,7 +11,7 @@ import re
|
||||
|
||||
from xml.etree import ElementTree as ET
|
||||
|
||||
from lib.core.common import backend
|
||||
from lib.core.common import Backend
|
||||
from lib.core.common import getCompiledRegex
|
||||
from lib.core.common import isDBMSVersionAtLeast
|
||||
from lib.core.common import isTechniqueAvailable
|
||||
@@ -222,8 +222,8 @@ class Agent:
|
||||
payload = payload.replace("[ORIGVALUE]", origvalue)
|
||||
|
||||
if "[INFERENCE]" in payload:
|
||||
if backend.getIdentifiedDbms() is not None:
|
||||
inference = queries[backend.getIdentifiedDbms()].inference
|
||||
if Backend.getIdentifiedDbms() is not None:
|
||||
inference = queries[Backend.getIdentifiedDbms()].inference
|
||||
|
||||
if "dbms_version" in inference:
|
||||
if isDBMSVersionAtLeast(inference.dbms_version):
|
||||
@@ -281,17 +281,17 @@ class Agent:
|
||||
|
||||
# SQLite version 2 does not support neither CAST() nor IFNULL(),
|
||||
# introduced only in SQLite version 3
|
||||
if backend.getIdentifiedDbms() == DBMS.SQLITE:
|
||||
if Backend.getIdentifiedDbms() == DBMS.SQLITE:
|
||||
return field
|
||||
|
||||
if field.startswith("(CASE"):
|
||||
nulledCastedField = field
|
||||
else:
|
||||
nulledCastedField = queries[backend.getIdentifiedDbms()].cast.query % field
|
||||
if backend.getIdentifiedDbms() == DBMS.ACCESS:
|
||||
nulledCastedField = queries[backend.getIdentifiedDbms()].isnull.query % (nulledCastedField, nulledCastedField)
|
||||
nulledCastedField = queries[Backend.getIdentifiedDbms()].cast.query % field
|
||||
if Backend.getIdentifiedDbms() == DBMS.ACCESS:
|
||||
nulledCastedField = queries[Backend.getIdentifiedDbms()].isnull.query % (nulledCastedField, nulledCastedField)
|
||||
else:
|
||||
nulledCastedField = queries[backend.getIdentifiedDbms()].isnull.query % nulledCastedField
|
||||
nulledCastedField = queries[Backend.getIdentifiedDbms()].isnull.query % nulledCastedField
|
||||
|
||||
return nulledCastedField
|
||||
|
||||
@@ -325,7 +325,7 @@ class Agent:
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
if not backend.getDbms():
|
||||
if not Backend.getDbms():
|
||||
return fields
|
||||
|
||||
if fields.startswith("(CASE"):
|
||||
@@ -333,7 +333,7 @@ class Agent:
|
||||
else:
|
||||
fields = fields.replace(", ", ",")
|
||||
fieldsSplitted = fields.split(",")
|
||||
dbmsDelimiter = queries[backend.getIdentifiedDbms()].delimiter.query
|
||||
dbmsDelimiter = queries[Backend.getIdentifiedDbms()].delimiter.query
|
||||
nulledCastedFields = []
|
||||
|
||||
for field in fieldsSplitted:
|
||||
@@ -396,13 +396,13 @@ class Agent:
|
||||
def simpleConcatQuery(self, query1, query2):
|
||||
concatenatedQuery = ""
|
||||
|
||||
if backend.getIdentifiedDbms() == DBMS.MYSQL:
|
||||
if Backend.getIdentifiedDbms() == DBMS.MYSQL:
|
||||
concatenatedQuery = "CONCAT(%s,%s)" % (query1, query2)
|
||||
|
||||
elif backend.getIdentifiedDbms() in (DBMS.PGSQL, DBMS.ORACLE, DBMS.SQLITE):
|
||||
elif Backend.getIdentifiedDbms() in (DBMS.PGSQL, DBMS.ORACLE, DBMS.SQLITE):
|
||||
concatenatedQuery = "%s||%s" % (query1, query2)
|
||||
|
||||
elif backend.getIdentifiedDbms() in (DBMS.MSSQL, DBMS.SYBASE):
|
||||
elif Backend.getIdentifiedDbms() in (DBMS.MSSQL, DBMS.SYBASE):
|
||||
concatenatedQuery = "%s+%s" % (query1, query2)
|
||||
|
||||
return concatenatedQuery
|
||||
@@ -444,7 +444,7 @@ class Agent:
|
||||
concatenatedQuery = query
|
||||
fieldsSelectFrom, fieldsSelect, fieldsNoSelect, fieldsSelectTop, fieldsSelectCase, _, fieldsToCastStr, fieldsExists = self.getFields(query)
|
||||
|
||||
if backend.getIdentifiedDbms() == DBMS.MYSQL:
|
||||
if Backend.getIdentifiedDbms() == DBMS.MYSQL:
|
||||
if fieldsExists:
|
||||
concatenatedQuery = concatenatedQuery.replace("SELECT ", "CONCAT('%s'," % kb.misc.start, 1)
|
||||
concatenatedQuery += ",'%s')" % kb.misc.stop
|
||||
@@ -460,7 +460,7 @@ class Agent:
|
||||
elif fieldsNoSelect:
|
||||
concatenatedQuery = "CONCAT('%s',%s,'%s')" % (kb.misc.start, concatenatedQuery, kb.misc.stop)
|
||||
|
||||
elif backend.getIdentifiedDbms() in (DBMS.PGSQL, DBMS.ORACLE, DBMS.SQLITE):
|
||||
elif Backend.getIdentifiedDbms() in (DBMS.PGSQL, DBMS.ORACLE, DBMS.SQLITE):
|
||||
if fieldsExists:
|
||||
concatenatedQuery = concatenatedQuery.replace("SELECT ", "'%s'||" % kb.misc.start, 1)
|
||||
concatenatedQuery += "||'%s'" % kb.misc.stop
|
||||
@@ -476,7 +476,7 @@ class Agent:
|
||||
elif fieldsNoSelect:
|
||||
concatenatedQuery = "'%s'||%s||'%s'" % (kb.misc.start, concatenatedQuery, kb.misc.stop)
|
||||
|
||||
elif backend.getIdentifiedDbms() in (DBMS.MSSQL, DBMS.SYBASE):
|
||||
elif Backend.getIdentifiedDbms() in (DBMS.MSSQL, DBMS.SYBASE):
|
||||
if fieldsExists:
|
||||
concatenatedQuery = concatenatedQuery.replace("SELECT ", "'%s'+" % kb.misc.start, 1)
|
||||
concatenatedQuery += "+'%s'" % kb.misc.stop
|
||||
@@ -545,8 +545,8 @@ class Agent:
|
||||
intoRegExp = intoRegExp.group(1)
|
||||
query = query[:query.index(intoRegExp)]
|
||||
|
||||
if backend.getIdentifiedDbms() in FROM_TABLE and inbandQuery.endswith(FROM_TABLE[backend.getIdentifiedDbms()]):
|
||||
inbandQuery = inbandQuery[:-len(FROM_TABLE[backend.getIdentifiedDbms()])]
|
||||
if Backend.getIdentifiedDbms() in FROM_TABLE and inbandQuery.endswith(FROM_TABLE[Backend.getIdentifiedDbms()]):
|
||||
inbandQuery = inbandQuery[:-len(FROM_TABLE[Backend.getIdentifiedDbms()])]
|
||||
|
||||
for element in range(0, count):
|
||||
if element > 0:
|
||||
@@ -565,9 +565,9 @@ class Agent:
|
||||
conditionIndex = query.index(" FROM ")
|
||||
inbandQuery += query[conditionIndex:]
|
||||
|
||||
if backend.getIdentifiedDbms() in FROM_TABLE:
|
||||
if Backend.getIdentifiedDbms() in FROM_TABLE:
|
||||
if " FROM " not in inbandQuery or "(CASE " in inbandQuery:
|
||||
inbandQuery += FROM_TABLE[backend.getIdentifiedDbms()]
|
||||
inbandQuery += FROM_TABLE[Backend.getIdentifiedDbms()]
|
||||
|
||||
if intoRegExp:
|
||||
inbandQuery += intoRegExp
|
||||
@@ -584,8 +584,8 @@ class Agent:
|
||||
else:
|
||||
inbandQuery += char
|
||||
|
||||
if backend.getIdentifiedDbms() in FROM_TABLE:
|
||||
inbandQuery += FROM_TABLE[backend.getIdentifiedDbms()]
|
||||
if Backend.getIdentifiedDbms() in FROM_TABLE:
|
||||
inbandQuery += FROM_TABLE[Backend.getIdentifiedDbms()]
|
||||
|
||||
inbandQuery = self.suffixQuery(inbandQuery, comment, suffix)
|
||||
|
||||
@@ -614,21 +614,21 @@ class Agent:
|
||||
"""
|
||||
|
||||
limitedQuery = query
|
||||
limitStr = queries[backend.getIdentifiedDbms()].limit.query
|
||||
limitStr = queries[Backend.getIdentifiedDbms()].limit.query
|
||||
fromIndex = limitedQuery.index(" FROM ")
|
||||
untilFrom = limitedQuery[:fromIndex]
|
||||
fromFrom = limitedQuery[fromIndex+1:]
|
||||
orderBy = False
|
||||
|
||||
if backend.getIdentifiedDbms() in (DBMS.MYSQL, DBMS.PGSQL, DBMS.SQLITE):
|
||||
limitStr = queries[backend.getIdentifiedDbms()].limit.query % (num, 1)
|
||||
if Backend.getIdentifiedDbms() in (DBMS.MYSQL, DBMS.PGSQL, DBMS.SQLITE):
|
||||
limitStr = queries[Backend.getIdentifiedDbms()].limit.query % (num, 1)
|
||||
limitedQuery += " %s" % limitStr
|
||||
|
||||
elif backend.getIdentifiedDbms() == DBMS.FIREBIRD:
|
||||
limitStr = queries[backend.getIdentifiedDbms()].limit.query % (num+1, num+1)
|
||||
elif Backend.getIdentifiedDbms() == DBMS.FIREBIRD:
|
||||
limitStr = queries[Backend.getIdentifiedDbms()].limit.query % (num+1, num+1)
|
||||
limitedQuery += " %s" % limitStr
|
||||
|
||||
elif backend.getIdentifiedDbms() == DBMS.ORACLE:
|
||||
elif Backend.getIdentifiedDbms() == DBMS.ORACLE:
|
||||
if " ORDER BY " in limitedQuery and "(SELECT " in limitedQuery:
|
||||
orderBy = limitedQuery[limitedQuery.index(" ORDER BY "):]
|
||||
limitedQuery = limitedQuery[:limitedQuery.index(" ORDER BY ")]
|
||||
@@ -640,7 +640,7 @@ class Agent:
|
||||
limitedQuery = limitedQuery % fromFrom
|
||||
limitedQuery += "=%d" % (num + 1)
|
||||
|
||||
elif backend.getIdentifiedDbms() in (DBMS.MSSQL, DBMS.SYBASE):
|
||||
elif Backend.getIdentifiedDbms() in (DBMS.MSSQL, DBMS.SYBASE):
|
||||
forgeNotIn = True
|
||||
|
||||
if " ORDER BY " in limitedQuery:
|
||||
@@ -654,7 +654,7 @@ class Agent:
|
||||
limitedQuery = limitedQuery.replace("DISTINCT %s" % notDistinct, notDistinct)
|
||||
|
||||
if limitedQuery.startswith("SELECT TOP ") or limitedQuery.startswith("TOP "):
|
||||
topNums = re.search(queries[backend.getIdentifiedDbms()].limitregexp.query, limitedQuery, re.I)
|
||||
topNums = re.search(queries[Backend.getIdentifiedDbms()].limitregexp.query, limitedQuery, re.I)
|
||||
|
||||
if topNums:
|
||||
topNums = topNums.groups()
|
||||
@@ -700,8 +700,8 @@ class Agent:
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
if backend.getIdentifiedDbms() is not None and hasattr(queries[backend.getIdentifiedDbms()], "case"):
|
||||
return queries[backend.getIdentifiedDbms()].case.query % expression
|
||||
if Backend.getIdentifiedDbms() is not None and hasattr(queries[Backend.getIdentifiedDbms()], "case"):
|
||||
return queries[Backend.getIdentifiedDbms()].case.query % expression
|
||||
else:
|
||||
return expression
|
||||
|
||||
|
||||
@@ -127,6 +127,279 @@ class DynamicContentItem:
|
||||
self.lineContentBefore = lineContentBefore
|
||||
self.lineContentAfter = lineContentAfter
|
||||
|
||||
class Format:
|
||||
@staticmethod
|
||||
def humanize(values, chain=" or "):
|
||||
strJoin = "|".join([v for v in values])
|
||||
|
||||
return strJoin.replace("|", chain)
|
||||
|
||||
# Get methods
|
||||
@staticmethod
|
||||
def getDbms(versions=None):
|
||||
"""
|
||||
Format the back-end DBMS fingerprint value and return its
|
||||
values formatted as a human readable string.
|
||||
|
||||
@return: detected back-end DBMS based upon fingerprint techniques.
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
if versions is None and Backend.getVersionList():
|
||||
versions = Backend.getVersionList()
|
||||
|
||||
if versions is None:
|
||||
return Backend.getDbms()
|
||||
else:
|
||||
return "%s %s" % (Backend.getDbms(), " and ".join([v for v in versions]))
|
||||
|
||||
@staticmethod
|
||||
def getErrorParsedDBMSes():
|
||||
"""
|
||||
Parses the knowledge base htmlFp list and return its values
|
||||
formatted as a human readable string.
|
||||
|
||||
@return: list of possible back-end DBMS based upon error messages
|
||||
parsing.
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
htmlParsed = ""
|
||||
|
||||
if len(kb.htmlFp) == 0:
|
||||
return None
|
||||
elif len(kb.htmlFp) == 1:
|
||||
htmlParsed = kb.htmlFp[0]
|
||||
elif len(kb.htmlFp) > 1:
|
||||
htmlParsed = " or ".join([htmlFp for htmlFp in kb.htmlFp])
|
||||
|
||||
return htmlParsed
|
||||
|
||||
@staticmethod
|
||||
def getOs(target, info):
|
||||
"""
|
||||
Formats the back-end operating system fingerprint value
|
||||
and return its values formatted as a human readable string.
|
||||
|
||||
Example of info (kb.headersFp) dictionary:
|
||||
|
||||
{
|
||||
'distrib': set(['Ubuntu']),
|
||||
'type': set(['Linux']),
|
||||
'technology': set(['PHP 5.2.6', 'Apache 2.2.9']),
|
||||
'release': set(['8.10'])
|
||||
}
|
||||
|
||||
Example of info (kb.bannerFp) dictionary:
|
||||
|
||||
{
|
||||
'sp': set(['Service Pack 4']),
|
||||
'dbmsVersion': '8.00.194',
|
||||
'dbmsServicePack': '0',
|
||||
'distrib': set(['2000']),
|
||||
'dbmsRelease': '2000',
|
||||
'type': set(['Windows'])
|
||||
}
|
||||
|
||||
@return: detected back-end operating system based upon fingerprint
|
||||
techniques.
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
infoStr = ""
|
||||
|
||||
if info and "type" in info:
|
||||
infoStr += "%s operating system: %s" % (target, Format.humanize(info["type"]))
|
||||
|
||||
if "distrib" in info:
|
||||
infoStr += " %s" % Format.humanize(info["distrib"])
|
||||
|
||||
if "release" in info:
|
||||
infoStr += " %s" % Format.humanize(info["release"])
|
||||
|
||||
if "sp" in info:
|
||||
infoStr += " %s" % Format.humanize(info["sp"])
|
||||
|
||||
if "codename" in info:
|
||||
infoStr += " (%s)" % Format.humanize(info["codename"])
|
||||
|
||||
if "technology" in info:
|
||||
infoStr += "\nweb application technology: %s" % Format.humanize(info["technology"], ", ")
|
||||
|
||||
return infoStr
|
||||
|
||||
class Backend:
|
||||
# Set methods
|
||||
@staticmethod
|
||||
def setDbms(dbms):
|
||||
dbms = aliasToDbmsEnum(dbms)
|
||||
|
||||
if dbms is None:
|
||||
return None
|
||||
|
||||
# Little precaution, in theory this condition should always be false
|
||||
elif kb.dbms is not None and kb.dbms != dbms:
|
||||
msg = "sqlmap previously fingerprinted back-end DBMS "
|
||||
msg += "%s. However now it has been fingerprinted " % kb.dbms
|
||||
msg += "to be %s. " % dbms
|
||||
msg += "Please, specify which DBMS is "
|
||||
msg += "correct [%s (default)/%s] " % (kb.dbms, dbms)
|
||||
|
||||
while True:
|
||||
inp = readInput(msg, default=kb.dbms)
|
||||
|
||||
if aliasToDbmsEnum(inp) == kb.dbms:
|
||||
break
|
||||
elif aliasToDbmsEnum(inp) == dbms:
|
||||
kb.dbms = aliasToDbmsEnum(inp)
|
||||
break
|
||||
else:
|
||||
warnMsg = "invalid value"
|
||||
logger.warn(warnMsg)
|
||||
|
||||
elif kb.dbms is None:
|
||||
kb.dbms = aliasToDbmsEnum(dbms)
|
||||
|
||||
return kb.dbms
|
||||
|
||||
@staticmethod
|
||||
def setVersion(version):
|
||||
if isinstance(version, basestring):
|
||||
kb.dbmsVersion = [ version ]
|
||||
|
||||
return kb.dbmsVersion
|
||||
|
||||
@staticmethod
|
||||
def setVersionList(versionsList):
|
||||
if isinstance(versionsList, list):
|
||||
kb.dbmsVersion = versionsList
|
||||
elif isinstance(version, basestring):
|
||||
Backend.setVersion(versionsList)
|
||||
else:
|
||||
logger.error("invalid format of versionsList")
|
||||
|
||||
@staticmethod
|
||||
def forceDbms(dbms):
|
||||
kb.misc.forcedDbms = aliasToDbmsEnum(dbms)
|
||||
|
||||
@staticmethod
|
||||
def flushForcedDbms():
|
||||
kb.misc.forcedDbms = None
|
||||
|
||||
@staticmethod
|
||||
def setOs(os):
|
||||
if os is None:
|
||||
return None
|
||||
|
||||
# Little precaution, in theory this condition should always be false
|
||||
elif kb.os is not None and kb.os != os:
|
||||
msg = "sqlmap previously fingerprinted back-end DBMS "
|
||||
msg += "operating system %s. However now it has " % kb.os
|
||||
msg += "been fingerprinted to be %s. " % os
|
||||
msg += "Please, specify which OS is "
|
||||
msg += "correct [%s (default)/%s] " % (kb.os, os)
|
||||
|
||||
while True:
|
||||
inp = readInput(msg, default=kb.os)
|
||||
|
||||
if inp == kb.os:
|
||||
break
|
||||
elif inp == os:
|
||||
kb.os = inp
|
||||
break
|
||||
else:
|
||||
warnMsg = "invalid value"
|
||||
logger.warn(warnMsg)
|
||||
|
||||
elif kb.os is None:
|
||||
kb.os = os
|
||||
|
||||
return kb.os
|
||||
|
||||
# Get methods
|
||||
@staticmethod
|
||||
def getForcedDbms():
|
||||
return aliasToDbmsEnum(kb.misc.forcedDbms)
|
||||
|
||||
@staticmethod
|
||||
def getDbms():
|
||||
return aliasToDbmsEnum(kb.dbms)
|
||||
|
||||
@staticmethod
|
||||
def getErrorParsedDBMSes():
|
||||
"""
|
||||
Returns array with parsed DBMS names till now
|
||||
|
||||
This functions is called to:
|
||||
|
||||
1. Sort the tests, getSortedInjectionTests() - detection phase.
|
||||
2. Ask user whether or not skip specific DBMS tests in detection phase,
|
||||
lib/controller/checks.py - detection phase.
|
||||
3. Sort the fingerprint of the DBMS, lib/controller/handler.py -
|
||||
fingerprint phase.
|
||||
"""
|
||||
|
||||
return kb.htmlFp
|
||||
|
||||
@staticmethod
|
||||
def getIdentifiedDbms():
|
||||
dbms = None
|
||||
|
||||
if Backend.getForcedDbms() is not None:
|
||||
dbms = Backend.getForcedDbms()
|
||||
elif Backend.getDbms() is not None:
|
||||
dbms = kb.dbms
|
||||
elif conf.dbms is not None:
|
||||
dbms = conf.dbms
|
||||
elif len(Backend.getErrorParsedDBMSes()) > 0:
|
||||
dbms = Backend.getErrorParsedDBMSes()[0]
|
||||
|
||||
return aliasToDbmsEnum(dbms)
|
||||
|
||||
@staticmethod
|
||||
def getVersion():
|
||||
if len(kb.dbmsVersion) > 0:
|
||||
return kb.dbmsVersion[0]
|
||||
else:
|
||||
return None
|
||||
|
||||
@staticmethod
|
||||
def getVersionList():
|
||||
if len(kb.dbmsVersion) > 0:
|
||||
return kb.dbmsVersion
|
||||
else:
|
||||
return None
|
||||
|
||||
# Comparison methods
|
||||
@staticmethod
|
||||
def isDbms(dbms):
|
||||
return Backend.getDbms() is not None and Backend.getDbms() == aliasToDbmsEnum(dbms)
|
||||
|
||||
@staticmethod
|
||||
def isDbmsWithin(aliases):
|
||||
return Backend.getDbms() is not None and Backend.getDbms().lower() in aliases
|
||||
|
||||
@staticmethod
|
||||
def isVersion(version):
|
||||
return Backend.getVersion() is not None and Backend.getVersion() == version
|
||||
|
||||
@staticmethod
|
||||
def isVersionWithin(versionList):
|
||||
if Backend.getVersionList() is None:
|
||||
return False
|
||||
|
||||
for dbmsVersion in Backend.getVersionList():
|
||||
if dbmsVersion == UNKNOWN_DBMS_VERSION:
|
||||
continue
|
||||
elif dbmsVersion in versionList:
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
@staticmethod
|
||||
def isVersionGreaterOrEqualThan(version):
|
||||
return Backend.getVersion() is not None and str(Backend.getVersion()) >= str(version)
|
||||
|
||||
def paramToDict(place, parameters=None):
|
||||
"""
|
||||
Split the parameters into names and values, check if these parameters
|
||||
@@ -512,14 +785,14 @@ def parsePasswordHash(password):
|
||||
if not password or password == " ":
|
||||
password = "NULL"
|
||||
|
||||
if backend.getIdentifiedDbms() == DBMS.MSSQL and password != "NULL" and isHexEncodedString(password):
|
||||
if Backend.getIdentifiedDbms() == DBMS.MSSQL and password != "NULL" and isHexEncodedString(password):
|
||||
hexPassword = password
|
||||
password = "%s\n" % hexPassword
|
||||
password += "%sheader: %s\n" % (blank, hexPassword[:6])
|
||||
password += "%ssalt: %s\n" % (blank, hexPassword[6:14])
|
||||
password += "%smixedcase: %s\n" % (blank, hexPassword[14:54])
|
||||
|
||||
if not backend.isVersionWithin(("2005", "2008")):
|
||||
if not Backend.isVersionWithin(("2005", "2008")):
|
||||
password += "%suppercase: %s" % (blank, hexPassword[54:])
|
||||
|
||||
return password
|
||||
@@ -817,25 +1090,25 @@ def parseUnionPage(output, expression, partial=False, condition=None, sort=True)
|
||||
def getDelayQuery(andCond=False):
|
||||
query = None
|
||||
|
||||
if backend.getIdentifiedDbms() in (DBMS.MYSQL, DBMS.PGSQL):
|
||||
if Backend.getIdentifiedDbms() in (DBMS.MYSQL, DBMS.PGSQL):
|
||||
if not kb.data.banner:
|
||||
conf.dbmsHandler.getVersionFromBanner()
|
||||
|
||||
banVer = kb.bannerFp["dbmsVersion"] if 'dbmsVersion' in kb.bannerFp else None
|
||||
|
||||
if banVer is None or (backend.getIdentifiedDbms() == DBMS.MYSQL and banVer >= "5.0.12") or (backend.getIdentifiedDbms() == DBMS.PGSQL and banVer >= "8.2"):
|
||||
query = queries[backend.getIdentifiedDbms()].timedelay.query % conf.timeSec
|
||||
if banVer is None or (Backend.getIdentifiedDbms() == DBMS.MYSQL and banVer >= "5.0.12") or (Backend.getIdentifiedDbms() == DBMS.PGSQL and banVer >= "8.2"):
|
||||
query = queries[Backend.getIdentifiedDbms()].timedelay.query % conf.timeSec
|
||||
else:
|
||||
query = queries[backend.getIdentifiedDbms()].timedelay.query2 % conf.timeSec
|
||||
elif backend.getIdentifiedDbms() == DBMS.FIREBIRD:
|
||||
query = queries[backend.getIdentifiedDbms()].timedelay.query
|
||||
query = queries[Backend.getIdentifiedDbms()].timedelay.query2 % conf.timeSec
|
||||
elif Backend.getIdentifiedDbms() == DBMS.FIREBIRD:
|
||||
query = queries[Backend.getIdentifiedDbms()].timedelay.query
|
||||
else:
|
||||
query = queries[backend.getIdentifiedDbms()].timedelay.query % conf.timeSec
|
||||
query = queries[Backend.getIdentifiedDbms()].timedelay.query % conf.timeSec
|
||||
|
||||
if andCond:
|
||||
if backend.getIdentifiedDbms() in ( DBMS.MYSQL, DBMS.SQLITE ):
|
||||
if Backend.getIdentifiedDbms() in ( DBMS.MYSQL, DBMS.SQLITE ):
|
||||
query = query.replace("SELECT ", "")
|
||||
elif backend.getIdentifiedDbms() == DBMS.FIREBIRD:
|
||||
elif Backend.getIdentifiedDbms() == DBMS.FIREBIRD:
|
||||
query = "(%s)>0" % query
|
||||
|
||||
return query
|
||||
@@ -1791,8 +2064,8 @@ def isDBMSVersionAtLeast(version):
|
||||
|
||||
retVal = None
|
||||
|
||||
if backend.getVersion() and backend.getVersion() != UNKNOWN_DBMS_VERSION:
|
||||
value = backend.getVersion().replace(" ", "").rstrip('.')
|
||||
if Backend.getVersion() and Backend.getVersion() != UNKNOWN_DBMS_VERSION:
|
||||
value = Backend.getVersion().replace(" ", "").rstrip('.')
|
||||
|
||||
while True:
|
||||
index = value.find('.', value.find('.') + 1)
|
||||
@@ -1910,14 +2183,14 @@ def getSortedInjectionTests():
|
||||
retVal = SORTORDER.LAST
|
||||
|
||||
elif 'details' in test and 'dbms' in test.details:
|
||||
if test.details.dbms in backend.getErrorParsedDBMSes():
|
||||
if test.details.dbms in Backend.getErrorParsedDBMSes():
|
||||
retVal = SORTORDER.SECOND
|
||||
else:
|
||||
retVal = SORTORDER.THIRD
|
||||
|
||||
return retVal
|
||||
|
||||
if backend.getErrorParsedDBMSes():
|
||||
if Backend.getErrorParsedDBMSes():
|
||||
retVal = sorted(retVal, key=priorityFunction)
|
||||
|
||||
return retVal
|
||||
@@ -1955,279 +2228,6 @@ def unicodeToSafeHTMLValue(value):
|
||||
|
||||
return retVal
|
||||
|
||||
class format:
|
||||
@staticmethod
|
||||
def humanize(values, chain=" or "):
|
||||
strJoin = "|".join([v for v in values])
|
||||
|
||||
return strJoin.replace("|", chain)
|
||||
|
||||
# Get methods
|
||||
@staticmethod
|
||||
def getDbms(versions=None):
|
||||
"""
|
||||
Format the back-end DBMS fingerprint value and return its
|
||||
values formatted as a human readable string.
|
||||
|
||||
@return: detected back-end DBMS based upon fingerprint techniques.
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
if versions is None and backend.getVersionList():
|
||||
versions = backend.getVersionList()
|
||||
|
||||
if versions is None:
|
||||
return backend.getDbms()
|
||||
else:
|
||||
return "%s %s" % (backend.getDbms(), " and ".join([v for v in versions]))
|
||||
|
||||
@staticmethod
|
||||
def getErrorParsedDBMSes():
|
||||
"""
|
||||
Parses the knowledge base htmlFp list and return its values
|
||||
formatted as a human readable string.
|
||||
|
||||
@return: list of possible back-end DBMS based upon error messages
|
||||
parsing.
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
htmlParsed = ""
|
||||
|
||||
if len(kb.htmlFp) == 0:
|
||||
return None
|
||||
elif len(kb.htmlFp) == 1:
|
||||
htmlParsed = kb.htmlFp[0]
|
||||
elif len(kb.htmlFp) > 1:
|
||||
htmlParsed = " or ".join([htmlFp for htmlFp in kb.htmlFp])
|
||||
|
||||
return htmlParsed
|
||||
|
||||
@staticmethod
|
||||
def getOs(target, info):
|
||||
"""
|
||||
Formats the back-end operating system fingerprint value
|
||||
and return its values formatted as a human readable string.
|
||||
|
||||
Example of info (kb.headersFp) dictionary:
|
||||
|
||||
{
|
||||
'distrib': set(['Ubuntu']),
|
||||
'type': set(['Linux']),
|
||||
'technology': set(['PHP 5.2.6', 'Apache 2.2.9']),
|
||||
'release': set(['8.10'])
|
||||
}
|
||||
|
||||
Example of info (kb.bannerFp) dictionary:
|
||||
|
||||
{
|
||||
'sp': set(['Service Pack 4']),
|
||||
'dbmsVersion': '8.00.194',
|
||||
'dbmsServicePack': '0',
|
||||
'distrib': set(['2000']),
|
||||
'dbmsRelease': '2000',
|
||||
'type': set(['Windows'])
|
||||
}
|
||||
|
||||
@return: detected back-end operating system based upon fingerprint
|
||||
techniques.
|
||||
@rtype: C{str}
|
||||
"""
|
||||
|
||||
infoStr = ""
|
||||
|
||||
if info and "type" in info:
|
||||
infoStr += "%s operating system: %s" % (target, format.humanize(info["type"]))
|
||||
|
||||
if "distrib" in info:
|
||||
infoStr += " %s" % format.humanize(info["distrib"])
|
||||
|
||||
if "release" in info:
|
||||
infoStr += " %s" % format.humanize(info["release"])
|
||||
|
||||
if "sp" in info:
|
||||
infoStr += " %s" % format.humanize(info["sp"])
|
||||
|
||||
if "codename" in info:
|
||||
infoStr += " (%s)" % format.humanize(info["codename"])
|
||||
|
||||
if "technology" in info:
|
||||
infoStr += "\nweb application technology: %s" % format.humanize(info["technology"], ", ")
|
||||
|
||||
return infoStr
|
||||
|
||||
class backend:
|
||||
# Set methods
|
||||
@staticmethod
|
||||
def setDbms(dbms):
|
||||
dbms = aliasToDbmsEnum(dbms)
|
||||
|
||||
if dbms is None:
|
||||
return None
|
||||
|
||||
# Little precaution, in theory this condition should always be false
|
||||
elif kb.dbms is not None and kb.dbms != dbms:
|
||||
msg = "sqlmap previously fingerprinted back-end DBMS "
|
||||
msg += "%s. However now it has been fingerprinted " % kb.dbms
|
||||
msg += "to be %s. " % dbms
|
||||
msg += "Please, specify which DBMS is "
|
||||
msg += "correct [%s (default)/%s] " % (kb.dbms, dbms)
|
||||
|
||||
while True:
|
||||
inp = readInput(msg, default=kb.dbms)
|
||||
|
||||
if aliasToDbmsEnum(inp) == kb.dbms:
|
||||
break
|
||||
elif aliasToDbmsEnum(inp) == dbms:
|
||||
kb.dbms = aliasToDbmsEnum(inp)
|
||||
break
|
||||
else:
|
||||
warnMsg = "invalid value"
|
||||
logger.warn(warnMsg)
|
||||
|
||||
elif kb.dbms is None:
|
||||
kb.dbms = aliasToDbmsEnum(dbms)
|
||||
|
||||
return kb.dbms
|
||||
|
||||
@staticmethod
|
||||
def setVersion(version):
|
||||
if isinstance(version, basestring):
|
||||
kb.dbmsVersion = [ version ]
|
||||
|
||||
return kb.dbmsVersion
|
||||
|
||||
@staticmethod
|
||||
def setVersionList(versionsList):
|
||||
if isinstance(versionsList, list):
|
||||
kb.dbmsVersion = versionsList
|
||||
elif isinstance(version, basestring):
|
||||
backend.setVersion(versionsList)
|
||||
else:
|
||||
logger.error("invalid format of versionsList")
|
||||
|
||||
@staticmethod
|
||||
def forceDbms(dbms):
|
||||
kb.misc.forcedDbms = aliasToDbmsEnum(dbms)
|
||||
|
||||
@staticmethod
|
||||
def flushForcedDbms():
|
||||
kb.misc.forcedDbms = None
|
||||
|
||||
@staticmethod
|
||||
def setOs(os):
|
||||
if os is None:
|
||||
return None
|
||||
|
||||
# Little precaution, in theory this condition should always be false
|
||||
elif kb.os is not None and kb.os != os:
|
||||
msg = "sqlmap previously fingerprinted back-end DBMS "
|
||||
msg += "operating system %s. However now it has " % kb.os
|
||||
msg += "been fingerprinted to be %s. " % os
|
||||
msg += "Please, specify which OS is "
|
||||
msg += "correct [%s (default)/%s] " % (kb.os, os)
|
||||
|
||||
while True:
|
||||
inp = readInput(msg, default=kb.os)
|
||||
|
||||
if inp == kb.os:
|
||||
break
|
||||
elif inp == os:
|
||||
kb.os = inp
|
||||
break
|
||||
else:
|
||||
warnMsg = "invalid value"
|
||||
logger.warn(warnMsg)
|
||||
|
||||
elif kb.os is None:
|
||||
kb.os = os
|
||||
|
||||
return kb.os
|
||||
|
||||
# Get methods
|
||||
@staticmethod
|
||||
def getForcedDbms():
|
||||
return aliasToDbmsEnum(kb.misc.forcedDbms)
|
||||
|
||||
@staticmethod
|
||||
def getDbms():
|
||||
return aliasToDbmsEnum(kb.dbms)
|
||||
|
||||
@staticmethod
|
||||
def getErrorParsedDBMSes():
|
||||
"""
|
||||
Returns array with parsed DBMS names till now
|
||||
|
||||
This functions is called to:
|
||||
|
||||
1. Sort the tests, getSortedInjectionTests() - detection phase.
|
||||
2. Ask user whether or not skip specific DBMS tests in detection phase,
|
||||
lib/controller/checks.py - detection phase.
|
||||
3. Sort the fingerprint of the DBMS, lib/controller/handler.py -
|
||||
fingerprint phase.
|
||||
"""
|
||||
|
||||
return kb.htmlFp
|
||||
|
||||
@staticmethod
|
||||
def getIdentifiedDbms():
|
||||
dbms = None
|
||||
|
||||
if backend.getForcedDbms() is not None:
|
||||
dbms = backend.getForcedDbms()
|
||||
elif backend.getDbms() is not None:
|
||||
dbms = kb.dbms
|
||||
elif conf.dbms is not None:
|
||||
dbms = conf.dbms
|
||||
elif len(backend.getErrorParsedDBMSes()) > 0:
|
||||
dbms = backend.getErrorParsedDBMSes()[0]
|
||||
|
||||
return aliasToDbmsEnum(dbms)
|
||||
|
||||
@staticmethod
|
||||
def getVersion():
|
||||
if len(kb.dbmsVersion) > 0:
|
||||
return kb.dbmsVersion[0]
|
||||
else:
|
||||
return None
|
||||
|
||||
@staticmethod
|
||||
def getVersionList():
|
||||
if len(kb.dbmsVersion) > 0:
|
||||
return kb.dbmsVersion
|
||||
else:
|
||||
return None
|
||||
|
||||
# Comparison methods
|
||||
@staticmethod
|
||||
def isDbms(dbms):
|
||||
return backend.getDbms() is not None and backend.getDbms() == aliasToDbmsEnum(dbms)
|
||||
|
||||
@staticmethod
|
||||
def isDbmsWithin(aliases):
|
||||
return backend.getDbms() is not None and backend.getDbms().lower() in aliases
|
||||
|
||||
@staticmethod
|
||||
def isVersion(version):
|
||||
return backend.getVersion() is not None and backend.getVersion() == version
|
||||
|
||||
@staticmethod
|
||||
def isVersionWithin(versionList):
|
||||
if backend.getVersionList() is None:
|
||||
return False
|
||||
|
||||
for dbmsVersion in backend.getVersionList():
|
||||
if dbmsVersion == UNKNOWN_DBMS_VERSION:
|
||||
continue
|
||||
elif dbmsVersion in versionList:
|
||||
return True
|
||||
|
||||
return False
|
||||
|
||||
@staticmethod
|
||||
def isVersionGreaterOrEqualThan(version):
|
||||
return backend.getVersion() is not None and str(backend.getVersion()) >= str(version)
|
||||
|
||||
def showHttpErrorCodes():
|
||||
"""
|
||||
Shows all HTTP error codes raised till now
|
||||
|
||||
@@ -24,7 +24,7 @@ from extra.clientform.clientform import ParseResponse
|
||||
from extra.keepalive import keepalive
|
||||
from extra.xmlobject import xmlobject
|
||||
from lib.controller.checks import checkConnection
|
||||
from lib.core.common import backend
|
||||
from lib.core.common import Backend
|
||||
from lib.core.common import extractRegexResult
|
||||
from lib.core.common import getConsoleWidth
|
||||
from lib.core.common import getFileItems
|
||||
@@ -595,7 +595,7 @@ def __setDBMS():
|
||||
dbmsRegExp = re.search("%s ([\d\.]+)" % firstRegExp, conf.dbms, re.I)
|
||||
|
||||
if dbmsRegExp:
|
||||
backend.setVersion(str(dbmsRegExp.group(2)))
|
||||
Backend.setVersion(str(dbmsRegExp.group(2)))
|
||||
|
||||
if conf.dbms not in SUPPORTED_DBMS:
|
||||
errMsg = "you provided an unsupported back-end database management "
|
||||
@@ -1255,7 +1255,7 @@ def __setKnowledgeBaseAttributes(flushAll=True):
|
||||
def __saveCmdline():
|
||||
"""
|
||||
Saves the command line options on a sqlmap configuration INI file
|
||||
format.
|
||||
Format.
|
||||
"""
|
||||
|
||||
if not conf.saveCmdline:
|
||||
|
||||
@@ -9,8 +9,8 @@ See the file 'doc/COPYING' for copying permission
|
||||
|
||||
import re
|
||||
|
||||
from lib.core.common import backend
|
||||
from lib.core.common import format
|
||||
from lib.core.common import Backend
|
||||
from lib.core.common import Format
|
||||
from lib.core.common import dataToSessionFile
|
||||
from lib.core.common import getFilteredPageContent
|
||||
from lib.core.common import readInput
|
||||
@@ -91,9 +91,9 @@ def setDbms(dbms):
|
||||
if dbmsRegExp:
|
||||
dbms = dbmsRegExp.group(1)
|
||||
|
||||
backend.setDbms(dbms)
|
||||
Backend.setDbms(dbms)
|
||||
|
||||
logger.info("the back-end DBMS is %s" % backend.getDbms())
|
||||
logger.info("the back-end DBMS is %s" % Backend.getDbms())
|
||||
|
||||
def setOs():
|
||||
"""
|
||||
@@ -120,15 +120,15 @@ def setOs():
|
||||
return
|
||||
|
||||
if "type" in kb.bannerFp:
|
||||
kb.os = format.humanize(kb.bannerFp["type"])
|
||||
kb.os = Format.humanize(kb.bannerFp["type"])
|
||||
infoMsg = "the back-end DBMS operating system is %s" % kb.os
|
||||
|
||||
if "distrib" in kb.bannerFp:
|
||||
kb.osVersion = format.humanize(kb.bannerFp["distrib"])
|
||||
kb.osVersion = Format.humanize(kb.bannerFp["distrib"])
|
||||
infoMsg += " %s" % kb.osVersion
|
||||
|
||||
if "sp" in kb.bannerFp:
|
||||
kb.osSP = int(format.humanize(kb.bannerFp["sp"]).replace("Service Pack ", ""))
|
||||
kb.osSP = int(Format.humanize(kb.bannerFp["sp"]).replace("Service Pack ", ""))
|
||||
|
||||
elif "sp" not in kb.bannerFp and kb.os == "Windows":
|
||||
kb.osSP = 0
|
||||
@@ -195,11 +195,11 @@ def resumeConfKb(expression, url, value):
|
||||
test = readInput(message, default="N")
|
||||
|
||||
if not test or test[0] in ("n", "N"):
|
||||
backend.setDbms(dbms)
|
||||
backend.setVersionList(dbmsVersion)
|
||||
Backend.setDbms(dbms)
|
||||
Backend.setVersionList(dbmsVersion)
|
||||
else:
|
||||
backend.setDbms(dbms)
|
||||
backend.setVersionList(dbmsVersion)
|
||||
Backend.setDbms(dbms)
|
||||
Backend.setVersionList(dbmsVersion)
|
||||
|
||||
elif expression == "OS" and url == conf.url:
|
||||
os = unSafeFormatString(value[:-1])
|
||||
@@ -236,7 +236,7 @@ def resumeConfKb(expression, url, value):
|
||||
if '.' in table:
|
||||
db, table = table.split('.')
|
||||
else:
|
||||
db = "%s%s" % (backend.getIdentifiedDbms(), METADB_SUFFIX)
|
||||
db = "%s%s" % (Backend.getIdentifiedDbms(), METADB_SUFFIX)
|
||||
|
||||
logMsg = "resuming brute forced table name "
|
||||
logMsg += "'%s' from session file" % table
|
||||
@@ -251,7 +251,7 @@ def resumeConfKb(expression, url, value):
|
||||
if '.' in table:
|
||||
db, table = table.split('.')
|
||||
else:
|
||||
db = "%s%s" % (backend.getIdentifiedDbms(), METADB_SUFFIX)
|
||||
db = "%s%s" % (Backend.getIdentifiedDbms(), METADB_SUFFIX)
|
||||
|
||||
logMsg = "resuming brute forced column name "
|
||||
logMsg += "'%s' for table '%s' from session file" % (colName, table)
|
||||
|
||||
@@ -12,7 +12,7 @@ import os
|
||||
import rlcompleter
|
||||
|
||||
from lib.core import readlineng as readline
|
||||
from lib.core.common import backend
|
||||
from lib.core.common import Backend
|
||||
from lib.core.data import kb
|
||||
from lib.core.data import logger
|
||||
from lib.core.data import paths
|
||||
@@ -35,7 +35,7 @@ def loadHistory():
|
||||
def queriesForAutoCompletion():
|
||||
autoComplQueries = {}
|
||||
|
||||
for item in queries[backend.getIdentifiedDbms()]._toflat():
|
||||
for item in queries[Backend.getIdentifiedDbms()]._toflat():
|
||||
if item._has_key('query') and len(item.query) > 1 and item._name != 'blind':
|
||||
autoComplQueries[item.query] = None
|
||||
|
||||
|
||||
@@ -7,12 +7,12 @@ Copyright (c) 2006-2010 sqlmap developers (http://sqlmap.sourceforge.net/)
|
||||
See the file 'doc/COPYING' for copying permission
|
||||
"""
|
||||
|
||||
from lib.core.common import backend
|
||||
from lib.core.common import Backend
|
||||
from lib.core.datatype import advancedDict
|
||||
|
||||
class Unescaper(advancedDict):
|
||||
def unescape(self, expression, quote=True, dbms=None):
|
||||
identifiedDbms = backend.getIdentifiedDbms()
|
||||
identifiedDbms = Backend.getIdentifiedDbms()
|
||||
|
||||
if not expression:
|
||||
return expression
|
||||
|
||||
@@ -76,7 +76,7 @@ ENTITIES = {'"':'"',"'":"'"}
|
||||
|
||||
class XMLDump:
|
||||
'''
|
||||
This class purpose is to dump the data into an xml format.
|
||||
This class purpose is to dump the data into an xml Format.
|
||||
The format of the xml file is described in the scheme file xml/sqlmap.xsd
|
||||
'''
|
||||
|
||||
@@ -118,7 +118,7 @@ class XMLDump:
|
||||
def __createTextNode(self,data):
|
||||
'''
|
||||
Creates a text node with utf8 data inside.
|
||||
The text is escaped to an fit the xml text format.
|
||||
The text is escaped to an fit the xml text Format.
|
||||
'''
|
||||
if data is None :
|
||||
return self.__doc.createTextNode(u'')
|
||||
@@ -129,7 +129,7 @@ class XMLDump:
|
||||
def __createAttribute(self,attrName,attrValue):
|
||||
'''
|
||||
Creates an attribute node with utf8 data inside.
|
||||
The text is escaped to an fit the xml text format.
|
||||
The text is escaped to an fit the xml text Format.
|
||||
'''
|
||||
attr = self.__doc.createAttribute(attrName)
|
||||
if attrValue is None :
|
||||
|
||||
Reference in New Issue
Block a user