Архитектура операционной системы UNIX :: Бах Морис Дж.
Страница:
570 из 715
При возобновлении работы отладчика ядро запоминает значение, возвращенное трассируемым процессом, снимает с глобальной структуры блокировку и возвращает управление пользователю.
Если в момент перехода процесса-потомка в состояние трассировки отладчик не находится в состоянии приостанова (wait), он не обнаружит потомка, пока не обратится к функции wait, после чего немедленно выйдет из функции и продолжит работу по вышеописанному плану.
int data[32];
main() {
int i;
for (i = 0; i ‹ 32; i++) printf("data[%d] = %d\n", i, data[i]);
printf("ptrace data addr 0x%x\n", data);
}
Рисунок 11.2. Программа trace (трассируемый процесс)
#define TR_SETUP 0
#define TR_WRITE 5
#define TR_RESUME 7
int addr;
main(argc, argv)
int argc;
char *argv[];
{
int i, pid;
sscanf(argv[1], "%x", &addr);
if ((pid = fork() == 0) {
ptrace(TR_SETUP, 0, 0, 0);
execl("trace", "trace", 0);
exit();
}
for (i = 0; i ‹ 32, i++) {
wait((int *) 0);
/* записать значение i в пространство процесса с идентификатором pid по адресу, содержащемуся в переменной addr */
if (ptrace(TR_WRITE, pid, addr, i) == -1) exit();
addr += sizeof(int);
}
/* трассируемый процесс возобновляет выполнение */
ptrace(TR_RESUME, pid, 1, 0);
}
Рисунок 11.3. Программа debug (трассирующий процесс)
Рассмотрим две программы, приведенные на Рисунках 11.2 и 11.3 и именуемые trace и debug, соответственно. При запуске программы trace с терминала массив data будет содержать нулевые значения; процесс выводит адрес массива и завершает работу.
|< Пред. 568 569 570 571 572 След. >|