Могу ли я создать точку останова в коде в iOS, например, `__asm ​​{int 3}` в VC ++, и продолжить выполнение после того, как он был достигнут? - PullRequest
15 голосов
/ 05 сентября 2010

Я пытаюсь вставить эквивалент asm{int 3} (или аналогичный) в мою программу iPhone.Моя цель состоит в том, чтобы Xcode остановился точно на вызывающей линии, без необходимости возиться со стеком вызовов (поэтому _Debugger звучит не так, как хотелось бы, не то, чтобы я мог найти, в каком фреймворке это в любом случае ...),и дайте мне возможность возобновить выполнение (вот почему я не доволен assert).

(я привык к обоим таким поведениям в других системах, и я хотел бы воспроизвести их наiOS.)

Моя лучшая попытка до сих пор была такой:

asm volatile("bkpt 1");

Это останавливает Xcode на рассматриваемой строке, но когда я пытаюсь продолжить с помощью Cmd + Alt + P, Xcodeпоявляется снова запустить BKPT.И если я использую Shift + Cmd + O, я просто получаю это:

Watchdog has expired.  Remote device was disconnected?  Debugging session terminated.

(Само собой разумеется, удаленное устройство все еще подключено.)

У меня нет огромногоопыт работы с iOS, Mac, ARM, gdb или gcc asm.Так что я уже в тупике.Есть ли какой-нибудь способ заставить iOS и XCode делать то, что я хочу?

(я не знаю, имеет ли это значение, но, судя по размеру инструкции, моя программа представляет собой код ARM.)

Ответы [ 7 ]

17 голосов
/ 09 мая 2012

Попробуйте:

__builtin_trap();

работает на Mac и iOS, и вы можете перетащить маленький зеленый курсор на следующую строку, чтобы продолжить работу.

5 голосов
/ 05 сентября 2010

raise(SIGTRAP) - относительно переносимый способ иметь точку останова «в коде».

4 голосов
/ 27 марта 2013

Я попробовал все эти решения, и хотя ответ @RichardGroves сохранил стек, лучшее решение:

  1. создайте свой собственный метод подтверждения, такой как Debug::assert(...)
  2. установить точку останова в XCode для этой реализации
  3. используйте команду Step Out, чтобы вернуться к вызывающей стороне

Это потому, что это единственный надежный путь к обоим

  • просмотр трассировки стека
  • шаг / продолжение
1 голос
/ 24 мая 2017

Я пытался найти реализацию, которая ведет себя так же, как __ debugbreak () , которая поставляется с компилятором Microsoft и разрывается внутри моего кода, а не где-то внутри системных библиотек и позволяет мне продолжить выполнение.Эта реализация __debugbreak () работает именно так, как я хотел:

#if defined(__APPLE__) && defined(__aarch64__)
#define __debugbreak() __asm__ __volatile__(            \
    "   mov    x0, %x0;    \n" /* pid                */ \
    "   mov    x1, #0x11;  \n" /* SIGSTOP            */ \
    "   mov    x16, #0x25; \n" /* syscall 37 = kill  */ \
    "   svc    #0x80       \n" /* software interrupt */ \
    "   mov    x0, x0      \n" /* nop                */ \
    ::  "r"(getpid())                                   \
    :   "x0", "x1", "x16", "memory")
#elif defined(__APPLE__) && defined(__arm__)
#define __debugbreak() __asm__ __volatile__(            \
    "   mov    r0, %0;     \n" /* pid                */ \
    "   mov    r1, #0x11;  \n" /* SIGSTOP            */ \
    "   mov    r12, #0x25; \n" /* syscall 37 = kill  */ \
    "   svc    #0x80       \n" /* software interrupt */ \
    "   mov    r0, r0      \n" /* nop                */ \
    ::  "r"(getpid())                                   \
    :   "r0", "r1", "r12", "memory")
#elif defined(__APPLE__) && defined(__i386__)
#define __debugbreak() __asm__ __volatile__("int $3; mov %eax, %eax")
#endif

#define ASSERT(expr) do { if (!(expr)){ __debugbreak(); } } while(0)
1 голос
/ 06 октября 2015
int resume = false;
for (int i = 0; i < 20 && !resume; ++i)
    sleep(1);

Выше приведена ловушка для бедного человека, которую вы должны вручную подключить к рассматриваемой программе. Увеличьте задержку по мере необходимости. Поместите код туда, где вы хотите разбить, и вставьте точку останова в оператор сна, соберите и запустите вашу программу и присоедините к ней из Xcode. Когда Xcode ломается, вы можете щелкнуть правой кнопкой мыши переменную возобновления и изменить ее на 1, чтобы возобновить выполнение.

Screenshot

0 голосов
/ 30 ноября 2016
std::runtime_error::runtime_error("breakpoint")

вместе с точкой останова исключения XCode типа

Исключение: C ++ "named: std :: runtime"

работал для меня (используя XCode 8.0).
Это дает тот же результат, как если бы я установил точку останова вручную в строке, где

std::runtime_error::runtime_error
Вызвана функция

, т. Е. Правильный поток, правильный стек вызовов и возможность возобновления.

0 голосов
/ 13 февраля 2016

int pthread_kill(pthread_t thread, int sig); допускает продолжение и паузы в текущем потоке через pthread_self().

Подобно другим функциям сигнала (например, kill(), raise() и т. Д.), Однако, pthread_kill() используется для запроса доставки сигнала в конкретный поток.

Pthread_kill Manual

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...