USB-устройство постоянно отключается: отладка циклов сброса, событий питания и сбоев перечисления

Как диагностировать USB-устройство, которое постоянно отключается, сбрасывается, перечисляется заново или ломается после suspend — по пакетным данным USB.

USB отключается, цикл сброса USB, перечисление USB, управление питанием USB, диагностика USB

USB-устройство, которое постоянно отключается, — одна из самых неприятных аппаратных проблем: "симптом шумный и нестабильный. Устройство появляется, исчезает, переподключается, меняет COM-порт, не перечисляется или работает несколько секунд и затем сбрасывается. Пользователи ищут «USB-устройство отключается», «цикл сброса USB», «USB-устройство не распознаётся после переподключения», «почему моё USB-устройство пере-нумеруется», потому что системное сообщение почти никогда не объясняет, что реально произошло." Полезные доказательства лежат ниже уровня приложения. Нужно понять — сбросил ли порт хост, перестало ли отвечать устройство, провалилось ли чтение дескриптора, отправило ли питание устройство в сон, послал ли драйвер классовый запрос или остановилась ли конечная точка.

Bus Scope создан именно для такой отладки USB. Вместо чёрного ящика он помогает рассмотреть управляющие передачи, чтения дескрипторов, сбросы, поведение конечных точек и тайминги вокруг отключения.

Что может означать «отключается»

Фраза «USB отключается» описывает несколько разных сбоев:

  • Физическое отсоединение или шевеление кабеля.
  • Электрические помехи или нестабильность питания.
  • Сброс порта хост-контроллера.
  • Сбой и перезагрузка прошивки устройства.
  • Неудачное перечисление после сброса.
  • Выгрузка и загрузка драйвера.
  • Selective suspend или управление питанием во время выполнения.
  • Остановка (stall) конечной точки с последующим провалом восстановления.
  • Сбой интерфейса составного устройства.
  • Перегрузка высокополосных передач.

В уведомлении операционной системы всё это выглядит одинаково, а в данных USB — по-разному.

Цикл сброса при перечислении

Цикл сброса часто начинается так: хост обнаруживает устройство, сбрасывает порт, читает дескрипторы, назначает адрес и затем проваливается до завершения конфигурации. Цикл повторяется.

Упрощённая последовательность выглядит так:

Сброс порта
GET_DESCRIPTOR device
SET_ADDRESS
GET_DESCRIPTOR configuration
SET_CONFIGURATION
Отключение
Сброс порта
GET_DESCRIPTOR device
...

Если устройство падает до SET_CONFIGURATION, причина может быть в содержимом дескрипторов, таймингах прошивки, питании или совместимости с хостом. Если падает после SET_CONFIGURATION — причина может быть в классовой инициализации, настройке конечной точки или запросе драйвера.

Проблемы питания выглядят как проблемы протокола

USB-устройства могут сбрасываться при просадке напряжения, скачках тока или когда концентратор не выдаёт нужный ток. Это часто встречается у:

  • USB-камер
  • плат видеозахвата
  • внешних дисков
  • отладочных плат
  • сотовых модемов
  • устройств, подключённых через пассивные концентраторы
  • длинных или некачественных кабелей

На уровне пакетов сброс из-за питания выглядит как внезапная тишина, за которой следует повторное перечисление. Устройство перестаёт отвечать, хост сбрасывает порт, перечисление начинается заново.

Bus Scope не измеряет напряжение напрямую, но показывает тайминги и последовательность вокруг сброса. Если последняя успешная операция была запуском тяжёлой по полосе операции или команды режима мотора/питания, доказательства указывают на стресс по питанию или прошивке.

Selective suspend и управление питанием во время выполнения

Операционные системы могут усыплять неактивные USB-устройства ради экономии энергии. Это нормально, если устройство и драйвер корректно это поддерживают. Это становится проблемой, когда прошивка не возвращается чисто из сна или драйвер усыпляет устройство, которое приложение ожидает активным.

Симптомы:

  • Устройство работает после включения, но сбоит после простоя.
  • Первый запрос после простоя возвращает ошибку.
  • Устройство исчезает после сна или блокировки экрана.
  • Serial-устройство меняет состояние после возобновления.
  • HID-устройство теряет ввод после пробуждения.

Трасса USB показывает, остановился ли трафик до сбоя и произошла ли последовательность resume/reset. Это полезнее, чем гадать по сообщению приложения.

Stall конечной точки перед отключением

Часть жалоб на отключение на самом деле — отказы на уровне конечной точки. Устройство может остановить (stall) bulk, interrupt или control-запрос. Драйвер пытается снять stall через CLEAR_FEATURE. Если восстановление не удаётся, драйвер сбрасывает устройство или приложение закрывает хэндл.

Ищите:

  • STALL на управляющей передаче.
  • Повторяющиеся неудачные bulk-передачи.
  • CLEAR_FEATURE(ENDPOINT_HALT).
  • Сброс после одного и того же запроса каждый раз.
  • Тайм-аут перед отключением.

Если одна и та же команда каждый раз вызывает сброс, прошивка устройства может падать при её обработке.

Циклы сброса составного устройства

Составные USB-устройства предоставляют несколько интерфейсов под одним устройством. Например, устройство может содержать:

  • CDC serial интерфейс
  • HID управляющий интерфейс
  • Mass storage интерфейс
  • Специфический вендорный диагностический интерфейс

Устройство может частично перечислиться и всё равно упасть, когда подключится драйвер одного из интерфейсов. Пользователь увидит «USB-устройство распознано», за которым сразу же последует отключение, потому что один интерфейс вызывает сбой прошивки или конфликт драйверов.

В трассе изучите дескрипторы интерфейсов, alternate settings, дескрипторы конечных точек и классовые запросы. Сброс может произойти только после того, как хост начнёт настраивать конкретный интерфейс.

Высокополосные устройства

USB-устройства видео, аудио, захвата и сбора данных могут отключаться под нагрузкой. Устройство может корректно перечислиться и пройти простые управляющие запросы, а затем упасть при запуске потока.

Частые причины:

  • Сбой резервирования полосы для изохронных передач.
  • Тайм-аут bulk-конечной точки.
  • Давление полосы на хост-контроллер.
  • Узкое место в концентраторе.
  • Несовпадение режима USB 2.0 и USB 3.x.
  • Переполнение буфера прошивки.
  • Драйвер выбирает неподдерживаемый alternate setting.

Если отключение происходит после запроса «запуск потока» или смены alternate setting, изучите конкретную передачу прямо перед сбросом. Это часто самая важная подсказка.

Что захватывать

Для повторяемого отключения начинайте захват до включения или до сбойного действия. Нужна полная картина:

  1. Подключение устройства.
  2. Сброс порта.
  3. Чтения дескрипторов.
  4. Назначение адреса.
  5. Выбор конфигурации.
  6. Запросы интерфейсных драйверов.
  7. Первая нормальная передача приложения.
  8. Последняя успешная передача перед сбоем.
  9. Тайм-аут, stall, reset или отключение.
  10. Пере-нумерация после сбоя.

Если начать захват после того, как устройство уже упало, потеряете самые важные данные.

Чек-лист отладки

Действуйте в таком порядке:

  1. Воспроизведите на коротком заведомо исправном кабеле.
  2. На первом тесте исключите пассивные концентраторы.
  3. Захватите перечисление с момента включения.
  4. Проверьте, происходит ли сбой до или после SET_CONFIGURATION.
  5. Определите последний успешный запрос.
  6. Ищите stall, тайм-ауты и повторяющиеся сбросы.
  7. Сравните сбой в простое со сбоем под нагрузкой.
  8. Проверьте на другом USB-порту или контроллере.
  9. Отключайте selective suspend только после сбора данных.
  10. Сравните то же устройство в другой ОС, если возможно.

Итоговый диагноз

«USB-устройство отключается» — это симптом, а не причина. Решение зависит от того, какие данные показывают: нестабильность питания, сброс прошивки, сбой дескрипторов, ошибку классового запроса драйвера, stall конечной точки, проблему suspend/resume или перегрузку полосы.

Bus Scope помогает показать USB-транзакции вокруг сбоя, чтобы перестать гадать по уведомлениям системы и начать отлаживать по реальному поведению шины.