Stlink: st-util должен выйти на LIBUSB_ERROR_NO_DEVICE

Созданный на 17 мар. 2019  ·  12Комментарии  ·  Источник: stlink-org/stlink

Когда я сначала отключаю отладчик USB, а затем пытаюсь выполнить команду через GDB, st-util очень быстро выдает следующие ошибки:

  core status: unknown
[!] send_recv send request failed: LIBUSB_ERROR_NO_DEVICE                      
[!] send_recv STLINK_DEBUG_GETSTATUS
  core status: unknown
[!] send_recv send request failed: LIBUSB_ERROR_NO_DEVICE                      
[!] send_recv STLINK_DEBUG_GETSTATUS
  core status: unknown
[!] send_recv send request failed: LIBUSB_ERROR_NO_DEVICE                      
[!] send_recv STLINK_DEBUG_GETSTATUS
  core status: unknown
[!] send_recv send request failed: LIBUSB_ERROR_NO_DEVICE                      
[!] send_recv STLINK_DEBUG_GETSTATUS
  core status: unknown
2019-03-17T14:26:42 ERROR src/flash_loader.c: flash loader run error           
2019-03-17T14:26:42 ERROR src/common.c: stlink_flash_loader_run(0x8000000) failed! == -1

таким образом занимая центральный процессор почти на 100%. Это приводит к серьезной трате времени (перезапуск виртуальной машины и т. Д.).

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

bufixed componenst-util componenstlink-lib dependenclibusb errogdb-server staturesolved

Все 12 Комментарий

Я думаю, что stlink должен прекратиться на этом этапе: https://github.com/texane/stlink/blob/df3c2b02867db03fb82f6faaad71300398965e85/src/usb.c#L54

Я думаю, что stlink должно завершиться на этом этапе:

https://github.com/texane/stlink/blob/df3c2b02867db03fb82f6faaad71300398965e85/src/usb.c#L54

Да, думаю, вы правы, вызов libusb надо проверять соответствующим образом. При желании можете залатать и отправить пиар. Это также необходимо сделать для других вызовов libusb в файле usb.c. Спасибо за сообщение!

При желании можете залатать и отправить пиар.

Мне бы хотелось. Однако я не уверен, что понимаю структуру проекта, поэтому простого exit(1) здесь достаточно или нет.

Это также необходимо сделать для других вызовов libusb в файле usb.c.

Я могу этого не очень хорошо понимать. Вы имеете в виду " send_recv заставить приложение завершать работу везде, где оно возвращает -1 "?

Я разместил комментарий в PR, есть еще места, где может пойти не так при обращении к libusb.

Проект организован следующим образом:

  • libstlink (usb.c является его частью и никогда не должен использовать exit в библиотеке) файлы библиотеки находятся в папке src, наиболее важными являются usb.c и common.c (и, конечно же, flash_loader.c)
  • st-util находится в src / gdbserver
  • st-info находится в src / tools / info.c
  • st-flash находится в src / tools / flash.c

Я думаю, это может быть связано с номерами 888 и 445.
@ceremcem и @rewolff : А как насчет идеи обсудить это вместе?

@chenguokai : У вас есть идея, как здесь действовать?

Невозможно воспроизвести этот случай.
Я выполнил процедуру на своем компьютере с macOS. Появляется сообщение об ошибке, но нет никаких признаков попадания в мертвые петли.
image
image

Изменить: я выполнил команду n после установки точки останова на функции main и отключения st-link

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

https://github.com/texane/stlink/blob/0082e488579077762627dba2cee54ffca64dad17/src/gdbserver/gdb-server.c#L1121

Этот вызов функции не возвращает правильного значения для завершения цикла while (1). Проблемы могут быть внутри функции или механизма while (1).

После проверки процесса обработки ошибок с помощью lldb я, вероятно, выяснил код ошибки.

https://github.com/texane/stlink/blob/bf840a1ae82ffc3ef9929f243bb8050d6856f698/src/gdbserver/gdb-server.c#L1448

Когда _stlink_usb_step обнаруживает ошибку, изначально вызванную неудачей вызова libusb, он возвращает ненулевое возвращаемое значение (в данном случае -1). Однако это возвращаемое значение не обрабатывается циклом recv-handle-send в gdb-server:

https://github.com/texane/stlink/blob/bf840a1ae82ffc3ef9929f243bb8050d6856f698/src/gdbserver/gdb-server.c#L1119

Я предлагаю две возможные стратегии сделки:

Общая часть: проверьте возвращаемое значение stlink_step в случае переключения.

  1. Если появляется какая-либо ошибка, попробуйте уведомить GDB и выйти.
  2. Повторить вызов этой функции в течение ограниченного времени, если ошибка остается, уведомить GDB и выйти, в противном случае продолжить.

Анализ:

Вариант 1 приемлем, поскольку мы не можем предсказать, что произойдет после ошибки связи. Недостатком является то, что st-util может чаще выходить из строя на некоторых нестабильных портах USB или что-то подобное.
Вариант 2 даст нестабильным устройствам еще один шанс, но может вызвать дублирование пакетов, что сделает отладку несколько более непредсказуемой.

Спасибо за подробный анализ. Я бы предпочел вариант 1 здесь. Если люди сталкиваются с проблемами, связанными с конкретной локальной нестабильностью оборудования, мы все равно ничего не можем с этим поделать, и это также не то, что должны учитывать инструменты stlink. Кажется более важным, чтобы мы пошли на компромисс при отладке. Вы можете это исправить прямо сейчас?

Я проверю документацию gdb, чтобы правильно отправлять пакеты. Думаю, не так уж и сложно.
После того, как я закончу, я подниму пиар.

Я этого не говорил, но я выбрал вариант 2. Но после вашего объяснения: вы правы. Вы меня убедили: если нет веских оснований полагать, что ошибка временная, ее следует немедленно считать фатальной.

Повторная попытка без уведомления пользователя приведет к неожиданным сюрпризам. Предположим, что 1/100 или 1/1000 переданных битов повреждены (на любом уровне). Если это приводит к тому, что команда становится «недействительной» в 99% случаев, пользователь в этой ситуации в среднем будет получать множество предупреждений (например, внезапный выход stlink) о том, что его оборудование нестабильно, прежде чем он получит незаметное повреждение данных, которое вызывает проблемы. ...

«Легкий выход» - просто «exit ()». Это внезапно закроет соединение с gdb, и он справится с этим достаточно изящно.

Базовые функции хорошо работают под PR с платой stm32f401.
Мертвая петля устранена во время моего локального теста. Теперь st-util выйдет. gdb получит ответ об ошибке и отключится.

Была ли эта страница полезной?
0 / 5 - 0 рейтинги