Если S19 Pro перестал выдавать свои 110 TH/s, а в веб-интерфейсе вместо 76 чипов светится 0 или оборванная цепочка — плату пора нести на диагностический стенд. В 90% случаев мы имеем дело с отвалом кристалла от перегрева, пробоем LDO-стабилизатора или микротрещиной в текстолите.
Архитектура хеш-платы S19 Pro: как устроены домены и сигналы
На хеш-плате Antminer S19 Pro стоят 76 чипов BM1398, разбитых на 19 последовательных питающих доменов (по 4 чипа в домене). Общее напряжение шины (около 12.5–15V в зависимости от прошивки) делится между ними. На один домен приходится в среднем 0.7–0.8V, а сам чип питается напряжением VCORE порядка 0.32–0.42V.
Сигналы идут последовательно по цепочке от 1-го чипа (возле разъема контрольки) до 76-го:
- CLK (25 MHz): Тактовый сигнал. Если обрывается на 30-м чипе, все остальные после него тухнут.
- CO (Command Output): Входная линия команд от контрольной платы.
- RI (Return Input): Обратная линия ответа в контрольку. Идет в обратном направлении — от 76-го чипа к 1-му.
- RST (Reset): Линия сброса. Низкий уровень на ней сажает чип в жесткий ресет.
- BO (Busy Output): Сигнал занятости линии.
Пошаговая диагностика: от логов майнера к прозвонке
Открываем Kernel Log через веб-интерфейс майнера или прошивку (VNish, HiveOS). Смотрим, на чем именно зануляется цепь.
Что искать в логах:
- Chain 1: found 0 asics — ответа по линии RI нет вообще. Смотрим 1-й чип, его LDO-питание или разъем сигнального шлейфа.
- Chain 2: only 42 asics found — сигнал «застрял» на 42-м или 43-м чипе. Идем сразу к этому участку.
- Read temp sensor failed — выбило датчик TMP75. На S19 Pro они стоят на нескольких доменах. Из-за мертвого датчика плата не запустится по соображениям защиты.
Замеры контрольных точек (Test Points)
Запитайте плату от сервисного БП или тестера (без подачи высокого тока на шину) и переведите мультиметр в режим прозвонки диодов (красный щуп на землю GND).
[Чип 42] ---> (CO / CLK / RST) ---> [Чип 43]
[Чип 42] <--- (RI / BO) <--- [Чип 43]Относительно земли сопротивление сигнальных линий на контрольных точках должно быть примерно одинаковым по всей плате:
- CLK, CO, RI, RST: в районе 450–600 Ом.
Если на 43-м чипе точка CLK звенеть в 0 Ом (короткое) или показывает бесконечность — чип под замену.
Питание LDO
Каждому домену нужны вспомогательные напряжения для внутренней логики чипа. Их формируют мелкие LDO-стабилизаторы:
- VDD 1.8V: питает сигнальную обвязку.
- VDD 0.8V: питает внутреннее ядро логики.
Если на чипе есть 1.8V, но нет 0.8V — чип не сможет транслировать CLK дальше по цепи, и плата срежет цепочку на нем.
Зачем нужен осциллограф и как им работать
Мультиметр показывает только усредненное постоянное напряжение (DC). Но он бесполезен, когда напряжение в норме, а сам сигнал искажен шумом или сорвана амплитуда. Врать мультиметр может знатно, а осциллограф сразу показывает форму волны.
Нужен прибор с полосой хотя бы 100 MHz и щуп с делителем 10X.
Проверка CLK (Тактовая частота 25 MHz):
Встаем щупом на контрольную точку CLK. Должна быть ровная синусоида или меандр амлитудой около 1.8V. Если вместо нормального сигнала видите сплющенную пилу амплитудой 0.4V — буфер чипа подгорел и не продавливает линию дальше.
Проверка пакетов CO/RI:
При старте плата кидает короткие пачки импульсов. На осциллографе они выглядят как быстрые всплески (Burst). Если на вход чипа 43 пачка пришла, а с его выхода ничего не вылетает — этот чип мертв, либо у него висит RST в нуле.
Пульсации по шине питания (Ripple):
Переключаем вход осциллографа в режим AC (закрытый вход) и меряем конденсаторы прямо на брюхе чипа. Пульсации больше 30–40 мВ говорят о том, что керамика вокруг чипа поплыла от постоянного перегрева.
Справочник контрольных точек (Antminer S19 Pro / BM1398)
| Линия | Норма V (DC) | Сигнал на осциллографе | Сопротивление на GND | Симптом при обрыве |
|---|---|---|---|---|
| CLK | 0.8–0.9V | Синусоида 25 MHz, 1.8Vpp | 500–600 Ом | Цепь обрывается на битом чипе |
| CO | 0–0.2V | Пачки импульсов 1.8V при опросе | 500–600 Ом | Опрос чипов останавливается |
| RI | 1.7–1.8V | Пачки импульсов при ответе | 500–600 Ом | Выдает 0 ASICs или режет хвост платы |
| RST | 1.8V | Высокий логический уровень | 500–650 Ом | Чипы не выходят из сброса |
| VDD 1.8V | 1.8V | Чистая линия (AC-помеха < 20 мВ) | 1–3 кОм | Не работают буферы ввода-вывода |
| VDD 0.8V | 0.8V | Чистая линия (AC-помеха < 15 мВ) | 100–300 Ом | Не работает ядро чипа |
Практика пайки: сдергиваем и сажаем BM1398
Алюминиевые платы S19 Pro работают как огромный теплоотвод. Попытаться сдуть чип просто феном сверху — верный способ ужарить подложку и оторвать пятаки.
Что понадобится:
- Нижний подогрев (термопрофиль 160–180°C).
- Паяльный фен (насадка под размер чипа).
- Безотмывочный BGA-флюс (NC-559, Martin или RMA-223).
- Свинцовые шары 0.35 мм или свинцовая паста Sn63/Pb37 (свинец плавится при 183°C, что сильно облегчает жизнь по сравнению с заводским безсвинцом).
Порядок действий:
- Кладем плату на нижний подогрев, плавно греем до 150–160°C. Если поторопитесь — плату из-за разницы расширения текстолита и алюминия выгнет бананом.
- Наносим немного флюса под чип.
- Догреваем феном сверху (температура на выходе фена примерно 340–360°C, средний поток). Греем круговыми движениями.
- Касаемся чипа пинцетом: как только он «поплыл» на шарах, аккуратно снимаем его строго вверх.
- Зачищаем контактные площадки на плате медной оплеткой с канифолью, смываем все галошей или изопропилом.
- Накатываем новый чип через трафарет свинцовой пастой или шариками.
- Ставим чип по ключу (метка на корпусе и шелкография на плате должны совпасть), позиционируем.
- Греем на нижнем подогреве с подачей верхнего фена до посадки. Чип сам сядет на место за счет поверхностного натяжения жидкого припоя.
Парсер логов на Python для быстрой диагностики
Чтобы не ковырять логи вручную, вот рабочий скрипт. Скидываете ему лог с майнера, он выдергивает сбойную цепь и сразу пишет, на какой чип ставить мультиметр.
#!/usr/bin/env python3
import re
import sys
EXPECTED_ASICS = 76
def parse_asic_log(filepath):
chain_pattern = re.compile(
r"Chain\[(\d+)\]:\s*found\s*(\d+)\s*asics",
re.IGNORECASE
)
sensor_pattern = re.compile(
r"sensor[\[\s]*(\d+)[\]\s]*.*temp.*error",
re.IGNORECASE
)
issues_found = False
problem_chains = []
reported_sensors = set()
print(f"[*] Разбор лога: {filepath}\n")
try:
with open(filepath, "r", errors="ignore") as f:
for num, line in enumerate(f, 1):
# Проверка количества чипов в цепи
c_match = chain_pattern.search(line)
if c_match:
chain_id = int(c_match.group(1))
found = int(c_match.group(2))
if found < EXPECTED_ASICS:
issues_found = True
problem_chains.append(
(chain_id, found, EXPECTED_ASICS)
)
print(
f"[!] Цепь {chain_id}: найдено "
f"{found} чипов из {EXPECTED_ASICS}."
)
if found == 0:
print(
" -> Не обнаружен первый чип цепи."
)
print(
" -> Проверить питание платы, RI, "
"RST, BOOT и тактирование."
)
else:
print(
f" -> Проверить выход (CLK/CO) "
f"чипа #{found}"
)
print(
f" -> Проверить вход (RI) и "
f"LDO-питание чипа #{found + 1}"
)
print()
# Проверка датчиков температуры
s_match = sensor_pattern.search(line)
if s_match:
sensor_id = int(s_match.group(1))
if sensor_id not in reported_sensors:
issues_found = True
reported_sensors.add(sensor_id)
print(
f"[!] Ошибка датчика температуры "
f"#{sensor_id} (строка {num})."
)
print(
" -> Проверить TMP75, питание "
"датчика и линии I2C."
)
print()
# Итоговая сводка
print("=" * 60)
print("ИТОГОВАЯ СВОДКА")
print("=" * 60)
if not issues_found:
print("[+] Проблем по шаблонам не обнаружено.")
return False
if problem_chains:
print("\nПроблемные цепи:")
for chain_id, found, expected in problem_chains:
print(
f" - Chain {chain_id}: "
f"{found}/{expected} ASIC"
)
if reported_sensors:
print("\nОшибки датчиков температуры:")
for sensor_id in sorted(reported_sensors):
print(f" - Sensor {sensor_id}")
print()
return True
except FileNotFoundError:
print(f"[-] Файл не найден: {filepath}")
return True
except Exception as e:
print(f"[-] Ошибка обработки файла: {e}")
return True
if __name__ == "__main__":
if len(sys.argv) < 2:
print(
f"Запуск: {sys.argv[0]} <path_to_log.txt> "
f"[expected_asics]"
)
sys.exit(1)
if len(sys.argv) >= 3:
try:
EXPECTED_ASICS = int(sys.argv[2])
except ValueError:
print("[-] expected_asics должен быть числом.")
sys.exit(1)
has_issues = parse_asic_log(sys.argv[1])
sys.exit(1 if has_issues else 0)Примеры запуска:
python diag.py kernel.log
Для платы с другим количеством чипов:
- python diag.py kernel.log 63
- python diag.py kernel.log 72
- python diag.py kernel.log 80
Чек-лист контрольной проверки перед запуском в корпус
- Сопротивление шины VCORE: Сопротивление относительно земли не должно быть нулевым (короткое замыкание).
- Контроль LDO без полной нагрузки: Подаем питание от сервисного БП, проверяем наличие 1.8V и 0.8V на замененном чипе.
- Прогонка сигнала: Проверяем осциллографом проходит ли 25 MHz через запаянный чип дальше по цепи.
- Тест под высокой нагрузкой: Собираем майнер обратно, ставим на родные вентиляторы, гоняем плату на штатной прошивке 2–3 часа, отслеживая HW-ошибки по этой цепи.