Ответ 1
Насколько я знаю, процессоры x86 для процессоров имеют четыре
Знаете ли вы какие-либо другие причины, по которым точка наблюдения не может быть вставлена иначе, чем слишком много аппаратных точек останова/точек наблюдения?
У меня есть следующий сеанс отладки:
GNU gdb (GDB) 7.1
...
(gdb) watch itrap_t_beg[1][222]
Hardware watchpoint 1: itrap_t_beg[1][222]
(gdb) cont
Continuing.
...
Hardware watchpoint 1: itrap_t_beg[1][222]
...
(gdb) cont
Continuing.
Warning:
Could not insert hardware watchpoint 1.
Could not insert hardware breakpoints:
You may have requested too many hardware breakpoints/watchpoints.
(gdb) info break
Num Type Disp Enb Address What
1 hw watchpoint keep y itrap_t_beg[1][222]
breakpoint already hit 1 time
Как вы можете видеть, есть только одна точка наблюдения, но она не может вставить точку останова.
Знаете ли вы, как я могу это исправить?
Насколько я знаю, процессоры x86 для процессоров имеют четыре
Может заставлять программные точки останова (которые не имеют ограничения по размеру), запустив
set can-use-hw-watchpoints 0
Ответ на съемку: используйте watch -location itrap_t_beg[1][222]
или короткую форму watch -l
.
Длинный ответ: Цитата руководства GDB:
Просмотр сложных выражений, которые ссылаются на многие переменные, также может исчерпывать ресурсы, доступные для сторожевых точек с аппаратным обеспечением. Это потому, что gdb нужно смотреть каждую переменную в выражении с отдельными выделенными ресурсами.
gdb буквально наблюдает за самим выражением, а не за любой адрес, на который он указывает. В этом случае это означает, что точка останова попадет, если сама itrap_t_beg
будет изменена так, что itrap_t_beg[1][222]
делает; там не только точка наблюдения для itrap_t_beg[1][222]
, но и одна для itrap_t_beg
. Это может быть больше, чем доступно.
В вашем случае itrap_t_beg
- 7 ints, 28 байт. Контрольная точка x86_64 имеет длину до восьми байтов, поэтому для всей системы GDB требуется четыре точки наблюдения - плюс пятая для itrap_t_beg
. Семейство x86 поддерживает только четыре одновременных точки наблюдения.
Более подробный пример того, как работают точки наблюдения:
//set a watchpoint on '*p' before running
#include <stdio.h>
int a = 0;
int b = 0;
int c = 0;
int* p = &a;
int main()
{
puts("Hi"); // Dummy lines to make the results clearer, watchpoints stop at the line after the change
*p = 1; // Breaks: *p was changed from 0 to 1
puts("Hi");
a = 2; // Breaks: a is *p, which changed from 1 to 2
puts("Hi");
p = &b; // Breaks: p is now b, changing *p from 2 to 0
puts("Hi");
p = &c; // Doesn't break: while p changed, *p is still 0
puts("Hi");
p = NULL; // Breaks: *p is now unreadable
puts("Hi");
return 0;
}
В теории это полезная функция; вы можете наблюдать сложное выражение, ломающееся, как только оно ложно, несколько похожее на постоянно проверенное утверждение. Например, вы можете watch a==b
в вышеуказанной программе.
На практике это неожиданно, часто вызывает эту проблему, и обычно это не то, что вы хотите.
Чтобы посмотреть только адрес цели, используйте watch -location itrap_t_beg[1][222]
. (Это доступно в GDB 7.3, выпущенном в июле 2011 года, если вы все еще на 7.1, используйте print &itrap_t_beg[1][222]
и watch *(itrap_t)0x12345678
, или какой бы адрес он не печатал.)