Skip to content

Commit e6a5e8f

Browse files
committed
More style changes for Esperanto DBMS engine
1 parent c294098 commit e6a5e8f

3 files changed

Lines changed: 25 additions & 31 deletions

File tree

extra/esperanto/__main__.py

Lines changed: 16 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -360,7 +360,7 @@ def _httpOracle(url, data=None, cookie=None, headers=None, string=None, code=Non
360360

361361
if "[INFERENCE]" not in (url + (data or "")) and "*" not in (url + (data or "")):
362362
url = url + "*" # no marker given -> inject at the end of the URL by default
363-
print("[*] no injection marker ('*' or '[INFERENCE]') given; defaulting to end of URL: %s" % url)
363+
print("[i] no injection marker ('*' or '[INFERENCE]') given; defaulting to end of URL: %s" % url)
364364

365365
# ONE kept-alive connection reused across every probe. a blind dump is thousands of
366366
# requests; opening a fresh TCP+TLS handshake per probe (what urlopen does) is ~0.2s of
@@ -458,7 +458,7 @@ def _clean(body, cond):
458458
if wanted is None: # (3) similarity ratio floor
459459
mode, base = "ratio", {"t": tc, "f": fc}
460460
if string is None:
461-
print("[*] calibrated oracle: %s%s" % (mode, (" (%r)" % wanted) if mode in ("code", "autostring") else ""))
461+
print("[i] calibrated oracle: %s%s" % (mode, (" (%r)" % wanted) if mode in ("code", "autostring") else ""))
462462

463463
def classify(cond):
464464
body, status = fetch(cond)
@@ -598,43 +598,37 @@ def _report(esp, args):
598598
else:
599599
scope = cur
600600
if scope:
601-
print("[*] scoping to database/schema: %s" % scope)
601+
print("[i] scoping to database/schema: %s" % scope)
602602
if args.current_user:
603603
expr = esp.dialect.identity.get("user")
604604
print("[*] current user: %s" % (_scalar(esp, expr) if expr else "n/a"))
605605
if args.current_db:
606606
expr = esp.dialect.identity.get("database")
607607
print("[*] current database: %s" % (_scalar(esp, expr) if expr else "n/a"))
608608
if args.tables:
609-
print("[*] fetching tables ...")
609+
print("[i] fetching tables ...")
610610
print("[*] tables: %s" % ", ".join(esp.enumerate("table", schema=scope) or ["<none>"]))
611611
if args.columns:
612612
if not args.tbl:
613613
print("[!] --columns needs -T <table>")
614614
else:
615-
print("[*] fetching columns for '%s' ..." % args.tbl)
615+
print("[i] fetching columns for '%s' ..." % args.tbl)
616616
print("[*] columns of %s: %s" % (args.tbl, ", ".join(esp.columns(args.tbl, schema=scope) or ["<none>"])))
617-
if args.query:
618-
print("[*] fetching %s ..." % args.query)
619-
print("[*] %s = %s" % (args.query, _scalar(esp, args.query)))
620617
if args.dump:
621618
if not args.tbl:
622619
print("[!] --dump needs -T <table>")
623620
else:
624621
cols = [c.strip() for c in args.col.split(",")] if args.col else None
625622
if cols is None: # enumerate columns FIRST (own phase), so the
626-
print("[*] fetching columns for table '%s' ..." % args.tbl) # 'entries' phase below streams ROWS, not column names
623+
print("[i] fetching columns for table '%s' ..." % args.tbl) # 'entries' phase below streams ROWS, not column names
627624
cols = esp.columns(args.tbl, schema=scope) or None
628-
print("[*] fetching entries for table '%s' ..." % args.tbl)
629-
# NO silent internal 10-row cap: honor --stop, else dump ALL rows (by COUNT) and
630-
# always print whether the result is complete.
631-
if getattr(args, "stop", None):
632-
limit = args.stop
633-
else:
634-
try:
635-
limit = esp.extractInteger("(SELECT COUNT(*) FROM %s)" % esp.qualify(args.tbl, scope)) or 10
636-
except Exception:
637-
limit = 1 << 30
625+
print("[i] fetching entries for table '%s' ..." % args.tbl)
626+
# NO silent internal cap: dump ALL rows (bounded by the live COUNT) and always
627+
# print whether the result came back complete.
628+
try:
629+
limit = esp.extractInteger("(SELECT COUNT(*) FROM %s)" % esp.qualify(args.tbl, scope)) or 10
630+
except Exception:
631+
limit = 1 << 30
638632
result = esp.dump(args.tbl, columns=cols, schema=scope, limit=limit)
639633
if not result or not result["columns"]:
640634
print("[!] could not dump %s" % args.tbl)
@@ -698,11 +692,9 @@ def _format_action_invocation(self, action):
698692
parser.add_argument("--tables", action="store_true", help="enumerate tables")
699693
parser.add_argument("--columns", action="store_true", help="enumerate table columns (needs -T)")
700694
parser.add_argument("--dump", action="store_true", help="dump table entries (needs -T)")
701-
parser.add_argument("--sql-query", dest="query", help="run a custom scalar SQL query")
702695
parser.add_argument("-D", dest="db", help="database/schema to enumerate")
703696
parser.add_argument("-T", dest="tbl", help="table to enumerate")
704697
parser.add_argument("-C", dest="col", help="columns to dump (comma-separated)")
705-
parser.add_argument("--stop", type=int, help="max rows to dump (default: all)")
706698
# internal dev/test harness switches - functional but hidden from --help (--live drives the
707699
# local-Docker DBMS livetest; --waf is a livetest-only fault-injection mode, NOT a real WAF bypass)
708700
parser.add_argument("--live", action="store_true", help=argparse.SUPPRESS)
@@ -733,18 +725,18 @@ def _charLive(partial, total):
733725
shown = _previewFramed(partial)
734726
if shown is None:
735727
shown = partial
736-
_sys.stdout.write("\r\033[K[*] retrieved: %s" % _safeterm(shown[-200:]))
728+
_sys.stdout.write("\r\033[K[i] retrieved: %s" % _safeterm(shown[-200:]))
737729
if len(partial) >= total: # value complete -> keep it and drop to a new line
738730
_sys.stdout.write("\n")
739731
_sys.stdout.flush()
740732
def _plainLive(value): # piped/non-tty: one plain line per value, no control codes
741-
_sys.stdout.write("[*] retrieved: %s\n" % _safeterm(value))
733+
_sys.stdout.write("[i] retrieved: %s\n" % _safeterm(value))
742734
_sys.stdout.flush()
743735
if _tty:
744736
esp._charProgress = _charLive # animated char-by-char is the sole feedback on a terminal
745737
else:
746738
esp._progress = _plainLive # logs/pipes get clean per-value lines instead
747-
print("[*] discovering the back-end SQL dialect (agnostic mode) ...")
739+
print("[i] discovering the back-end SQL dialect (agnostic mode) ...")
748740
try:
749741
esp.discover()
750742
_report(esp, args)

extra/esperanto/enumeration.py

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -329,12 +329,14 @@ def _discoverKey(self, table, schema=None):
329329
# take the alphabetically-first key column (deterministic); a compound key
330330
# still yields a usable ordering column for the walk
331331
keyexpr = "(SELECT MIN(%s) FROM %s WHERE %s)" % (ncol, source, filt)
332-
with self._probePhase(): # a catalog that lacks this key structure errors -> "no key", not fatal
333-
present = self._ask("%s IS NOT NULL" % keyexpr)
334-
if present:
335-
res = self.extractResult(keyexpr) # a key COLUMN NAME becomes SQL -> require an EXACT value
336-
if res.exact and res.value: # (a case-ambiguous name could mis-target)
337-
return res.value
332+
# discovering the key COLUMN NAME is setup, not data - run it inside the probe phase so a
333+
# catalog lacking this key structure degrades to "no key" (not fatal) AND so the name does
334+
# not surface on the live "retrieved:" feed (it is a column name, not a dumped entry).
335+
with self._probePhase():
336+
if self._ask("%s IS NOT NULL" % keyexpr):
337+
res = self.extractResult(keyexpr) # a key COLUMN NAME becomes SQL -> require an EXACT value
338+
if res.exact and res.value: # (a case-ambiguous name could mis-target)
339+
return res.value
338340
return None
339341

340342
def columnType(self, expr):

lib/core/settings.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@
2020
from thirdparty import six
2121

2222
# sqlmap version (<major>.<minor>.<month>.<monthly commit>)
23-
VERSION = "1.10.7.175"
23+
VERSION = "1.10.7.176"
2424
TYPE = "dev" if VERSION.count('.') > 2 and VERSION.split('.')[-1] != '0' else "stable"
2525
TYPE_COLORS = {"dev": 33, "stable": 90, "pip": 34}
2626
VERSION_STRING = "sqlmap/%s#%s" % ('.'.join(VERSION.split('.')[:-1]) if VERSION.count('.') > 2 and VERSION.split('.')[-1] == '0' else VERSION, TYPE)

0 commit comments

Comments
 (0)