This commit is contained in:
Jan Rude
2017-05-24 13:02:22 +02:00
parent e1da01505f
commit 527b7303b4
7 changed files with 31 additions and 12 deletions

View File

@@ -1,3 +1,10 @@
## Version 0.4.5.2
* Fixed error on update
* Fixed version search
* Path to version file(s) is printed
* Support for HTTP Basic Auth is now added (--auth)
## Version 0.4.5.1 ## Version 0.4.5.1
* Fixed error on launch when launching from different directory * Fixed error on launch when launching from different directory

View File

@@ -1,5 +1,6 @@
# TODO # TODO
* Newer Typo3 installations use /typo3/index.php?id=xxx * Newer Typo3 installations use /typo3/index.php?id=xxx
* Version search fix * Stop extension enumeration with ctrl-c
* Stop extension enumeration with ctrl-c * maybe store extensions and findings in database
* code cleanup

View File

@@ -131,7 +131,7 @@ class Typo3_Installation:
if ('TYPO3 Backend access denied: The IP address of your client' in response[0]) or (response[3] == 403): if ('TYPO3 Backend access denied: The IP address of your client' in response[0]) or (response[3] == 403):
login_text += (Fore.YELLOW + ' Forbidden (IP Address Restriction)' + Fore.RESET) login_text += (Fore.YELLOW + ' Forbidden (IP Address Restriction)' + Fore.RESET)
elif ('TYPO3 Login' in title): elif (('TYPO3 Login' in title) or ('TYPO3 CMS Login') in title):
login_text += Fore.GREEN + ' Yes' + Fore.RESET login_text += Fore.GREEN + ' Yes' + Fore.RESET
else: else:
login_text = Fore.RED + 'Could not be found' + Fore.RESET login_text = Fore.RED + 'Could not be found' + Fore.RESET

View File

@@ -1 +1 @@
{"threads": 5, "agent": "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:40.0) Gecko/20100101 Firefox/40.0", "timeout": 10} {"threads": 5, "pass": "ne", "user": "No", "timeout": 10, "agent": "Mozilla/5.0 (Windows NT 6.1; WOW64; rv:40.0) Gecko/20100101 Firefox/40.0"}

View File

@@ -42,7 +42,7 @@ class Request:
""" """
try: try:
config = json.load(open('lib/config.json')) config = json.load(open('lib/config.json'))
r = requests.get(domain_name + path, timeout=config['timeout'], headers={'User-Agent' : config['agent']}, verify=False) r = requests.get(domain_name + path, timeout=config['timeout'], headers={'User-Agent' : config['agent']}, auth=(config['user'], config['pass']), verify=False)
httpResponse = str((r.text).encode('utf-8')) httpResponse = str((r.text).encode('utf-8'))
headers = r.headers headers = r.headers
cookies = r.cookies cookies = r.cookies
@@ -50,8 +50,10 @@ class Request:
response = [httpResponse, headers, cookies, status_code] response = [httpResponse, headers, cookies, status_code]
return response return response
except requests.exceptions.Timeout: except requests.exceptions.Timeout:
print(e)
print(Fore.RED + '[x] Connection timed out' + Fore.RESET) print(Fore.RED + '[x] Connection timed out' + Fore.RESET)
except requests.exceptions.ConnectionError as e: except requests.exceptions.ConnectionError as e:
print(e)
print(Fore.RED + '[x] Connection error\n | Please make sure you provided the right URL' + Fore.RESET) print(Fore.RED + '[x] Connection error\n | Please make sure you provided the right URL' + Fore.RESET)
except requests.exceptions.RequestException as e: except requests.exceptions.RequestException as e:
print(Fore.RED + str(e) + Fore.RESET) print(Fore.RED + str(e) + Fore.RESET)
@@ -68,7 +70,7 @@ class Request:
""" """
try: try:
config = json.load(open('lib/config.json')) config = json.load(open('lib/config.json'))
r = requests.head(domain_name + path, timeout=config['timeout'], headers={'User-Agent' : config['agent']}, allow_redirects=False, verify=False) r = requests.head(domain_name + path, timeout=config['timeout'], headers={'User-Agent' : config['agent']}, auth=(config['user'], config['pass']), allow_redirects=False, verify=False)
status_code = str(r.status_code) status_code = str(r.status_code)
if status_code == '405': if status_code == '405':
print("WARNING, (HEAD) method not allowed!!") print("WARNING, (HEAD) method not allowed!!")
@@ -126,7 +128,7 @@ class Request:
because usually the TYPO3 version is in the first few lines of the response. because usually the TYPO3 version is in the first few lines of the response.
""" """
config = json.load(open('lib/config.json')) config = json.load(open('lib/config.json'))
r = requests.get(domain_name + path, stream=True, timeout=config['timeout'], headers={'User-Agent' : config['agent']}, verify=False) r = requests.get(domain_name + path, stream=True, timeout=config['timeout'], headers={'User-Agent' : config['agent']}, auth=(config['user'], config['pass']), verify=False)
if r.status_code == 200: if r.status_code == 200:
try: try:
for content in r.iter_content(chunk_size=400, decode_unicode=False): for content in r.iter_content(chunk_size=400, decode_unicode=False):

View File

@@ -42,8 +42,14 @@ class VersionInformation:
version = 'could not be determined' version = 'could not be determined'
for path, regex in files.items(): for path, regex in files.items():
response = Request.version_information(domain.get_name(), path, regex) response = Request.version_information(domain.get_name(), path, regex)
if not (response is None) and (len(response) > len(domain.get_typo3_version())):
domain.set_typo3_version(response) if not (response is None):
return True string = '[!] ' + 'Found version file:'
print(string.ljust(30) + path)
if (version is 'could not be determined'):
version = response
elif (len(response) > len(version)):
version = response
domain.set_typo3_version(version) domain.set_typo3_version(version)

View File

@@ -18,7 +18,7 @@
# along with this program. If not, see [http://www.gnu.org/licenses/](http://www.gnu.org/licenses/) # along with this program. If not, see [http://www.gnu.org/licenses/](http://www.gnu.org/licenses/)
#------------------------------------------------------------------------------- #-------------------------------------------------------------------------------
__version__ = '0.4.5.1' __version__ = '0.4.5.2'
__program__ = 'Typo-Enumerator' __program__ = 'Typo-Enumerator'
__description__ = 'Automatic Typo3 enumeration tool' __description__ = 'Automatic Typo3 enumeration tool'
__author__ = 'https://github.com/whoot' __author__ = 'https://github.com/whoot'
@@ -29,6 +29,7 @@ import datetime
import argparse import argparse
import json import json
import inspect import inspect
import base64
from colorama import Fore, init, deinit, Style from colorama import Fore, init, deinit, Style
from lib.check_installation import Typo3_Installation from lib.check_installation import Typo3_Installation
from lib.version_information import VersionInformation from lib.version_information import VersionInformation
@@ -69,6 +70,7 @@ Options:
Default: 10 seconds Default: 10 seconds
--agent USER_AGENT The user-agent used for all requests --agent USER_AGENT The user-agent used for all requests
Default: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:40.0) Gecko/20100101 Firefox/40.0 Default: Mozilla/5.0 (Windows NT 6.1; WOW64; rv:40.0) Gecko/20100101 Firefox/40.0
--auth USER:PASS Username and Password for HTTP Basic Authorization
--threads THREADS The number of threads used for enumerating the extensions --threads THREADS The number of threads used for enumerating the extensions
Default: 5 Default: 5
@@ -98,6 +100,7 @@ Options:
parser.add_argument('-p', '--port', dest='port', type=int) parser.add_argument('-p', '--port', dest='port', type=int)
parser.add_argument('--threads', dest='threads', type=int, default = 5) parser.add_argument('--threads', dest='threads', type=int, default = 5)
parser.add_argument('--agent', dest='agent', type=str, default = 'Mozilla/5.0 (Windows NT 6.1; WOW64; rv:40.0) Gecko/20100101 Firefox/40.0') parser.add_argument('--agent', dest='agent', type=str, default = 'Mozilla/5.0 (Windows NT 6.1; WOW64; rv:40.0) Gecko/20100101 Firefox/40.0')
parser.add_argument('--auth', dest='auth', type=str, default = 'No:ne')
parser.add_argument('--timeout', dest='timeout', type=int, default = 10) parser.add_argument('--timeout', dest='timeout', type=int, default = 10)
help.add_argument( '-h', '--help', action='store_true') help.add_argument( '-h', '--help', action='store_true')
args = parser.parse_args() args = parser.parse_args()
@@ -132,7 +135,7 @@ Options:
for line in f: for line in f:
self.__domain_list.append(Domain(line.strip('\n'), args.ext_state, args.top)) self.__domain_list.append(Domain(line.strip('\n'), args.ext_state, args.top))
config = {'threads':args.threads, 'agent':args.agent, 'timeout':args.timeout} config = {'threads':args.threads, 'agent':args.agent, 'timeout':args.timeout, 'user': (args.auth).split(':')[0], 'pass': (args.auth).split(':')[1]}
json.dump(config, open(os.path.join(self.__path, 'lib', 'config.json'), 'w')) json.dump(config, open(os.path.join(self.__path, 'lib', 'config.json'), 'w'))
for domain in self.__domain_list: for domain in self.__domain_list: