root/tools/lib/api/fs/tracing_path.c

/* [<][>][^][v][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. __tracing_path_set
  2. tracing_path_tracefs_mount
  3. tracing_path_debugfs_mount
  4. tracing_path_mount
  5. tracing_path_set
  6. get_tracing_file
  7. put_tracing_file
  8. get_events_file
  9. put_events_file
  10. tracing_events__opendir
  11. tracing_path__strerror_open_tp

   1 // SPDX-License-Identifier: GPL-2.0
   2 #ifndef _GNU_SOURCE
   3 # define _GNU_SOURCE
   4 #endif
   5 
   6 #include <stdio.h>
   7 #include <stdlib.h>
   8 #include <string.h>
   9 #include <linux/string.h>
  10 #include <errno.h>
  11 #include <unistd.h>
  12 #include "fs.h"
  13 
  14 #include "tracing_path.h"
  15 
  16 static char tracing_mnt[PATH_MAX]  = "/sys/kernel/debug";
  17 static char tracing_path[PATH_MAX]        = "/sys/kernel/debug/tracing";
  18 static char tracing_events_path[PATH_MAX] = "/sys/kernel/debug/tracing/events";
  19 
  20 static void __tracing_path_set(const char *tracing, const char *mountpoint)
  21 {
  22         snprintf(tracing_mnt, sizeof(tracing_mnt), "%s", mountpoint);
  23         snprintf(tracing_path, sizeof(tracing_path), "%s/%s",
  24                  mountpoint, tracing);
  25         snprintf(tracing_events_path, sizeof(tracing_events_path), "%s/%s%s",
  26                  mountpoint, tracing, "events");
  27 }
  28 
  29 static const char *tracing_path_tracefs_mount(void)
  30 {
  31         const char *mnt;
  32 
  33         mnt = tracefs__mount();
  34         if (!mnt)
  35                 return NULL;
  36 
  37         __tracing_path_set("", mnt);
  38 
  39         return tracing_path;
  40 }
  41 
  42 static const char *tracing_path_debugfs_mount(void)
  43 {
  44         const char *mnt;
  45 
  46         mnt = debugfs__mount();
  47         if (!mnt)
  48                 return NULL;
  49 
  50         __tracing_path_set("tracing/", mnt);
  51 
  52         return tracing_path;
  53 }
  54 
  55 const char *tracing_path_mount(void)
  56 {
  57         const char *mnt;
  58 
  59         mnt = tracing_path_tracefs_mount();
  60         if (mnt)
  61                 return mnt;
  62 
  63         mnt = tracing_path_debugfs_mount();
  64 
  65         return mnt;
  66 }
  67 
  68 void tracing_path_set(const char *mntpt)
  69 {
  70         __tracing_path_set("tracing/", mntpt);
  71 }
  72 
  73 char *get_tracing_file(const char *name)
  74 {
  75         char *file;
  76 
  77         if (asprintf(&file, "%s/%s", tracing_path_mount(), name) < 0)
  78                 return NULL;
  79 
  80         return file;
  81 }
  82 
  83 void put_tracing_file(char *file)
  84 {
  85         free(file);
  86 }
  87 
  88 char *get_events_file(const char *name)
  89 {
  90         char *file;
  91 
  92         if (asprintf(&file, "%s/events/%s", tracing_path_mount(), name) < 0)
  93                 return NULL;
  94 
  95         return file;
  96 }
  97 
  98 void put_events_file(char *file)
  99 {
 100         free(file);
 101 }
 102 
 103 DIR *tracing_events__opendir(void)
 104 {
 105         DIR *dir = NULL;
 106         char *path = get_tracing_file("events");
 107 
 108         if (path) {
 109                 dir = opendir(path);
 110                 put_events_file(path);
 111         }
 112 
 113         return dir;
 114 }
 115 
 116 int tracing_path__strerror_open_tp(int err, char *buf, size_t size,
 117                                    const char *sys, const char *name)
 118 {
 119         char sbuf[128];
 120         char filename[PATH_MAX];
 121 
 122         snprintf(filename, PATH_MAX, "%s/%s", sys, name ?: "*");
 123 
 124         switch (err) {
 125         case ENOENT:
 126                 /*
 127                  * We will get here if we can't find the tracepoint, but one of
 128                  * debugfs or tracefs is configured, which means you probably
 129                  * want some tracepoint which wasn't compiled in your kernel.
 130                  * - jirka
 131                  */
 132                 if (debugfs__configured() || tracefs__configured()) {
 133                         /* sdt markers */
 134                         if (!strncmp(filename, "sdt_", 4)) {
 135                                 snprintf(buf, size,
 136                                         "Error:\tFile %s/%s not found.\n"
 137                                         "Hint:\tSDT event cannot be directly recorded on.\n"
 138                                         "\tPlease first use 'perf probe %s:%s' before recording it.\n",
 139                                         tracing_events_path, filename, sys, name);
 140                         } else {
 141                                 snprintf(buf, size,
 142                                          "Error:\tFile %s/%s not found.\n"
 143                                          "Hint:\tPerhaps this kernel misses some CONFIG_ setting to enable this feature?.\n",
 144                                          tracing_events_path, filename);
 145                         }
 146                         break;
 147                 }
 148                 snprintf(buf, size, "%s",
 149                          "Error:\tUnable to find debugfs/tracefs\n"
 150                          "Hint:\tWas your kernel compiled with debugfs/tracefs support?\n"
 151                          "Hint:\tIs the debugfs/tracefs filesystem mounted?\n"
 152                          "Hint:\tTry 'sudo mount -t debugfs nodev /sys/kernel/debug'");
 153                 break;
 154         case EACCES: {
 155                 snprintf(buf, size,
 156                          "Error:\tNo permissions to read %s/%s\n"
 157                          "Hint:\tTry 'sudo mount -o remount,mode=755 %s'\n",
 158                          tracing_events_path, filename, tracing_path_mount());
 159         }
 160                 break;
 161         default:
 162                 snprintf(buf, size, "%s", str_error_r(err, sbuf, sizeof(sbuf)));
 163                 break;
 164         }
 165 
 166         return 0;
 167 }

/* [<][>][^][v][top][bottom][index][help] */