0
<< предыдущая заметкаследующая заметка >>
21 октября 2024
Фейковый NTP-сервер

UPD: Дружище Андрей Нигматуллин предложил нормальное решение через DynDNS и даже помог разобраться и настроить, спасибо ему!

Итак, задача: у вас есть говнороутер и провайдер, который выдает ему внешний (это важно) IP, но постоянно его меняет. А вы хотите, чтобы этот IP всегда отзывался по адресу в вашем родном домене, скажем oops.lleo.me (все имена здесь и ниже условные). У вашего роутера есть раздел динамического обновления адреса DDNS, но там только 4 варианта. Но среди них есть afraid.org!

Решение:

Допустим, у вас домен lleo.me на CloudFlare.com (можно и без него, но с ним лучше)
Выбираем поддоменное имя для своего lleo.me, например: govnorouter.lleo.me
На CloudFlare.com в разделе DNS сайта lleo.me создаем новую запись типа NS:

Type: NS
Name: govnorouter
Nameserver: ns1.afraid.org

Идем на https://afraid.org и создаем бесплатную запись «Sign up Free». Поле «userID» — пишите любое латинское слово, надеюсь там такого юзера нет. Подтвердите email, и вы залогинены. Теперь на afraid.org (дизайн там даже не 90-е, а 80-е, под браузер lynx) идем в «Domains», «Add domain» — и там прописываем свой govnorouter.lleo.me (Shared:Public я выбрал на всякий случай).

Придумываем домен еще более нижнего уровня для своего govnorouter.lleo.me, например real.govnorouter.lleo.me На afraid.org в разделе «Subdomains» нажимаем «Add».
Но, сцуко, не тот Add, который внизу, а тот Add, который в строке с доменом govnorouter.lleo.me
И в открывшемся меню пишем:

Type: A
Subdomain: real
Domain: govnorouter.lleo.me

После чего в разделе «Dynamic DNS» можно найти ключ. Например посмотреть «Direct URL»
для своего real.govnorouter.lleo.me, там покажет ключ:

httрs://freedns.afraid.org/dynamic/update.php?dFhXQzRtRWltMkpONzRQMOQ1BxOjIzMzU1NTg2

Собственно, каждый, кто постучится по этой ссылке, пропишет вам свой IP.

Теперь идем в админку своего говнороутера. Выбираем DDNS чотатакое.afraid.com и заполняем поля c с логином и паролем guest (не спрашивайте):

Login: guest
Password: guest
domain_name: real.govnorouter.lleo.me
Hash Value: dFhXQzRtRWltMkpONzRQMOQ1BxOjIzMzU1NTg2

Если в вашем роутере нет поля «Hash Value» — ищите доку на afraid.org, там что-то было про «через запятую» в каком-то другом поле.

Короче, теперь роутер обновляет свой IP для домена четвертого уровня, согласно NS-записи для домена третьего уровня. На хера такое длинное? Придумываем на CloudFlare нормальное короткое имя, чтоб набирать удобно: oops.lleo.me и вписываем:

Type: CNAME
Name: oops
Target: real.govnorouter.lleo.me
Proxied: NO

Вот теперь норм. Мы получили собственное имя в своем собственном домене oops.lleo.me, которое всегда указывает на IP нужного нам далекого устройства. А даже если afraid.org когда-нибудь поломается (посылаю им лучи здоровья и процветания), имя-то ваше, оно никуда не пропадет, придумаем другой способ его обновлять.

Было:


Забавную проблему решаю в свободные от работы полчасика. Итак, есть в офисе интернет-роутер (от провайдера — ни сменить, ни перепрошить), ему выдается внешний IP, но динамический. И его надо знать. Обычно я динамические IP подвязываю к поддомену lleo.me, автоматически меняя скриптиком через API CloudFlare. Но для этого адрес надо сначала узнать! А для этого надо, чтобы из той сети кто-то постучался на любой из серверов, куда у меня есть доступ.

1. Первое что приходит на ум — поставить в офис маленькую Raspberry, я лучше даже ESP12. Этим, чую, в итоге и кончится. Это очевидно. Но это не спортивно! Это потом. Так что пока никаких дополнительных устройств ставить не буду, попробую другие пути.

2. В офисе есть свой девайс — погодная станция от Юры, которая раз в час посылает телеметрию на его сайт. Перепрограммировать ее на какие-то еще обращения к другим сайтам может только Юра. Но у меня зато есть доступ к его сайту, где приемник телеметрии я сам ему писал когда-то на PHP. Так что не вопрос вставить в тот приемный скрипт закладку, что для станции номер 123 фиксировать ее IP. Казалось бы, что может пойти не так? Выясняется, что хостер у Юры как-то так криво настроен, что передает в nginx все запросы от имени своего собственного IP и никаких хедеров и прочих следов о реальном IP тупо не дает. Обычно это пофиг, потому что нормальные люди свои проксируют через CloudFlare, а тот сам выставляет нужный хедер. Но Юра сайт через CloudFlare не прописал и переносить категорически не хочет — у меня, говорит, всё работает, как бы чего не сломалось.

3. Окей, копаемся в самом роутере. Роутер примитивный. У него, конечно, есть свой раздел DDNS, и там есть на выбор 4 сервиса, но свой собственный url указать нельзя. А пользоваться чужими сервисами DDNS я раз и навсегда зарекся — меня когда-то кинул homeip, просто тупо отобрал домен, и мне пришлось переписывать все мои программы и сервисы, которые были на то имя жестко завязаны. Так что чужие DDNS я отныне никогда использовать не буду — ни деньги этим пидарасам платить не стану, ни бесплатно регистрироваться не буду, это принцип.

4. Единственное, что есть в роутере — это сервис определения точного времени NTP. На хера он тупому роутеру нужен — загадка, но он есть, и там можно вводить свои имена доменов. Вау! Вот это задача по-настоящему интересная!

Итак, вписываю в качестве NTP-сервера fake-ntp.lleo.me Там быстро набрасываю (с советами ChatGPT) софтинку на питоне, которая ловит обращения UDP (пробрасываю дома порт 123 на 8123), пишу логи, а для себя даже отправляю в Телеграм.

[показать спрятанное]
<?php
import socket
import logging
import requests
import urllib
.parse
import os
import time
import threading
# Настроим логированиеlogging.basicConfig(filename='/home/work/NTP-fake/ntp_requests.log',level=logging.INFO,format='%(asctime)s — %(message)s')# Создаем UDP-сокетsock=socket.socket(socket.AF_INET,socket.SOCK_DGRAM)server_address= ('0.0.0.0',8123)# Слушаем на всех интерфейсах на порту 8123sock.bind(server_address)
print(
"ListeningforNTP packets on port 8123...")# Создаем директорию для временных файлов, если она не существуетTEMP_DIR="/tmp/NTP-fake"
if not os.path.exists(TEMP_DIR):

os.makedirs(TEMP_DIR)

# Функция для отправки GET-запроса в мой канал в Телеграм
def send_get_request(message):

encoded_message = urllib.parse.quote(message, safe='')

url = f"https://lleo.me/bot/telegram.php?password=lleo123&soft=ntpfake&message={encoded_message}"try:response=requests.get(url)

ifresponse.status_code==200:

print(f"Notification sent: {message}")

else:

print(f"Failed to notify: {response.status_code}")except requests.RequestExceptionase:

print(f"Error sending notification: {e}")

# Функция для создания файла с содержимым
def create_message_file(ip, message):

file_path = os.path.join(TEMP_DIR, ip)

with open(file_path, 'w') as f:

f.write(message)

# Функция для проверки и отправки старых файлов
def process_old_files():

while True:

current_time = time.time()

for filename in os.listdir(TEMP_DIR):

file_path = os.path.join(TEMP_DIR, filename)

# Проверяем, если файл старше 10 секунд

if current_time — os.path.getmtime(file_path) > 10:

with open(file_path, 'r') as f:

message = f.read()

send_get_request(message)

os.remove(file_path) # Удаляем файл после отправки

time.sleep(1) # Проверяем папку каждую секунду

# Запускаем процесс обработки старых файлов в отдельном потоке
threading.Thread(target=process_old_files, daemon=True).start()

# Основной цикл обработки NTP-запросов
while True:

try:

# Получаем данные от клиента

data, address = sock.recvfrom(1024) # Получаем пакет (максимум 1024 байта)

ip = address[0]

port = address[1]

message = f"\nNTP-fake\nIP:{ip} Port:{port}"# Логируем запросlogging.info(f"NTP request from IP: {ip},Port: {port}")

print(f"Received packet from {ip}:{port}")# Создаем файл с именем IP и записываем encoded_messagecreate_message_file(ip,message)except Exceptionase:logging.error(f"Error occurred: {e}")

print(f"Error occurred: {e}")

Прописываю как демон:

[показать спрятанное]
install.sh:

sudo systemctl stop ntp-fake.service
sudo systemctl disable ntp-fake.service
sudo rm /etc/systemd/system/ntp-fake.service
sudo ln -s /home/work/NTP-fake/ntp-fake.service /etc/systemd/system/ntp-fake.service
sudo systemctl daemon-reload
sudo systemctl enable ntp-fake.service
sudo systemctl start ntp-fake.service
sudo systemctl status ntp-fake.service

/home/work/NTP-fake/ntp-fake.service:

[Unit]
Description=NTP Fake Service (logs IPs)
After=network.target

[Service]
ExecStart=/usr/bin/python3 /home/work/NTP-fake/ntp2.py
WorkingDirectory=/home/work/NTP-fake
Restart=always
User=lleo
Group=lleo
StandardOutput=syslog
StandardError=syslog
SyslogIdentifier=ntp-fake

[Install]
WantedBy=multi-user.target

Проверяю с любого другого внешнего сервера:

sudo ntpdate fake-ntp.lleo.me

Всё работает! Приходит запрос с порта 123, хотя ответ, понятно, мой сервер не передает.

Но в итоге результат логов за трое суток: целые дни стучатся по сотне левых мудацких роботов с самых разных лохматых портов (33007, 38388, 51319)! А роутер со своего IP пока не зашел ни разу! Ни после резета, никак.

Вот и думаю: то ли в нем выключен этот NTP вообще, то ли он его запускает раз в месяц или по какой-то неожиданной надобности, то ли зря я вписал свой адрес первой строчкой, а вторую, запасную, оставил, как была, — может, он вторую строчку запомнил как-то как основную и по первой уже не пытается постучать?

<< предыдущая заметка следующая заметка >>
пожаловаться на эту публикацию администрации портала
архив понравившихся мне ссылок

Комментарии к этой заметке скрываются - они будут видны только вам и мне.

Оставить комментарий