Trace system call linux

10 Strace Commands for Troubleshooting and Debugging Linux Processes

strace is a powerful command line tool for debugging and trouble shooting programs in Unix-like operating systems such as Linux. It captures and records all system calls made by a process and the signals received by the process.

It displays the name of each system call together with its arguments enclosed in a parenthesis and its return value to standard error; you can optionally redirect it to a file as well.

In this article, we will explain 10 strace command examples for troubleshooting and debugging programs and processes in a Linux system.

How to Install Strace Process Monitoring Tool in Linux

If strace is not pre-installed on your Linux system, run the appropriate command below for your distribution, to install it.

In case a program crashes or behaves in a way not expected, you can go through its systems calls to get a clue of what exactly happened during its execution. As we will see later on, system calls can be categorized under different events: those relating to process management, those that take a file as an argument, those that involve networking, memory mapping, signals, IPC and also file descriptor related system calls.

You can either run a program/command with strace or pass a PID to it using the -p option as in the following examples.

1. Trace Linux Command System Calls

You can simply run a command with strace like this, here we are tracing of all system calls made by the df command.

>P\t». 832) = 832 fstat(3, ) = 0 mmap(NULL, 3971488, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x7f82f7310000 .

From the output above, you can see various types of system calls made by df command, for example.

  • open – is the type of system call
  • (“/etc/ld.so.cache”, O_RDONLY|O_CLOEXEC) – system call argument
  • 3 – system call return value

Below is an sample output showing the write system calls, that displays df command output on the screen.

2. Trace Linux Process PID

If a process is already running, you can trace it by simply passing its PID as follows; this will fill your screen with continues output that shows system calls being made by the process, to end it, press [Ctrl + C] .

%», 4096>], msg_controllen=0, msg_flags=0>, 0) = 32 recvmsg(4, 0x7ffee4dbf870, 0) = -1 EAGAIN (Resource temporarily unavailable) recvmsg(4, 0x7ffee4dbf850, 0) = -1 EAGAIN (Resource temporarily unavailable) poll([, , , , , ], 6, -1) = 1 ([]) read(31, «2», 1) = 1 recvmsg(4, 0x7ffee4dbf850, 0) = -1 EAGAIN (Resource temporarily unavailable) poll([, , , , , ], 6, 0) = 1 ([]) read(31, «2», 1) = 1 recvmsg(4, 0x7ffee4dbf850, 0) = -1 EAGAIN (Resource temporarily unavailable) poll([, , , , , ], 6, 0) = 0 (Timeout) mprotect(0x207faa20000, 8192, PROT_READ|PROT_WRITE) = 0 mprotect(0x207faa20000, 8192, PROT_READ|PROT_EXEC) = 0 mprotect(0x207faa21000, 4096, PROT_READ|PROT_WRITE) = 0 mprotect(0x207faa21000, 4096, PROT_READ|PROT_EXEC) = 0 .

3. Get Summary of Linux Process

Using the -c flag, you can generate a report of total time, calls, and errors for each system call, as follows.

4. Print Instruction Pointer During System Call

The -i option displays the instruction pointer at the time of each system call made by the program.

Читайте также:  Рекорд плеер для windows

>P\t». 832) = 832 [00007faf9cafb2b4] fstat(3, ) = 0 [00007faf9cafb47a] mmap(NULL, 3971488, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x7faf9c716000 [00007faf9cafb517] mprotect(0x7faf9c8d6000, 2097152, PROT_NONE) = 0 .

5. Show Time of Day For Each Trace Output Line

You can also print the time of day for each line in the trace output, by passing the -t flag.

>P\t». 832) = 832 15:19:25 fstat(3, ) = 0 15:19:25 mmap(NULL, 3971488, PROT_READ|PROT_EXEC, MAP_PRIVATE|MAP_DENYWRITE, 3, 0) = 0x7f8c7ebec000 15:19:25 mprotect(0x7f8c7edac000, 2097152, PROT_NONE) = 0 .

6. Print Command Time Spent in System Calls

To shows the time difference between the starting and the end of each system call made by a program, use the -T option.

7. Trace Only Specific System Calls

In the command below, trace=write is known as a qualifying expression, where trace is a qualifier (others include signal, abbrev, verbose, raw, read, or write). Here, write is the value of the qualifier.

The following command actually shows the system calls to print df output on standard output.

Here are some additional commands about trace qualifier.

8. Trace System Calls Based on a Certain Condition

Let’s look at how to trace system calls relating to a given class of events. This command can be used to trace all system calls involving process management.

Next, to trace all system calls that take a filename as an argument, run this command.

To trace all system calls involving memory mapping, type.

You can trace all network and signals related system calls.

9. Redirect Trace Output to File

To write the trace messages sent to standard error to a file, use the -o option. This means that only the command output is printed on the screen as shown below.

To look through the file, use cat command.

10. Show Some Debugging Output of Strace

To show debugging information for strace tool, use the -d flag.

For additional information, see the strace man page.

Also read these useful related articles:

In conclusion, strace is a remarkable tool for diagnosing cause(s) of program failure: it is a powerful debugging and trouble shooting. It is practically useful to experienced system administrators, programmers and hackers. To share any thoughts concerning this article, use the feedback form below.

If You Appreciate What We Do Here On TecMint, You Should Consider:

TecMint is the fastest growing and most trusted community site for any kind of Linux Articles, Guides and Books on the web. Millions of people visit TecMint! to search or browse the thousands of published articles available FREELY to all.

If you like what you are reading, please consider buying us a coffee ( or 2 ) as a token of appreciation.

We are thankful for your never ending support.

Источник

Команда strace в Linux

В операционной системе и используемых в ней программах иногда возникают ошибки, причину которых очень сложно понять, анализируя файлы журналов и сообщения об ошибках. Но и для таких ситуаций в Linux есть средства. За процессом работы любой из программ можно проследить, наблюдая системные вызовы, которые использует программа.

С помощью системных вызовов можно понять, к каким файлам обращается программа, какие сетевые порты она использует, какие ресурсы ей нужны, а также какие ошибки возвращает ей система. Это помогает разобраться в особенностях работы программы и лучше понять причину ошибки. За всё это отвечает команда strace Linux. В сегодняшней статье мы разберёмся, что она из себя представляет и как ею пользоваться.

Команда strace Linux

Как я уже сказал, команда strace показывает все системные вызовы программы, которые та отправляет к системе во время выполнения, а также их параметры и результат выполнения. Но при необходимости можно подключиться и к уже запущенному процессу. Перед тем, как перейти к практике, разберём опции утилиты и её синтаксис:

$ strace опции команда аргументы

В самом простом варианте strace запускает переданную команду с её аргументами и выводит в стандартный поток ошибок все системные вызовы команды. Давайте разберём опции утилиты, с помощью которых можно управлять её поведением:

  • -i — выводить указатель на инструкцию во время выполнения системного вызова;
  • -k — выводить стек вызовов для отслеживаемого процесса после каждого системного вызова;
  • -o — выводить всю информацию о системных вызовах не в стандартный поток ошибок, а в файл;
  • -q — не выводить сообщения о подключении о отключении от процесса;
  • -qq — не выводить сообщения о завершении работы процесса;
  • -r — выводить временную метку для каждого системного вызова;
  • -s — указать максимальный размер выводимой строки, по умолчанию 32;
  • -t — выводить время суток для каждого вызова;
  • -tt — добавить микросекунды;
  • -ttt — добавить микросекунды и количество секунд после начала эпохи Unix;
  • -T — выводить длительность выполнения системного вызова;
  • -x — выводить все не ASCI-строки в шестнадцатеричном виде;
  • -xx — выводить все строки в шестнадцатеричном виде;
  • -y — выводить пути для файловых дескрипторов;
  • -yy — выводить информацию о протоколе для файловых дескрипторов;
  • -c — подсчитывать количество ошибок, вызовов и время выполнения для каждого системного вызова;
  • -O — добавить определённое количество микросекунд к счетчику времени для каждого вызова;
  • -S — сортировать информацию выводимую при опции -c. Доступны поля time, calls, name и nothing. По умолчанию используется time;
  • -w — суммировать время между началом и завершением системного вызова;
  • -e — позволяет отфильтровать только нужные системные вызовы или события;
  • -P — отслеживать только системные вызовы, которые касаются указанного пути;
  • -v — позволяет выводить дополнительную информацию, такую как версии окружения, статистику и так далее;
  • -b — если указанный системный вызов обнаружен, трассировка прекращается;
  • -f — отслеживать также дочерние процессы, если они будут созданы;
  • -ff — если задана опция -o, то для каждого дочернего процесса будет создан отдельный файл с именем имя_файла.pid.
  • -I — позволяет блокировать реакцию на нажатия Ctrl+C и Ctrl+Z;
  • -E — добавляет переменную окружения для запускаемой программы;
  • -p — указывает pid процесса, к которому следует подключиться;
  • -u — запустить программу, от имени указанного пользователя.
Читайте также:  Windows messaging queue install

Вы знаете основные опции strace, но чтобы полноценно ею пользоваться, нужно ещё разобраться с системными вызовами, которые используются чаще всего. Мы не будем рассматривать все, а только основные. Многие из них вы уже и так знаете, потому что они называются так же, как и команды в терминале:

  • fork — создание нового дочернего процесса;
  • read — попытка читать из файлового дескриптора;
  • write — попытка записи в файловый дескриптор;
  • open — открыть файл для чтения или записи;
  • close — закрыть файл после чтения или записи;
  • chdir — изменить текущую директорию;
  • execve — выполнить исполняемый файл;
  • stat — получить информацию о файле;
  • mknod — создать специальный файл, например, файл устройства или сокет;

А теперь разберём примеры strace Linux.

Примеры использования Strace

1. Запуск программы

Самый простой способ запуска утилиты — просто передать ей в параметрах имя команды или исполняемый файл программы, которую мы хотим исследовать. Например, uname:

Как и ожидалось, мы видим список системных вызовов, которые делает утилита, чтобы узнать версию ядра. Синтаксис вывода такой:

имя_системного_вызова ( параметр1 , параметр2 ) = результат сообщение

Имя системного вызова указывает, какой именно вызов использовала программа. Для большинства вызовов характерно то, что им нужно передавать параметры, имена файлов, данные и так далее. Эти параметры передаются в скобках. Далее идет знак равенства и результат выполнения. Если всё прошло успешно, то здесь будет ноль или положительное число. Если же возвращается отрицательное значение, делаем вывод, что произошла ошибка. В таком случае выводится сообщение.

Например, в нашем выводе есть сообщения об ошибке:

openat(AT_FDCWD, «/usr/local/cuda-6.5/lib64/tls/x86_64/libc.so.6», O_RDONLY|O_CLOEXEC) = -1 ENOENT (No such file or directory)

Здесь результат выполнения -1 и сообщение говорит, что файл не найден. Но на работу программы это не влияет. Это проблема подключения сторонних библиотек и к этой утилите она не имеет отношения. А основная работа программы выполняется строчкой:

Читайте также:  Windows 10 домашняя или pro различия

И здесь ядро вернуло положительный результат.

2. Подключение к запущенной программе

Если программа, которую нам надо отследить, уже запущена, то не обязательно её перезапускать с нашей утилитой. Можно подключиться к ней по ее идентификатору PID. Для тестирования этой возможности запустим утилиту dd, которая будет записывать нули из /dev/zero в файл file1:

dd if=/dev/zero of=

Теперь узнаем PID нашего процесса, поскольку он такой один, можно воспользоваться pidof, вы же можете использовать ps:

И осталось подключиться к нашему процессу:

sudo strace -p 31796

В выводе утилиты мы видим, что она читает данные из одного места с помощью вызова read и записывает в другое через write. Чтобы отсоединится от процесса, достаточно нажать Ctrl+C. Дальше рассмотрим примеры strace Linux для фильтрации данных.

3. Фильтрация системных вызовов

Утилита выводит слишком много данных, и, зачастую, большинство из них нас не интересуют. С помощью опции -e можно применять различные фильтры для более удобного поиска проблемы. Мы можем отобразить только вызовы stat, передав в опцию -e такой параметр trace=stat:

sudo strace -e trace=stat nautilus

Кроме непосредственно системных вызовов, в качестве параметра для trace можно передавать и такие значения:

  • file — все системные вызовы, которые касаются файлов;
  • process — управление процессами;
  • network — сетевые системные вызовы;
  • signal — системные вызовы, что касаются сигналов;
  • ipc — системные вызовы IPC;
  • desc — управление дескрипторами файлов;
  • memory — работа с памятью программы.

4. Возвращение ошибки

Можно попросить strace вернуть программе ошибку по нужному системному вызову -e, но с параметром fault. Синтаксис конструкции такой:

fault = имя_вызова : error = тип_ошибки : when = количество

С именем вызова всё понятно, тип ошибки, номер ошибки, которую надо вернуть. А с количеством всё немного сложнее. Есть три варианта:

  • цифра — вернуть ошибку только после указанного количества запросов;
  • цифра+ — вернуть ошибку после указанного количества запросов и для всех последующих;
  • цифра+шаг — вернуть ошибку для указанного количества и для последующих с указанным шагом.

Например, сообщим uname, что системного вызова uname не существует:

sudo strace -e fault=uname uname

В выводе видим, что система вернула программе нашу ошибку, а потом та с помощью вызова write говорит пользователю, что узнать версию и называние системы невозможно.

5. Фильтрация по пути

Если вас интересует не определённый вызов, а все операции с нужным файлом, то можно выполнить фильтрацию по нему с помощью опции -P. Например, меня интересует, действительно ли утилита lscpu обращается к файлу /proc/cpuinfo, чтобы узнать информацию о процессоре:

strace -P /proc/cpuinfo lscpu

И в результате мы видим, что действительно обращается. Она открывает его для чтения с помощью вызова openat.

6. Статистика системных вызовов

С помощью опции вы можете собрать статистику для системных вызовов, которые использует программа. Например, сделаем это для nautilus:

sudo strace -c nautilus

Во время работы утилита ничего выводить не будет. Результат будет рассчитан и выведен, когда вы завершите отладку. В выводе будут такие колонки:

  • time — процент времени от общего времени выполнения системных вызовов;
  • seconds — общее количество секунд, затраченное на выполнение системных вызовов этого типа;
  • calls — количество обращений к вызову;
  • errors — количество ошибок;
  • syscall — имя системного вызова.

Если вы хотите получать эту информацию в режиме реального времени, используйте опцию -C.

7. Отслеживание времени выполнения

Чтобы отображать время выполнения каждого системного вызова, используйте опцию —t:

Можно также отображать микросекунды:

strace -tt uname

Или отображать время в формате UNIX:

strace -ttt uname

Чтобы добавить время выполнения вызова, добавьте —T:

strace -ttt -T uname

Выводы

В этой статье была рассмотрена команда strace Linux. Как видите, это очень удобный инструмент, который поможет решить множество проблем в вашей системе или на сервере. Мы рассмотрели только основные возможности утилиты, но этого будет вполне достаточно, чтобы начать работать с ней, а более подробную информацию можно найти в официальном руководстве.

Источник

Оцените статью