]> git.ipfire.org Git - thirdparty/kernel/linux.git/commitdiff
perf env: Add helper to lazily compute the os_release
authorIan Rogers <irogers@google.com>
Tue, 2 Jun 2026 15:25:14 +0000 (08:25 -0700)
committerArnaldo Carvalho de Melo <acme@redhat.com>
Wed, 3 Jun 2026 19:53:16 +0000 (16:53 -0300)
In live mode the os_release isn't being initialized, make a lazy
initialization helper that assumes when the os_release isn't
initialized this is live mode.

Signed-off-by: Ian Rogers <irogers@google.com>
Acked-by: Namhyung Kim <namhyung@kernel.org>
Cc: Alexander Gordeev <agordeev@linux.ibm.com>
Cc: Heiko Carstens <hca@linux.ibm.com>
Cc: Honglei Wang <jameshongleiwang@126.com>
Cc: Jan Polensky <japo@linux.ibm.com>
Cc: Sumanth Korikkar <sumanthk@linux.ibm.com>
Cc: Thomas Richter <tmricht@linux.ibm.com>
Cc: Vasily Gorbik <gor@linux.ibm.com>
Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
tools/perf/util/data-convert-bt.c
tools/perf/util/data-convert-json.c
tools/perf/util/env.c
tools/perf/util/env.h
tools/perf/util/header.c
tools/perf/util/symbol.c

index b3f745cff2a75d9e2cb78889a48f7c17c7ded9e9..cc51b8677c8e7c67f9f1918577b14ac2c099fbf5 100644 (file)
@@ -1414,7 +1414,7 @@ do {                                                                      \
 
        ADD("host",    env->hostname);
        ADD("sysname", "Linux");
-       ADD("release", env->os_release);
+       ADD("release", perf_env__os_release(env));
        ADD("version", env->version);
        ADD("machine", env->arch);
        ADD("domain", "kernel");
index a7da93a7ff0e6b4ae61057b66b917bf7e627d2c8..c71dfb77c697b51200f786e98893c66aacc3b63e 100644 (file)
@@ -16,6 +16,7 @@
 #include "linux/err.h"
 #include "util/auxtrace.h"
 #include "util/debug.h"
+#include "util/env.h"
 #include "util/dso.h"
 #include "util/event.h"
 #include "util/evsel.h"
@@ -272,7 +273,7 @@ static void output_headers(struct perf_session *session, struct convert_json *c)
 {
        struct stat st;
        const struct perf_header *header = &session->header;
-       const struct perf_env *env = perf_session__env(session);
+       struct perf_env *env = perf_session__env(session);
        int ret;
        int fd = perf_data__fd(session->data);
        int i;
@@ -296,7 +297,8 @@ static void output_headers(struct perf_session *session, struct convert_json *c)
        output_json_key_format(out, true, 2, "feat-offset", "%" PRIu64, header->feat_offset);
 
        output_json_key_string(out, true, 2, "hostname", env->hostname);
-       output_json_key_string(out, true, 2, "os-release", env->os_release);
+       output_json_key_string(out, true, 2, "os-release",
+                              perf_env__os_release(env));
        output_json_key_string(out, true, 2, "arch", env->arch);
 
        if (env->cpu_desc)
index 03d90a45992c33a83c0db07861c1bae6809b2dd8..c0e2b9d5f0b2c7bbebe2bbe6593b2575799bf102 100644 (file)
@@ -361,6 +361,44 @@ bool perf_arch_is_big_endian(const char *arch)
        return false;
 }
 
+const char *perf_env__os_release(struct perf_env *env)
+{
+       struct utsname uts;
+       int ret;
+       const char *release;
+
+       if (!env)
+               return perf_version_string;
+
+       mutex_lock(&env->lock);
+       if (env->os_release) {
+               release = env->os_release;
+               goto out;
+       }
+
+       /*
+        * If env->arch is set, this is an offline target environment.
+        * If the os_release is not populated in the file, we do not want
+        * to poison it with the host's release which would break guest checks.
+        */
+       if (env->arch) {
+               release = NULL;
+               goto out;
+       }
+
+       /*
+        * The os_release is being accessed but wasn't initialized from a data
+        * file, assume this is 'live' mode and use the release from uname. If
+        * uname or strdup fails then use the current perf tool version.
+        */
+       ret = uname(&uts);
+       env->os_release = strdup(ret < 0 ? perf_version_string : uts.release);
+       release = env->os_release ?: perf_version_string;
+out:
+       mutex_unlock(&env->lock);
+       return release;
+}
+
 int perf_env__set_cmdline(struct perf_env *env, int argc, const char *argv[])
 {
        int i;
index 6aaf80c640bd061165b3201567ecdfe29ea98b71..7621d1f73b83a3415d18e970d77069b42101899e 100644 (file)
@@ -176,6 +176,7 @@ void perf_env__exit(struct perf_env *env);
 
 int perf_env__kernel_is_64_bit(struct perf_env *env);
 bool perf_arch_is_big_endian(const char *arch);
+const char *perf_env__os_release(struct perf_env *env);
 
 int perf_env__set_cmdline(struct perf_env *env, int argc, const char *argv[]);
 
index ecdac427d9c41c45eda379e1255839b3372b267f..d7f41db7322cbcb46b1f7551adb56dedf3c6afaf 100644 (file)
@@ -432,13 +432,19 @@ static int write_osrelease(struct feat_fd *ff,
                           struct evlist *evlist __maybe_unused)
 {
        struct utsname uts;
-       int ret;
+       const char *release = NULL;
 
-       ret = uname(&uts);
-       if (ret < 0)
-               return -1;
+       if (evlist->session)
+               release = perf_env__os_release(perf_session__env(evlist->session));
 
-       return do_write_string(ff, uts.release);
+       if (!release) {
+               int ret = uname(&uts);
+
+               if (ret < 0)
+                       return -1;
+               release = uts.release;
+       }
+       return do_write_string(ff, release);
 }
 
 static int write_arch(struct feat_fd *ff, struct evlist *evlist)
index 2ce512f08a1d6fea431071105a1e694bd617bcc8..077d19af5240871e8bc287d25500ba8206cf0d80 100644 (file)
@@ -2225,7 +2225,7 @@ static int vmlinux_path__init(struct perf_env *env)
 {
        struct utsname uts;
        char bf[PATH_MAX];
-       char *kernel_version;
+       const char *kernel_version;
        unsigned int i;
 
        vmlinux_path = malloc(sizeof(char *) * (ARRAY_SIZE(vmlinux_paths) +
@@ -2242,7 +2242,7 @@ static int vmlinux_path__init(struct perf_env *env)
                return 0;
 
        if (env) {
-               kernel_version = env->os_release;
+               kernel_version = perf_env__os_release(env);
        } else {
                if (uname(&uts) < 0)
                        goto out_fail;