как избавиться от "неизвестного" раздела в перфе - PullRequest
0 голосов
/ 05 ноября 2019

Я сделал следующее:

1. sudo rm -rf /root/.debug/
2. compile program with -g -O2 -fno-omit-frame-pointer
3. run the program and get the pid
4. sudo perf record -F 2000 -a -s -g -p $pid sleep 15
5. sudo perf report

, затем я получил крошечную часть "неизвестного", например

-    2.50%     0.00%  postgres  [unknown]            [k] 0000000000000000                                                                                                                                  
   - 0                                                                                                                                                                                                     
        1.12% _int_malloc                                                                                                                                                                                  ▒
        0.79% _IO_vsnprintf

, похоже, это из-за вызова libc 'malloc'. затем я пишу программу на той же машине , чтобы проверить ее.

#include <stdlib.h>
#include <stdio.h>
#include <unistd.h>
#include <string.h>
#include <sys/types.h>

int main(int argc, char *argv[])
{
    while(1) {
        printf("perf record -g -p %d -- sleep 5; perf report\n", getpid());
        sleep(1);
        void *p = malloc(10);
        memset(p, 0, 10);
        free(p);
    }
    return 0;
}

тогда я сделал то же самое, что и выше, нет "неизвестного" раздела.

как это объяснить / исправить?

1 Ответ

1 голос
/ 08 ноября 2019

Блок [unknown] в выводе perf report относится к имени динамического общего объекта ( DSO ). perf report не удалось разрешить путь DSO , поэтому он печатает [unknown]. Согласно последнему дереву исходного кода ядра (которое на момент написания статьи было 5.3.9), вы можете видеть это здесь .

Важно знать, что определение символов DSOпроизойдет с помощью выборочного адреса события. Функция thread__resolve отвечает именно за это. В более старых ядрах метод thread__resolve имел другое имя - perf_event__preprocess_sample_addr.

. Учитывая снимок вашего вывода, похоже, что адрес события, которое было выбрано во время perf record, равно 0. Этоозначает, что адрес не может быть разрешен вообще. Это адрес в пространстве ядра (глядя на символ [k] 0000000000000000), и perf в вашем случае не может его разрешить.

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

...