linux/tools/perf/util/header.c
<<
>>
Prefs
   1#include "util.h"
   2#include <sys/types.h>
   3#include <byteswap.h>
   4#include <unistd.h>
   5#include <stdio.h>
   6#include <stdlib.h>
   7#include <linux/list.h>
   8#include <linux/kernel.h>
   9#include <linux/bitops.h>
  10#include <sys/utsname.h>
  11
  12#include "evlist.h"
  13#include "evsel.h"
  14#include "header.h"
  15#include "../perf.h"
  16#include "trace-event.h"
  17#include "session.h"
  18#include "symbol.h"
  19#include "debug.h"
  20#include "cpumap.h"
  21#include "pmu.h"
  22#include "vdso.h"
  23#include "strbuf.h"
  24#include "build-id.h"
  25
  26static bool no_buildid_cache = false;
  27
  28static int trace_event_count;
  29static struct perf_trace_event_type *trace_events;
  30
  31static u32 header_argc;
  32static const char **header_argv;
  33
  34int perf_header__push_event(u64 id, const char *name)
  35{
  36        struct perf_trace_event_type *nevents;
  37
  38        if (strlen(name) > MAX_EVENT_NAME)
  39                pr_warning("Event %s will be truncated\n", name);
  40
  41        nevents = realloc(trace_events, (trace_event_count + 1) * sizeof(*trace_events));
  42        if (nevents == NULL)
  43                return -ENOMEM;
  44        trace_events = nevents;
  45
  46        memset(&trace_events[trace_event_count], 0, sizeof(struct perf_trace_event_type));
  47        trace_events[trace_event_count].event_id = id;
  48        strncpy(trace_events[trace_event_count].name, name, MAX_EVENT_NAME - 1);
  49        trace_event_count++;
  50        return 0;
  51}
  52
  53char *perf_header__find_event(u64 id)
  54{
  55        int i;
  56        for (i = 0 ; i < trace_event_count; i++) {
  57                if (trace_events[i].event_id == id)
  58                        return trace_events[i].name;
  59        }
  60        return NULL;
  61}
  62
  63/*
  64 * magic2 = "PERFILE2"
  65 * must be a numerical value to let the endianness
  66 * determine the memory layout. That way we are able
  67 * to detect endianness when reading the perf.data file
  68 * back.
  69 *
  70 * we check for legacy (PERFFILE) format.
  71 */
  72static const char *__perf_magic1 = "PERFFILE";
  73static const u64 __perf_magic2    = 0x32454c4946524550ULL;
  74static const u64 __perf_magic2_sw = 0x50455246494c4532ULL;
  75
  76#define PERF_MAGIC      __perf_magic2
  77
  78struct perf_file_attr {
  79        struct perf_event_attr  attr;
  80        struct perf_file_section        ids;
  81};
  82
  83void perf_header__set_feat(struct perf_header *header, int feat)
  84{
  85        set_bit(feat, header->adds_features);
  86}
  87
  88void perf_header__clear_feat(struct perf_header *header, int feat)
  89{
  90        clear_bit(feat, header->adds_features);
  91}
  92
  93bool perf_header__has_feat(const struct perf_header *header, int feat)
  94{
  95        return test_bit(feat, header->adds_features);
  96}
  97
  98static int do_write(int fd, const void *buf, size_t size)
  99{
 100        while (size) {
 101                int ret = write(fd, buf, size);
 102
 103                if (ret < 0)
 104                        return -errno;
 105
 106                size -= ret;
 107                buf += ret;
 108        }
 109
 110        return 0;
 111}
 112
 113#define NAME_ALIGN 64
 114
 115static int write_padded(int fd, const void *bf, size_t count,
 116                        size_t count_aligned)
 117{
 118        static const char zero_buf[NAME_ALIGN];
 119        int err = do_write(fd, bf, count);
 120
 121        if (!err)
 122                err = do_write(fd, zero_buf, count_aligned - count);
 123
 124        return err;
 125}
 126
 127static int do_write_string(int fd, const char *str)
 128{
 129        u32 len, olen;
 130        int ret;
 131
 132        olen = strlen(str) + 1;
 133        len = PERF_ALIGN(olen, NAME_ALIGN);
 134
 135        /* write len, incl. \0 */
 136        ret = do_write(fd, &len, sizeof(len));
 137        if (ret < 0)
 138                return ret;
 139
 140        return write_padded(fd, str, olen, len);
 141}
 142
 143static char *do_read_string(int fd, struct perf_header *ph)
 144{
 145        ssize_t sz, ret;
 146        u32 len;
 147        char *buf;
 148
 149        sz = readn(fd, &len, sizeof(len));
 150        if (sz < (ssize_t)sizeof(len))
 151                return NULL;
 152
 153        if (ph->needs_swap)
 154                len = bswap_32(len);
 155
 156        buf = malloc(len);
 157        if (!buf)
 158                return NULL;
 159
 160        ret = readn(fd, buf, len);
 161        if (ret == (ssize_t)len) {
 162                /*
 163                 * strings are padded by zeroes
 164                 * thus the actual strlen of buf
 165                 * may be less than len
 166                 */
 167                return buf;
 168        }
 169
 170        free(buf);
 171        return NULL;
 172}
 173
 174int
 175perf_header__set_cmdline(int argc, const char **argv)
 176{
 177        int i;
 178
 179        /*
 180         * If header_argv has already been set, do not override it.
 181         * This allows a command to set the cmdline, parse args and
 182         * then call another builtin function that implements a
 183         * command -- e.g, cmd_kvm calling cmd_record.
 184         */
 185        if (header_argv)
 186                return 0;
 187
 188        header_argc = (u32)argc;
 189
 190        /* do not include NULL termination */
 191        header_argv = calloc(argc, sizeof(char *));
 192        if (!header_argv)
 193                return -ENOMEM;
 194
 195        /*
 196         * must copy argv contents because it gets moved
 197         * around during option parsing
 198         */
 199        for (i = 0; i < argc ; i++)
 200                header_argv[i] = argv[i];
 201
 202        return 0;
 203}
 204
 205#define dsos__for_each_with_build_id(pos, head) \
 206        list_for_each_entry(pos, head, node)    \
 207                if (!pos->has_build_id)         \
 208                        continue;               \
 209                else
 210
 211static int write_buildid(char *name, size_t name_len, u8 *build_id,
 212                         pid_t pid, u16 misc, int fd)
 213{
 214        int err;
 215        struct build_id_event b;
 216        size_t len;
 217
 218        len = name_len + 1;
 219        len = PERF_ALIGN(len, NAME_ALIGN);
 220
 221        memset(&b, 0, sizeof(b));
 222        memcpy(&b.build_id, build_id, BUILD_ID_SIZE);
 223        b.pid = pid;
 224        b.header.misc = misc;
 225        b.header.size = sizeof(b) + len;
 226
 227        err = do_write(fd, &b, sizeof(b));
 228        if (err < 0)
 229                return err;
 230
 231        return write_padded(fd, name, name_len + 1, len);
 232}
 233
 234static int __dsos__write_buildid_table(struct list_head *head, pid_t pid,
 235                                u16 misc, int fd)
 236{
 237        struct dso *pos;
 238
 239        dsos__for_each_with_build_id(pos, head) {
 240                int err;
 241                char  *name;
 242                size_t name_len;
 243
 244                if (!pos->hit)
 245                        continue;
 246
 247                if (is_vdso_map(pos->short_name)) {
 248                        name = (char *) VDSO__MAP_NAME;
 249                        name_len = sizeof(VDSO__MAP_NAME) + 1;
 250                } else {
 251                        name = pos->long_name;
 252                        name_len = pos->long_name_len + 1;
 253                }
 254
 255                err = write_buildid(name, name_len, pos->build_id,
 256                                    pid, misc, fd);
 257                if (err)
 258                        return err;
 259        }
 260
 261        return 0;
 262}
 263
 264static int machine__write_buildid_table(struct machine *machine, int fd)
 265{
 266        int err;
 267        u16 kmisc = PERF_RECORD_MISC_KERNEL,
 268            umisc = PERF_RECORD_MISC_USER;
 269
 270        if (!machine__is_host(machine)) {
 271                kmisc = PERF_RECORD_MISC_GUEST_KERNEL;
 272                umisc = PERF_RECORD_MISC_GUEST_USER;
 273        }
 274
 275        err = __dsos__write_buildid_table(&machine->kernel_dsos, machine->pid,
 276                                          kmisc, fd);
 277        if (err == 0)
 278                err = __dsos__write_buildid_table(&machine->user_dsos,
 279                                                  machine->pid, umisc, fd);
 280        return err;
 281}
 282
 283static int dsos__write_buildid_table(struct perf_header *header, int fd)
 284{
 285        struct perf_session *session = container_of(header,
 286                        struct perf_session, header);
 287        struct rb_node *nd;
 288        int err = machine__write_buildid_table(&session->machines.host, fd);
 289
 290        if (err)
 291                return err;
 292
 293        for (nd = rb_first(&session->machines.guests); nd; nd = rb_next(nd)) {
 294                struct machine *pos = rb_entry(nd, struct machine, rb_node);
 295                err = machine__write_buildid_table(pos, fd);
 296                if (err)
 297                        break;
 298        }
 299        return err;
 300}
 301
 302int build_id_cache__add_s(const char *sbuild_id, const char *debugdir,
 303                          const char *name, bool is_kallsyms, bool is_vdso)
 304{
 305        const size_t size = PATH_MAX;
 306        char *realname, *filename = zalloc(size),
 307             *linkname = zalloc(size), *targetname;
 308        int len, err = -1;
 309        bool slash = is_kallsyms || is_vdso;
 310
 311        if (is_kallsyms) {
 312                if (symbol_conf.kptr_restrict) {
 313                        pr_debug("Not caching a kptr_restrict'ed /proc/kallsyms\n");
 314                        err = 0;
 315                        goto out_free;
 316                }
 317                realname = (char *) name;
 318        } else
 319                realname = realpath(name, NULL);
 320
 321        if (realname == NULL || filename == NULL || linkname == NULL)
 322                goto out_free;
 323
 324        len = scnprintf(filename, size, "%s%s%s",
 325                       debugdir, slash ? "/" : "",
 326                       is_vdso ? VDSO__MAP_NAME : realname);
 327        if (mkdir_p(filename, 0755))
 328                goto out_free;
 329
 330        snprintf(filename + len, size - len, "/%s", sbuild_id);
 331
 332        if (access(filename, F_OK)) {
 333                if (is_kallsyms) {
 334                         if (copyfile("/proc/kallsyms", filename))
 335                                goto out_free;
 336                } else if (link(realname, filename) && copyfile(name, filename))
 337                        goto out_free;
 338        }
 339
 340        len = scnprintf(linkname, size, "%s/.build-id/%.2s",
 341                       debugdir, sbuild_id);
 342
 343        if (access(linkname, X_OK) && mkdir_p(linkname, 0755))
 344                goto out_free;
 345
 346        snprintf(linkname + len, size - len, "/%s", sbuild_id + 2);
 347        targetname = filename + strlen(debugdir) - 5;
 348        memcpy(targetname, "../..", 5);
 349
 350        if (symlink(targetname, linkname) == 0)
 351                err = 0;
 352out_free:
 353        if (!is_kallsyms)
 354                free(realname);
 355        free(filename);
 356        free(linkname);
 357        return err;
 358}
 359
 360static int build_id_cache__add_b(const u8 *build_id, size_t build_id_size,
 361                                 const char *name, const char *debugdir,
 362                                 bool is_kallsyms, bool is_vdso)
 363{
 364        char sbuild_id[BUILD_ID_SIZE * 2 + 1];
 365
 366        build_id__sprintf(build_id, build_id_size, sbuild_id);
 367
 368        return build_id_cache__add_s(sbuild_id, debugdir, name,
 369                                     is_kallsyms, is_vdso);
 370}
 371
 372int build_id_cache__remove_s(const char *sbuild_id, const char *debugdir)
 373{
 374        const size_t size = PATH_MAX;
 375        char *filename = zalloc(size),
 376             *linkname = zalloc(size);
 377        int err = -1;
 378
 379        if (filename == NULL || linkname == NULL)
 380                goto out_free;
 381
 382        snprintf(linkname, size, "%s/.build-id/%.2s/%s",
 383                 debugdir, sbuild_id, sbuild_id + 2);
 384
 385        if (access(linkname, F_OK))
 386                goto out_free;
 387
 388        if (readlink(linkname, filename, size - 1) < 0)
 389                goto out_free;
 390
 391        if (unlink(linkname))
 392                goto out_free;
 393
 394        /*
 395         * Since the link is relative, we must make it absolute:
 396         */
 397        snprintf(linkname, size, "%s/.build-id/%.2s/%s",
 398                 debugdir, sbuild_id, filename);
 399
 400        if (unlink(linkname))
 401                goto out_free;
 402
 403        err = 0;
 404out_free:
 405        free(filename);
 406        free(linkname);
 407        return err;
 408}
 409
 410static int dso__cache_build_id(struct dso *dso, const char *debugdir)
 411{
 412        bool is_kallsyms = dso->kernel && dso->long_name[0] != '/';
 413        bool is_vdso = is_vdso_map(dso->short_name);
 414
 415        return build_id_cache__add_b(dso->build_id, sizeof(dso->build_id),
 416                                     dso->long_name, debugdir,
 417                                     is_kallsyms, is_vdso);
 418}
 419
 420static int __dsos__cache_build_ids(struct list_head *head, const char *debugdir)
 421{
 422        struct dso *pos;
 423        int err = 0;
 424
 425        dsos__for_each_with_build_id(pos, head)
 426                if (dso__cache_build_id(pos, debugdir))
 427                        err = -1;
 428
 429        return err;
 430}
 431
 432static int machine__cache_build_ids(struct machine *machine, const char *debugdir)
 433{
 434        int ret = __dsos__cache_build_ids(&machine->kernel_dsos, debugdir);
 435        ret |= __dsos__cache_build_ids(&machine->user_dsos, debugdir);
 436        return ret;
 437}
 438
 439static int perf_session__cache_build_ids(struct perf_session *session)
 440{
 441        struct rb_node *nd;
 442        int ret;
 443        char debugdir[PATH_MAX];
 444
 445        snprintf(debugdir, sizeof(debugdir), "%s", buildid_dir);
 446
 447        if (mkdir(debugdir, 0755) != 0 && errno != EEXIST)
 448                return -1;
 449
 450        ret = machine__cache_build_ids(&session->machines.host, debugdir);
 451
 452        for (nd = rb_first(&session->machines.guests); nd; nd = rb_next(nd)) {
 453                struct machine *pos = rb_entry(nd, struct machine, rb_node);
 454                ret |= machine__cache_build_ids(pos, debugdir);
 455        }
 456        return ret ? -1 : 0;
 457}
 458
 459static bool machine__read_build_ids(struct machine *machine, bool with_hits)
 460{
 461        bool ret = __dsos__read_build_ids(&machine->kernel_dsos, with_hits);
 462        ret |= __dsos__read_build_ids(&machine->user_dsos, with_hits);
 463        return ret;
 464}
 465
 466static bool perf_session__read_build_ids(struct perf_session *session, bool with_hits)
 467{
 468        struct rb_node *nd;
 469        bool ret = machine__read_build_ids(&session->machines.host, with_hits);
 470
 471        for (nd = rb_first(&session->machines.guests); nd; nd = rb_next(nd)) {
 472                struct machine *pos = rb_entry(nd, struct machine, rb_node);
 473                ret |= machine__read_build_ids(pos, with_hits);
 474        }
 475
 476        return ret;
 477}
 478
 479static int write_tracing_data(int fd, struct perf_header *h __maybe_unused,
 480                            struct perf_evlist *evlist)
 481{
 482        return read_tracing_data(fd, &evlist->entries);
 483}
 484
 485
 486static int write_build_id(int fd, struct perf_header *h,
 487                          struct perf_evlist *evlist __maybe_unused)
 488{
 489        struct perf_session *session;
 490        int err;
 491
 492        session = container_of(h, struct perf_session, header);
 493
 494        if (!perf_session__read_build_ids(session, true))
 495                return -1;
 496
 497        err = dsos__write_buildid_table(h, fd);
 498        if (err < 0) {
 499                pr_debug("failed to write buildid table\n");
 500                return err;
 501        }
 502        if (!no_buildid_cache)
 503                perf_session__cache_build_ids(session);
 504
 505        return 0;
 506}
 507
 508static int write_hostname(int fd, struct perf_header *h __maybe_unused,
 509                          struct perf_evlist *evlist __maybe_unused)
 510{
 511        struct utsname uts;
 512        int ret;
 513
 514        ret = uname(&uts);
 515        if (ret < 0)
 516                return -1;
 517
 518        return do_write_string(fd, uts.nodename);
 519}
 520
 521static int write_osrelease(int fd, struct perf_header *h __maybe_unused,
 522                           struct perf_evlist *evlist __maybe_unused)
 523{
 524        struct utsname uts;
 525        int ret;
 526
 527        ret = uname(&uts);
 528        if (ret < 0)
 529                return -1;
 530
 531        return do_write_string(fd, uts.release);
 532}
 533
 534static int write_arch(int fd, struct perf_header *h __maybe_unused,
 535                      struct perf_evlist *evlist __maybe_unused)
 536{
 537        struct utsname uts;
 538        int ret;
 539
 540        ret = uname(&uts);
 541        if (ret < 0)
 542                return -1;
 543
 544        return do_write_string(fd, uts.machine);
 545}
 546
 547static int write_version(int fd, struct perf_header *h __maybe_unused,
 548                         struct perf_evlist *evlist __maybe_unused)
 549{
 550        return do_write_string(fd, perf_version_string);
 551}
 552
 553static int write_cpudesc(int fd, struct perf_header *h __maybe_unused,
 554                       struct perf_evlist *evlist __maybe_unused)
 555{
 556#ifndef CPUINFO_PROC
 557#define CPUINFO_PROC NULL
 558#endif
 559        FILE *file;
 560        char *buf = NULL;
 561        char *s, *p;
 562        const char *search = CPUINFO_PROC;
 563        size_t len = 0;
 564        int ret = -1;
 565
 566        if (!search)
 567                return -1;
 568
 569        file = fopen("/proc/cpuinfo", "r");
 570        if (!file)
 571                return -1;
 572
 573        while (getline(&buf, &len, file) > 0) {
 574                ret = strncmp(buf, search, strlen(search));
 575                if (!ret)
 576                        break;
 577        }
 578
 579        if (ret)
 580                goto done;
 581
 582        s = buf;
 583
 584        p = strchr(buf, ':');
 585        if (p && *(p+1) == ' ' && *(p+2))
 586                s = p + 2;
 587        p = strchr(s, '\n');
 588        if (p)
 589                *p = '\0';
 590
 591        /* squash extra space characters (branding string) */
 592        p = s;
 593        while (*p) {
 594                if (isspace(*p)) {
 595                        char *r = p + 1;
 596                        char *q = r;
 597                        *p = ' ';
 598                        while (*q && isspace(*q))
 599                                q++;
 600                        if (q != (p+1))
 601                                while ((*r++ = *q++));
 602                }
 603                p++;
 604        }
 605        ret = do_write_string(fd, s);
 606done:
 607        free(buf);
 608        fclose(file);
 609        return ret;
 610}
 611
 612static int write_nrcpus(int fd, struct perf_header *h __maybe_unused,
 613                        struct perf_evlist *evlist __maybe_unused)
 614{
 615        long nr;
 616        u32 nrc, nra;
 617        int ret;
 618
 619        nr = sysconf(_SC_NPROCESSORS_CONF);
 620        if (nr < 0)
 621                return -1;
 622
 623        nrc = (u32)(nr & UINT_MAX);
 624
 625        nr = sysconf(_SC_NPROCESSORS_ONLN);
 626        if (nr < 0)
 627                return -1;
 628
 629        nra = (u32)(nr & UINT_MAX);
 630
 631        ret = do_write(fd, &nrc, sizeof(nrc));
 632        if (ret < 0)
 633                return ret;
 634
 635        return do_write(fd, &nra, sizeof(nra));
 636}
 637
 638static int write_event_desc(int fd, struct perf_header *h __maybe_unused,
 639                            struct perf_evlist *evlist)
 640{
 641        struct perf_evsel *evsel;
 642        u32 nre, nri, sz;
 643        int ret;
 644
 645        nre = evlist->nr_entries;
 646
 647        /*
 648         * write number of events
 649         */
 650        ret = do_write(fd, &nre, sizeof(nre));
 651        if (ret < 0)
 652                return ret;
 653
 654        /*
 655         * size of perf_event_attr struct
 656         */
 657        sz = (u32)sizeof(evsel->attr);
 658        ret = do_write(fd, &sz, sizeof(sz));
 659        if (ret < 0)
 660                return ret;
 661
 662        list_for_each_entry(evsel, &evlist->entries, node) {
 663
 664                ret = do_write(fd, &evsel->attr, sz);
 665                if (ret < 0)
 666                        return ret;
 667                /*
 668                 * write number of unique id per event
 669                 * there is one id per instance of an event
 670                 *
 671                 * copy into an nri to be independent of the
 672                 * type of ids,
 673                 */
 674                nri = evsel->ids;
 675                ret = do_write(fd, &nri, sizeof(nri));
 676                if (ret < 0)
 677                        return ret;
 678
 679                /*
 680                 * write event string as passed on cmdline
 681                 */
 682                ret = do_write_string(fd, perf_evsel__name(evsel));
 683                if (ret < 0)
 684                        return ret;
 685                /*
 686                 * write unique ids for this event
 687                 */
 688                ret = do_write(fd, evsel->id, evsel->ids * sizeof(u64));
 689                if (ret < 0)
 690                        return ret;
 691        }
 692        return 0;
 693}
 694
 695static int write_cmdline(int fd, struct perf_header *h __maybe_unused,
 696                         struct perf_evlist *evlist __maybe_unused)
 697{
 698        char buf[MAXPATHLEN];
 699        char proc[32];
 700        u32 i, n;
 701        int ret;
 702
 703        /*
 704         * actual atual path to perf binary
 705         */
 706        sprintf(proc, "/proc/%d/exe", getpid());
 707        ret = readlink(proc, buf, sizeof(buf));
 708        if (ret <= 0)
 709                return -1;
 710
 711        /* readlink() does not add null termination */
 712        buf[ret] = '\0';
 713
 714        /* account for binary path */
 715        n = header_argc + 1;
 716
 717        ret = do_write(fd, &n, sizeof(n));
 718        if (ret < 0)
 719                return ret;
 720
 721        ret = do_write_string(fd, buf);
 722        if (ret < 0)
 723                return ret;
 724
 725        for (i = 0 ; i < header_argc; i++) {
 726                ret = do_write_string(fd, header_argv[i]);
 727                if (ret < 0)
 728                        return ret;
 729        }
 730        return 0;
 731}
 732
 733#define CORE_SIB_FMT \
 734        "/sys/devices/system/cpu/cpu%d/topology/core_siblings_list"
 735#define THRD_SIB_FMT \
 736        "/sys/devices/system/cpu/cpu%d/topology/thread_siblings_list"
 737
 738struct cpu_topo {
 739        u32 core_sib;
 740        u32 thread_sib;
 741        char **core_siblings;
 742        char **thread_siblings;
 743};
 744
 745static int build_cpu_topo(struct cpu_topo *tp, int cpu)
 746{
 747        FILE *fp;
 748        char filename[MAXPATHLEN];
 749        char *buf = NULL, *p;
 750        size_t len = 0;
 751        u32 i = 0;
 752        int ret = -1;
 753
 754        sprintf(filename, CORE_SIB_FMT, cpu);
 755        fp = fopen(filename, "r");
 756        if (!fp)
 757                return -1;
 758
 759        if (getline(&buf, &len, fp) <= 0)
 760                goto done;
 761
 762        fclose(fp);
 763
 764        p = strchr(buf, '\n');
 765        if (p)
 766                *p = '\0';
 767
 768        for (i = 0; i < tp->core_sib; i++) {
 769                if (!strcmp(buf, tp->core_siblings[i]))
 770                        break;
 771        }
 772        if (i == tp->core_sib) {
 773                tp->core_siblings[i] = buf;
 774                tp->core_sib++;
 775                buf = NULL;
 776                len = 0;
 777        }
 778
 779        sprintf(filename, THRD_SIB_FMT, cpu);
 780        fp = fopen(filename, "r");
 781        if (!fp)
 782                goto done;
 783
 784        if (getline(&buf, &len, fp) <= 0)
 785                goto done;
 786
 787        p = strchr(buf, '\n');
 788        if (p)
 789                *p = '\0';
 790
 791        for (i = 0; i < tp->thread_sib; i++) {
 792                if (!strcmp(buf, tp->thread_siblings[i]))
 793                        break;
 794        }
 795        if (i == tp->thread_sib) {
 796                tp->thread_siblings[i] = buf;
 797                tp->thread_sib++;
 798                buf = NULL;
 799        }
 800        ret = 0;
 801done:
 802        if(fp)
 803                fclose(fp);
 804        free(buf);
 805        return ret;
 806}
 807
 808static void free_cpu_topo(struct cpu_topo *tp)
 809{
 810        u32 i;
 811
 812        if (!tp)
 813                return;
 814
 815        for (i = 0 ; i < tp->core_sib; i++)
 816                free(tp->core_siblings[i]);
 817
 818        for (i = 0 ; i < tp->thread_sib; i++)
 819                free(tp->thread_siblings[i]);
 820
 821        free(tp);
 822}
 823
 824static struct cpu_topo *build_cpu_topology(void)
 825{
 826        struct cpu_topo *tp;
 827        void *addr;
 828        u32 nr, i;
 829        size_t sz;
 830        long ncpus;
 831        int ret = -1;
 832
 833        ncpus = sysconf(_SC_NPROCESSORS_CONF);
 834        if (ncpus < 0)
 835                return NULL;
 836
 837        nr = (u32)(ncpus & UINT_MAX);
 838
 839        sz = nr * sizeof(char *);
 840
 841        addr = calloc(1, sizeof(*tp) + 2 * sz);
 842        if (!addr)
 843                return NULL;
 844
 845        tp = addr;
 846
 847        addr += sizeof(*tp);
 848        tp->core_siblings = addr;
 849        addr += sz;
 850        tp->thread_siblings = addr;
 851
 852        for (i = 0; i < nr; i++) {
 853                ret = build_cpu_topo(tp, i);
 854                if (ret < 0)
 855                        break;
 856        }
 857        if (ret) {
 858                free_cpu_topo(tp);
 859                tp = NULL;
 860        }
 861        return tp;
 862}
 863
 864static int write_cpu_topology(int fd, struct perf_header *h __maybe_unused,
 865                          struct perf_evlist *evlist __maybe_unused)
 866{
 867        struct cpu_topo *tp;
 868        u32 i;
 869        int ret;
 870
 871        tp = build_cpu_topology();
 872        if (!tp)
 873                return -1;
 874
 875        ret = do_write(fd, &tp->core_sib, sizeof(tp->core_sib));
 876        if (ret < 0)
 877                goto done;
 878
 879        for (i = 0; i < tp->core_sib; i++) {
 880                ret = do_write_string(fd, tp->core_siblings[i]);
 881                if (ret < 0)
 882                        goto done;
 883        }
 884        ret = do_write(fd, &tp->thread_sib, sizeof(tp->thread_sib));
 885        if (ret < 0)
 886                goto done;
 887
 888        for (i = 0; i < tp->thread_sib; i++) {
 889                ret = do_write_string(fd, tp->thread_siblings[i]);
 890                if (ret < 0)
 891                        break;
 892        }
 893done:
 894        free_cpu_topo(tp);
 895        return ret;
 896}
 897
 898
 899
 900static int write_total_mem(int fd, struct perf_header *h __maybe_unused,
 901                          struct perf_evlist *evlist __maybe_unused)
 902{
 903        char *buf = NULL;
 904        FILE *fp;
 905        size_t len = 0;
 906        int ret = -1, n;
 907        uint64_t mem;
 908
 909        fp = fopen("/proc/meminfo", "r");
 910        if (!fp)
 911                return -1;
 912
 913        while (getline(&buf, &len, fp) > 0) {
 914                ret = strncmp(buf, "MemTotal:", 9);
 915                if (!ret)
 916                        break;
 917        }
 918        if (!ret) {
 919                n = sscanf(buf, "%*s %"PRIu64, &mem);
 920                if (n == 1)
 921                        ret = do_write(fd, &mem, sizeof(mem));
 922        }
 923        free(buf);
 924        fclose(fp);
 925        return ret;
 926}
 927
 928static int write_topo_node(int fd, int node)
 929{
 930        char str[MAXPATHLEN];
 931        char field[32];
 932        char *buf = NULL, *p;
 933        size_t len = 0;
 934        FILE *fp;
 935        u64 mem_total, mem_free, mem;
 936        int ret = -1;
 937
 938        sprintf(str, "/sys/devices/system/node/node%d/meminfo", node);
 939        fp = fopen(str, "r");
 940        if (!fp)
 941                return -1;
 942
 943        while (getline(&buf, &len, fp) > 0) {
 944                /* skip over invalid lines */
 945                if (!strchr(buf, ':'))
 946                        continue;
 947                if (sscanf(buf, "%*s %*d %s %"PRIu64, field, &mem) != 2)
 948                        goto done;
 949                if (!strcmp(field, "MemTotal:"))
 950                        mem_total = mem;
 951                if (!strcmp(field, "MemFree:"))
 952                        mem_free = mem;
 953        }
 954
 955        fclose(fp);
 956        fp = NULL;
 957
 958        ret = do_write(fd, &mem_total, sizeof(u64));
 959        if (ret)
 960                goto done;
 961
 962        ret = do_write(fd, &mem_free, sizeof(u64));
 963        if (ret)
 964                goto done;
 965
 966        ret = -1;
 967        sprintf(str, "/sys/devices/system/node/node%d/cpulist", node);
 968
 969        fp = fopen(str, "r");
 970        if (!fp)
 971                goto done;
 972
 973        if (getline(&buf, &len, fp) <= 0)
 974                goto done;
 975
 976        p = strchr(buf, '\n');
 977        if (p)
 978                *p = '\0';
 979
 980        ret = do_write_string(fd, buf);
 981done:
 982        free(buf);
 983        if (fp)
 984                fclose(fp);
 985        return ret;
 986}
 987
 988static int write_numa_topology(int fd, struct perf_header *h __maybe_unused,
 989                          struct perf_evlist *evlist __maybe_unused)
 990{
 991        char *buf = NULL;
 992        size_t len = 0;
 993        FILE *fp;
 994        struct cpu_map *node_map = NULL;
 995        char *c;
 996        u32 nr, i, j;
 997        int ret = -1;
 998
 999        fp = fopen("/sys/devices/system/node/online", "r");
1000        if (!fp)
1001                return -1;
1002
1003        if (getline(&buf, &len, fp) <= 0)
1004                goto done;
1005
1006        c = strchr(buf, '\n');
1007        if (c)
1008                *c = '\0';
1009
1010        node_map = cpu_map__new(buf);
1011        if (!node_map)
1012                goto done;
1013
1014        nr = (u32)node_map->nr;
1015
1016        ret = do_write(fd, &nr, sizeof(nr));
1017        if (ret < 0)
1018                goto done;
1019
1020        for (i = 0; i < nr; i++) {
1021                j = (u32)node_map->map[i];
1022                ret = do_write(fd, &j, sizeof(j));
1023                if (ret < 0)
1024                        break;
1025
1026                ret = write_topo_node(fd, i);
1027                if (ret < 0)
1028                        break;
1029        }
1030done:
1031        free(buf);
1032        fclose(fp);
1033        free(node_map);
1034        return ret;
1035}
1036
1037/*
1038 * File format:
1039 *
1040 * struct pmu_mappings {
1041 *      u32     pmu_num;
1042 *      struct pmu_map {
1043 *              u32     type;
1044 *              char    name[];
1045 *      }[pmu_num];
1046 * };
1047 */
1048
1049static int write_pmu_mappings(int fd, struct perf_header *h __maybe_unused,
1050                              struct perf_evlist *evlist __maybe_unused)
1051{
1052        struct perf_pmu *pmu = NULL;
1053        off_t offset = lseek(fd, 0, SEEK_CUR);
1054        __u32 pmu_num = 0;
1055        int ret;
1056
1057        /* write real pmu_num later */
1058        ret = do_write(fd, &pmu_num, sizeof(pmu_num));
1059        if (ret < 0)
1060                return ret;
1061
1062        while ((pmu = perf_pmu__scan(pmu))) {
1063                if (!pmu->name)
1064                        continue;
1065                pmu_num++;
1066
1067                ret = do_write(fd, &pmu->type, sizeof(pmu->type));
1068                if (ret < 0)
1069                        return ret;
1070
1071                ret = do_write_string(fd, pmu->name);
1072                if (ret < 0)
1073                        return ret;
1074        }
1075
1076        if (pwrite(fd, &pmu_num, sizeof(pmu_num), offset) != sizeof(pmu_num)) {
1077                /* discard all */
1078                lseek(fd, offset, SEEK_SET);
1079                return -1;
1080        }
1081
1082        return 0;
1083}
1084
1085/*
1086 * File format:
1087 *
1088 * struct group_descs {
1089 *      u32     nr_groups;
1090 *      struct group_desc {
1091 *              char    name[];
1092 *              u32     leader_idx;
1093 *              u32     nr_members;
1094 *      }[nr_groups];
1095 * };
1096 */
1097static int write_group_desc(int fd, struct perf_header *h __maybe_unused,
1098                            struct perf_evlist *evlist)
1099{
1100        u32 nr_groups = evlist->nr_groups;
1101        struct perf_evsel *evsel;
1102        int ret;
1103
1104        ret = do_write(fd, &nr_groups, sizeof(nr_groups));
1105        if (ret < 0)
1106                return ret;
1107
1108        list_for_each_entry(evsel, &evlist->entries, node) {
1109                if (perf_evsel__is_group_leader(evsel) &&
1110                    evsel->nr_members > 1) {
1111                        const char *name = evsel->group_name ?: "{anon_group}";
1112                        u32 leader_idx = evsel->idx;
1113                        u32 nr_members = evsel->nr_members;
1114
1115                        ret = do_write_string(fd, name);
1116                        if (ret < 0)
1117                                return ret;
1118
1119                        ret = do_write(fd, &leader_idx, sizeof(leader_idx));
1120                        if (ret < 0)
1121                                return ret;
1122
1123                        ret = do_write(fd, &nr_members, sizeof(nr_members));
1124                        if (ret < 0)
1125                                return ret;
1126                }
1127        }
1128        return 0;
1129}
1130
1131/*
1132 * default get_cpuid(): nothing gets recorded
1133 * actual implementation must be in arch/$(ARCH)/util/header.c
1134 */
1135int __attribute__ ((weak)) get_cpuid(char *buffer __maybe_unused,
1136                                     size_t sz __maybe_unused)
1137{
1138        return -1;
1139}
1140
1141static int write_cpuid(int fd, struct perf_header *h __maybe_unused,
1142                       struct perf_evlist *evlist __maybe_unused)
1143{
1144        char buffer[64];
1145        int ret;
1146
1147        ret = get_cpuid(buffer, sizeof(buffer));
1148        if (!ret)
1149                goto write_it;
1150
1151        return -1;
1152write_it:
1153        return do_write_string(fd, buffer);
1154}
1155
1156static int write_branch_stack(int fd __maybe_unused,
1157                              struct perf_header *h __maybe_unused,
1158                       struct perf_evlist *evlist __maybe_unused)
1159{
1160        return 0;
1161}
1162
1163static void print_hostname(struct perf_header *ph, int fd __maybe_unused,
1164                           FILE *fp)
1165{
1166        fprintf(fp, "# hostname : %s\n", ph->env.hostname);
1167}
1168
1169static void print_osrelease(struct perf_header *ph, int fd __maybe_unused,
1170                            FILE *fp)
1171{
1172        fprintf(fp, "# os release : %s\n", ph->env.os_release);
1173}
1174
1175static void print_arch(struct perf_header *ph, int fd __maybe_unused, FILE *fp)
1176{
1177        fprintf(fp, "# arch : %s\n", ph->env.arch);
1178}
1179
1180static void print_cpudesc(struct perf_header *ph, int fd __maybe_unused,
1181                          FILE *fp)
1182{
1183        fprintf(fp, "# cpudesc : %s\n", ph->env.cpu_desc);
1184}
1185
1186static void print_nrcpus(struct perf_header *ph, int fd __maybe_unused,
1187                         FILE *fp)
1188{
1189        fprintf(fp, "# nrcpus online : %u\n", ph->env.nr_cpus_online);
1190        fprintf(fp, "# nrcpus avail : %u\n", ph->env.nr_cpus_avail);
1191}
1192
1193static void print_version(struct perf_header *ph, int fd __maybe_unused,
1194                          FILE *fp)
1195{
1196        fprintf(fp, "# perf version : %s\n", ph->env.version);
1197}
1198
1199static void print_cmdline(struct perf_header *ph, int fd __maybe_unused,
1200                          FILE *fp)
1201{
1202        int nr, i;
1203        char *str;
1204
1205        nr = ph->env.nr_cmdline;
1206        str = ph->env.cmdline;
1207
1208        fprintf(fp, "# cmdline : ");
1209
1210        for (i = 0; i < nr; i++) {
1211                fprintf(fp, "%s ", str);
1212                str += strlen(str) + 1;
1213        }
1214        fputc('\n', fp);
1215}
1216
1217static void print_cpu_topology(struct perf_header *ph, int fd __maybe_unused,
1218                               FILE *fp)
1219{
1220        int nr, i;
1221        char *str;
1222
1223        nr = ph->env.nr_sibling_cores;
1224        str = ph->env.sibling_cores;
1225
1226        for (i = 0; i < nr; i++) {
1227                fprintf(fp, "# sibling cores   : %s\n", str);
1228                str += strlen(str) + 1;
1229        }
1230
1231        nr = ph->env.nr_sibling_threads;
1232        str = ph->env.sibling_threads;
1233
1234        for (i = 0; i < nr; i++) {
1235                fprintf(fp, "# sibling threads : %s\n", str);
1236                str += strlen(str) + 1;
1237        }
1238}
1239
1240static void free_event_desc(struct perf_evsel *events)
1241{
1242        struct perf_evsel *evsel;
1243
1244        if (!events)
1245                return;
1246
1247        for (evsel = events; evsel->attr.size; evsel++) {
1248                if (evsel->name)
1249                        free(evsel->name);
1250                if (evsel->id)
1251                        free(evsel->id);
1252        }
1253
1254        free(events);
1255}
1256
1257static struct perf_evsel *
1258read_event_desc(struct perf_header *ph, int fd)
1259{
1260        struct perf_evsel *evsel, *events = NULL;
1261        u64 *id;
1262        void *buf = NULL;
1263        u32 nre, sz, nr, i, j;
1264        ssize_t ret;
1265        size_t msz;
1266
1267        /* number of events */
1268        ret = readn(fd, &nre, sizeof(nre));
1269        if (ret != (ssize_t)sizeof(nre))
1270                goto error;
1271
1272        if (ph->needs_swap)
1273                nre = bswap_32(nre);
1274
1275        ret = readn(fd, &sz, sizeof(sz));
1276        if (ret != (ssize_t)sizeof(sz))
1277                goto error;
1278
1279        if (ph->needs_swap)
1280                sz = bswap_32(sz);
1281
1282        /* buffer to hold on file attr struct */
1283        buf = malloc(sz);
1284        if (!buf)
1285                goto error;
1286
1287        /* the last event terminates with evsel->attr.size == 0: */
1288        events = calloc(nre + 1, sizeof(*events));
1289        if (!events)
1290                goto error;
1291
1292        msz = sizeof(evsel->attr);
1293        if (sz < msz)
1294                msz = sz;
1295
1296        for (i = 0, evsel = events; i < nre; evsel++, i++) {
1297                evsel->idx = i;
1298
1299                /*
1300                 * must read entire on-file attr struct to
1301                 * sync up with layout.
1302                 */
1303                ret = readn(fd, buf, sz);
1304                if (ret != (ssize_t)sz)
1305                        goto error;
1306
1307                if (ph->needs_swap)
1308                        perf_event__attr_swap(buf);
1309
1310                memcpy(&evsel->attr, buf, msz);
1311
1312                ret = readn(fd, &nr, sizeof(nr));
1313                if (ret != (ssize_t)sizeof(nr))
1314                        goto error;
1315
1316                if (ph->needs_swap) {
1317                        nr = bswap_32(nr);
1318                        evsel->needs_swap = true;
1319                }
1320
1321                evsel->name = do_read_string(fd, ph);
1322
1323                if (!nr)
1324                        continue;
1325
1326                id = calloc(nr, sizeof(*id));
1327                if (!id)
1328                        goto error;
1329                evsel->ids = nr;
1330                evsel->id = id;
1331
1332                for (j = 0 ; j < nr; j++) {
1333                        ret = readn(fd, id, sizeof(*id));
1334                        if (ret != (ssize_t)sizeof(*id))
1335                                goto error;
1336                        if (ph->needs_swap)
1337                                *id = bswap_64(*id);
1338                        id++;
1339                }
1340        }
1341out:
1342        if (buf)
1343                free(buf);
1344        return events;
1345error:
1346        if (events)
1347                free_event_desc(events);
1348        events = NULL;
1349        goto out;
1350}
1351
1352static void print_event_desc(struct perf_header *ph, int fd, FILE *fp)
1353{
1354        struct perf_evsel *evsel, *events = read_event_desc(ph, fd);
1355        u32 j;
1356        u64 *id;
1357
1358        if (!events) {
1359                fprintf(fp, "# event desc: not available or unable to read\n");
1360                return;
1361        }
1362
1363        for (evsel = events; evsel->attr.size; evsel++) {
1364                fprintf(fp, "# event : name = %s, ", evsel->name);
1365
1366                fprintf(fp, "type = %d, config = 0x%"PRIx64
1367                            ", config1 = 0x%"PRIx64", config2 = 0x%"PRIx64,
1368                                evsel->attr.type,
1369                                (u64)evsel->attr.config,
1370                                (u64)evsel->attr.config1,
1371                                (u64)evsel->attr.config2);
1372
1373                fprintf(fp, ", excl_usr = %d, excl_kern = %d",
1374                                evsel->attr.exclude_user,
1375                                evsel->attr.exclude_kernel);
1376
1377                fprintf(fp, ", excl_host = %d, excl_guest = %d",
1378                                evsel->attr.exclude_host,
1379                                evsel->attr.exclude_guest);
1380
1381                fprintf(fp, ", precise_ip = %d", evsel->attr.precise_ip);
1382
1383                if (evsel->ids) {
1384                        fprintf(fp, ", id = {");
1385                        for (j = 0, id = evsel->id; j < evsel->ids; j++, id++) {
1386                                if (j)
1387                                        fputc(',', fp);
1388                                fprintf(fp, " %"PRIu64, *id);
1389                        }
1390                        fprintf(fp, " }");
1391                }
1392
1393                fputc('\n', fp);
1394        }
1395
1396        free_event_desc(events);
1397}
1398
1399static void print_total_mem(struct perf_header *ph, int fd __maybe_unused,
1400                            FILE *fp)
1401{
1402        fprintf(fp, "# total memory : %Lu kB\n", ph->env.total_mem);
1403}
1404
1405static void print_numa_topology(struct perf_header *ph, int fd __maybe_unused,
1406                                FILE *fp)
1407{
1408        u32 nr, c, i;
1409        char *str, *tmp;
1410        uint64_t mem_total, mem_free;
1411
1412        /* nr nodes */
1413        nr = ph->env.nr_numa_nodes;
1414        str = ph->env.numa_nodes;
1415
1416        for (i = 0; i < nr; i++) {
1417                /* node number */
1418                c = strtoul(str, &tmp, 0);
1419                if (*tmp != ':')
1420                        goto error;
1421
1422                str = tmp + 1;
1423                mem_total = strtoull(str, &tmp, 0);
1424                if (*tmp != ':')
1425                        goto error;
1426
1427                str = tmp + 1;
1428                mem_free = strtoull(str, &tmp, 0);
1429                if (*tmp != ':')
1430                        goto error;
1431
1432                fprintf(fp, "# node%u meminfo  : total = %"PRIu64" kB,"
1433                            " free = %"PRIu64" kB\n",
1434                        c, mem_total, mem_free);
1435
1436                str = tmp + 1;
1437                fprintf(fp, "# node%u cpu list : %s\n", c, str);
1438
1439                str += strlen(str) + 1;
1440        }
1441        return;
1442error:
1443        fprintf(fp, "# numa topology : not available\n");
1444}
1445
1446static void print_cpuid(struct perf_header *ph, int fd __maybe_unused, FILE *fp)
1447{
1448        fprintf(fp, "# cpuid : %s\n", ph->env.cpuid);
1449}
1450
1451static void print_branch_stack(struct perf_header *ph __maybe_unused,
1452                               int fd __maybe_unused, FILE *fp)
1453{
1454        fprintf(fp, "# contains samples with branch stack\n");
1455}
1456
1457static void print_pmu_mappings(struct perf_header *ph, int fd __maybe_unused,
1458                               FILE *fp)
1459{
1460        const char *delimiter = "# pmu mappings: ";
1461        char *str, *tmp;
1462        u32 pmu_num;
1463        u32 type;
1464
1465        pmu_num = ph->env.nr_pmu_mappings;
1466        if (!pmu_num) {
1467                fprintf(fp, "# pmu mappings: not available\n");
1468                return;
1469        }
1470
1471        str = ph->env.pmu_mappings;
1472
1473        while (pmu_num) {
1474                type = strtoul(str, &tmp, 0);
1475                if (*tmp != ':')
1476                        goto error;
1477
1478                str = tmp + 1;
1479                fprintf(fp, "%s%s = %" PRIu32, delimiter, str, type);
1480
1481                delimiter = ", ";
1482                str += strlen(str) + 1;
1483                pmu_num--;
1484        }
1485
1486        fprintf(fp, "\n");
1487
1488        if (!pmu_num)
1489                return;
1490error:
1491        fprintf(fp, "# pmu mappings: unable to read\n");
1492}
1493
1494static void print_group_desc(struct perf_header *ph, int fd __maybe_unused,
1495                             FILE *fp)
1496{
1497        struct perf_session *session;
1498        struct perf_evsel *evsel;
1499        u32 nr = 0;
1500
1501        session = container_of(ph, struct perf_session, header);
1502
1503        list_for_each_entry(evsel, &session->evlist->entries, node) {
1504                if (perf_evsel__is_group_leader(evsel) &&
1505                    evsel->nr_members > 1) {
1506                        fprintf(fp, "# group: %s{%s", evsel->group_name ?: "",
1507                                perf_evsel__name(evsel));
1508
1509                        nr = evsel->nr_members - 1;
1510                } else if (nr) {
1511                        fprintf(fp, ",%s", perf_evsel__name(evsel));
1512
1513                        if (--nr == 0)
1514                                fprintf(fp, "}\n");
1515                }
1516        }
1517}
1518
1519static int __event_process_build_id(struct build_id_event *bev,
1520                                    char *filename,
1521                                    struct perf_session *session)
1522{
1523        int err = -1;
1524        struct list_head *head;
1525        struct machine *machine;
1526        u16 misc;
1527        struct dso *dso;
1528        enum dso_kernel_type dso_type;
1529
1530        machine = perf_session__findnew_machine(session, bev->pid);
1531        if (!machine)
1532                goto out;
1533
1534        misc = bev->header.misc & PERF_RECORD_MISC_CPUMODE_MASK;
1535
1536        switch (misc) {
1537        case PERF_RECORD_MISC_KERNEL:
1538                dso_type = DSO_TYPE_KERNEL;
1539                head = &machine->kernel_dsos;
1540                break;
1541        case PERF_RECORD_MISC_GUEST_KERNEL:
1542                dso_type = DSO_TYPE_GUEST_KERNEL;
1543                head = &machine->kernel_dsos;
1544                break;
1545        case PERF_RECORD_MISC_USER:
1546        case PERF_RECORD_MISC_GUEST_USER:
1547                dso_type = DSO_TYPE_USER;
1548                head = &machine->user_dsos;
1549                break;
1550        default:
1551                goto out;
1552        }
1553
1554        dso = __dsos__findnew(head, filename);
1555        if (dso != NULL) {
1556                char sbuild_id[BUILD_ID_SIZE * 2 + 1];
1557
1558                dso__set_build_id(dso, &bev->build_id);
1559
1560                if (filename[0] == '[')
1561                        dso->kernel = dso_type;
1562
1563                build_id__sprintf(dso->build_id, sizeof(dso->build_id),
1564                                  sbuild_id);
1565                pr_debug("build id event received for %s: %s\n",
1566                         dso->long_name, sbuild_id);
1567        }
1568
1569        err = 0;
1570out:
1571        return err;
1572}
1573
1574static int perf_header__read_build_ids_abi_quirk(struct perf_header *header,
1575                                                 int input, u64 offset, u64 size)
1576{
1577        struct perf_session *session = container_of(header, struct perf_session, header);
1578        struct {
1579                struct perf_event_header   header;
1580                u8                         build_id[PERF_ALIGN(BUILD_ID_SIZE, sizeof(u64))];
1581                char                       filename[0];
1582        } old_bev;
1583        struct build_id_event bev;
1584        char filename[PATH_MAX];
1585        u64 limit = offset + size;
1586
1587        while (offset < limit) {
1588                ssize_t len;
1589
1590                if (readn(input, &old_bev, sizeof(old_bev)) != sizeof(old_bev))
1591                        return -1;
1592
1593                if (header->needs_swap)
1594                        perf_event_header__bswap(&old_bev.header);
1595
1596                len = old_bev.header.size - sizeof(old_bev);
1597                if (readn(input, filename, len) != len)
1598                        return -1;
1599
1600                bev.header = old_bev.header;
1601
1602                /*
1603                 * As the pid is the missing value, we need to fill
1604                 * it properly. The header.misc value give us nice hint.
1605                 */
1606                bev.pid = HOST_KERNEL_ID;
1607                if (bev.header.misc == PERF_RECORD_MISC_GUEST_USER ||
1608                    bev.header.misc == PERF_RECORD_MISC_GUEST_KERNEL)
1609                        bev.pid = DEFAULT_GUEST_KERNEL_ID;
1610
1611                memcpy(bev.build_id, old_bev.build_id, sizeof(bev.build_id));
1612                __event_process_build_id(&bev, filename, session);
1613
1614                offset += bev.header.size;
1615        }
1616
1617        return 0;
1618}
1619
1620static int perf_header__read_build_ids(struct perf_header *header,
1621                                       int input, u64 offset, u64 size)
1622{
1623        struct perf_session *session = container_of(header, struct perf_session, header);
1624        struct build_id_event bev;
1625        char filename[PATH_MAX];
1626        u64 limit = offset + size, orig_offset = offset;
1627        int err = -1;
1628
1629        while (offset < limit) {
1630                ssize_t len;
1631
1632                if (readn(input, &bev, sizeof(bev)) != sizeof(bev))
1633                        goto out;
1634
1635                if (header->needs_swap)
1636                        perf_event_header__bswap(&bev.header);
1637
1638                len = bev.header.size - sizeof(bev);
1639                if (readn(input, filename, len) != len)
1640                        goto out;
1641                /*
1642                 * The a1645ce1 changeset:
1643                 *
1644                 * "perf: 'perf kvm' tool for monitoring guest performance from host"
1645                 *
1646                 * Added a field to struct build_id_event that broke the file
1647                 * format.
1648                 *
1649                 * Since the kernel build-id is the first entry, process the
1650                 * table using the old format if the well known
1651                 * '[kernel.kallsyms]' string for the kernel build-id has the
1652                 * first 4 characters chopped off (where the pid_t sits).
1653                 */
1654                if (memcmp(filename, "nel.kallsyms]", 13) == 0) {
1655                        if (lseek(input, orig_offset, SEEK_SET) == (off_t)-1)
1656                                return -1;
1657                        return perf_header__read_build_ids_abi_quirk(header, input, offset, size);
1658                }
1659
1660                __event_process_build_id(&bev, filename, session);
1661
1662                offset += bev.header.size;
1663        }
1664        err = 0;
1665out:
1666        return err;
1667}
1668
1669static int process_tracing_data(struct perf_file_section *section __maybe_unused,
1670                                struct perf_header *ph __maybe_unused,
1671                                int fd, void *data)
1672{
1673        ssize_t ret = trace_report(fd, data, false);
1674        return ret < 0 ? -1 : 0;
1675}
1676
1677static int process_build_id(struct perf_file_section *section,
1678                            struct perf_header *ph, int fd,
1679                            void *data __maybe_unused)
1680{
1681        if (perf_header__read_build_ids(ph, fd, section->offset, section->size))
1682                pr_debug("Failed to read buildids, continuing...\n");
1683        return 0;
1684}
1685
1686static int process_hostname(struct perf_file_section *section __maybe_unused,
1687                            struct perf_header *ph, int fd,
1688                            void *data __maybe_unused)
1689{
1690        ph->env.hostname = do_read_string(fd, ph);
1691        return ph->env.hostname ? 0 : -ENOMEM;
1692}
1693
1694static int process_osrelease(struct perf_file_section *section __maybe_unused,
1695                             struct perf_header *ph, int fd,
1696                             void *data __maybe_unused)
1697{
1698        ph->env.os_release = do_read_string(fd, ph);
1699        return ph->env.os_release ? 0 : -ENOMEM;
1700}
1701
1702static int process_version(struct perf_file_section *section __maybe_unused,
1703                           struct perf_header *ph, int fd,
1704                           void *data __maybe_unused)
1705{
1706        ph->env.version = do_read_string(fd, ph);
1707        return ph->env.version ? 0 : -ENOMEM;
1708}
1709
1710static int process_arch(struct perf_file_section *section __maybe_unused,
1711                        struct perf_header *ph, int fd,
1712                        void *data __maybe_unused)
1713{
1714        ph->env.arch = do_read_string(fd, ph);
1715        return ph->env.arch ? 0 : -ENOMEM;
1716}
1717
1718static int process_nrcpus(struct perf_file_section *section __maybe_unused,
1719                          struct perf_header *ph, int fd,
1720                          void *data __maybe_unused)
1721{
1722        size_t ret;
1723        u32 nr;
1724
1725        ret = readn(fd, &nr, sizeof(nr));
1726        if (ret != sizeof(nr))
1727                return -1;
1728
1729        if (ph->needs_swap)
1730                nr = bswap_32(nr);
1731
1732        ph->env.nr_cpus_online = nr;
1733
1734        ret = readn(fd, &nr, sizeof(nr));
1735        if (ret != sizeof(nr))
1736                return -1;
1737
1738        if (ph->needs_swap)
1739                nr = bswap_32(nr);
1740
1741        ph->env.nr_cpus_avail = nr;
1742        return 0;
1743}
1744
1745static int process_cpudesc(struct perf_file_section *section __maybe_unused,
1746                           struct perf_header *ph, int fd,
1747                           void *data __maybe_unused)
1748{
1749        ph->env.cpu_desc = do_read_string(fd, ph);
1750        return ph->env.cpu_desc ? 0 : -ENOMEM;
1751}
1752
1753static int process_cpuid(struct perf_file_section *section __maybe_unused,
1754                         struct perf_header *ph,  int fd,
1755                         void *data __maybe_unused)
1756{
1757        ph->env.cpuid = do_read_string(fd, ph);
1758        return ph->env.cpuid ? 0 : -ENOMEM;
1759}
1760
1761static int process_total_mem(struct perf_file_section *section __maybe_unused,
1762                             struct perf_header *ph, int fd,
1763                             void *data __maybe_unused)
1764{
1765        uint64_t mem;
1766        size_t ret;
1767
1768        ret = readn(fd, &mem, sizeof(mem));
1769        if (ret != sizeof(mem))
1770                return -1;
1771
1772        if (ph->needs_swap)
1773                mem = bswap_64(mem);
1774
1775        ph->env.total_mem = mem;
1776        return 0;
1777}
1778
1779static struct perf_evsel *
1780perf_evlist__find_by_index(struct perf_evlist *evlist, int idx)
1781{
1782        struct perf_evsel *evsel;
1783
1784        list_for_each_entry(evsel, &evlist->entries, node) {
1785                if (evsel->idx == idx)
1786                        return evsel;
1787        }
1788
1789        return NULL;
1790}
1791
1792static void
1793perf_evlist__set_event_name(struct perf_evlist *evlist,
1794                            struct perf_evsel *event)
1795{
1796        struct perf_evsel *evsel;
1797
1798        if (!event->name)
1799                return;
1800
1801        evsel = perf_evlist__find_by_index(evlist, event->idx);
1802        if (!evsel)
1803                return;
1804
1805        if (evsel->name)
1806                return;
1807
1808        evsel->name = strdup(event->name);
1809}
1810
1811static int
1812process_event_desc(struct perf_file_section *section __maybe_unused,
1813                   struct perf_header *header, int fd,
1814                   void *data __maybe_unused)
1815{
1816        struct perf_session *session;
1817        struct perf_evsel *evsel, *events = read_event_desc(header, fd);
1818
1819        if (!events)
1820                return 0;
1821
1822        session = container_of(header, struct perf_session, header);
1823        for (evsel = events; evsel->attr.size; evsel++)
1824                perf_evlist__set_event_name(session->evlist, evsel);
1825
1826        free_event_desc(events);
1827
1828        return 0;
1829}
1830
1831static int process_cmdline(struct perf_file_section *section __maybe_unused,
1832                           struct perf_header *ph, int fd,
1833                           void *data __maybe_unused)
1834{
1835        size_t ret;
1836        char *str;
1837        u32 nr, i;
1838        struct strbuf sb;
1839
1840        ret = readn(fd, &nr, sizeof(nr));
1841        if (ret != sizeof(nr))
1842                return -1;
1843
1844        if (ph->needs_swap)
1845                nr = bswap_32(nr);
1846
1847        ph->env.nr_cmdline = nr;
1848        strbuf_init(&sb, 128);
1849
1850        for (i = 0; i < nr; i++) {
1851                str = do_read_string(fd, ph);
1852                if (!str)
1853                        goto error;
1854
1855                /* include a NULL character at the end */
1856                strbuf_add(&sb, str, strlen(str) + 1);
1857                free(str);
1858        }
1859        ph->env.cmdline = strbuf_detach(&sb, NULL);
1860        return 0;
1861
1862error:
1863        strbuf_release(&sb);
1864        return -1;
1865}
1866
1867static int process_cpu_topology(struct perf_file_section *section __maybe_unused,
1868                                struct perf_header *ph, int fd,
1869                                void *data __maybe_unused)
1870{
1871        size_t ret;
1872        u32 nr, i;
1873        char *str;
1874        struct strbuf sb;
1875
1876        ret = readn(fd, &nr, sizeof(nr));
1877        if (ret != sizeof(nr))
1878                return -1;
1879
1880        if (ph->needs_swap)
1881                nr = bswap_32(nr);
1882
1883        ph->env.nr_sibling_cores = nr;
1884        strbuf_init(&sb, 128);
1885
1886        for (i = 0; i < nr; i++) {
1887                str = do_read_string(fd, ph);
1888                if (!str)
1889                        goto error;
1890
1891                /* include a NULL character at the end */
1892                strbuf_add(&sb, str, strlen(str) + 1);
1893                free(str);
1894        }
1895        ph->env.sibling_cores = strbuf_detach(&sb, NULL);
1896
1897        ret = readn(fd, &nr, sizeof(nr));
1898        if (ret != sizeof(nr))
1899                return -1;
1900
1901        if (ph->needs_swap)
1902                nr = bswap_32(nr);
1903
1904        ph->env.nr_sibling_threads = nr;
1905
1906        for (i = 0; i < nr; i++) {
1907                str = do_read_string(fd, ph);
1908                if (!str)
1909                        goto error;
1910
1911                /* include a NULL character at the end */
1912                strbuf_add(&sb, str, strlen(str) + 1);
1913                free(str);
1914        }
1915        ph->env.sibling_threads = strbuf_detach(&sb, NULL);
1916        return 0;
1917
1918error:
1919        strbuf_release(&sb);
1920        return -1;
1921}
1922
1923static int process_numa_topology(struct perf_file_section *section __maybe_unused,
1924                                 struct perf_header *ph, int fd,
1925                                 void *data __maybe_unused)
1926{
1927        size_t ret;
1928        u32 nr, node, i;
1929        char *str;
1930        uint64_t mem_total, mem_free;
1931        struct strbuf sb;
1932
1933        /* nr nodes */
1934        ret = readn(fd, &nr, sizeof(nr));
1935        if (ret != sizeof(nr))
1936                goto error;
1937
1938        if (ph->needs_swap)
1939                nr = bswap_32(nr);
1940
1941        ph->env.nr_numa_nodes = nr;
1942        strbuf_init(&sb, 256);
1943
1944        for (i = 0; i < nr; i++) {
1945                /* node number */
1946                ret = readn(fd, &node, sizeof(node));
1947                if (ret != sizeof(node))
1948                        goto error;
1949
1950                ret = readn(fd, &mem_total, sizeof(u64));
1951                if (ret != sizeof(u64))
1952                        goto error;
1953
1954                ret = readn(fd, &mem_free, sizeof(u64));
1955                if (ret != sizeof(u64))
1956                        goto error;
1957
1958                if (ph->needs_swap) {
1959                        node = bswap_32(node);
1960                        mem_total = bswap_64(mem_total);
1961                        mem_free = bswap_64(mem_free);
1962                }
1963
1964                strbuf_addf(&sb, "%u:%"PRIu64":%"PRIu64":",
1965                            node, mem_total, mem_free);
1966
1967                str = do_read_string(fd, ph);
1968                if (!str)
1969                        goto error;
1970
1971                /* include a NULL character at the end */
1972                strbuf_add(&sb, str, strlen(str) + 1);
1973                free(str);
1974        }
1975        ph->env.numa_nodes = strbuf_detach(&sb, NULL);
1976        return 0;
1977
1978error:
1979        strbuf_release(&sb);
1980        return -1;
1981}
1982
1983static int process_pmu_mappings(struct perf_file_section *section __maybe_unused,
1984                                struct perf_header *ph, int fd,
1985                                void *data __maybe_unused)
1986{
1987        size_t ret;
1988        char *name;
1989        u32 pmu_num;
1990        u32 type;
1991        struct strbuf sb;
1992
1993        ret = readn(fd, &pmu_num, sizeof(pmu_num));
1994        if (ret != sizeof(pmu_num))
1995                return -1;
1996
1997        if (ph->needs_swap)
1998                pmu_num = bswap_32(pmu_num);
1999
2000        if (!pmu_num) {
2001                pr_debug("pmu mappings not available\n");
2002                return 0;
2003        }
2004
2005        ph->env.nr_pmu_mappings = pmu_num;
2006        strbuf_init(&sb, 128);
2007
2008        while (pmu_num) {
2009                if (readn(fd, &type, sizeof(type)) != sizeof(type))
2010                        goto error;
2011                if (ph->needs_swap)
2012                        type = bswap_32(type);
2013
2014                name = do_read_string(fd, ph);
2015                if (!name)
2016                        goto error;
2017
2018                strbuf_addf(&sb, "%u:%s", type, name);
2019                /* include a NULL character at the end */
2020                strbuf_add(&sb, "", 1);
2021
2022                free(name);
2023                pmu_num--;
2024        }
2025        ph->env.pmu_mappings = strbuf_detach(&sb, NULL);
2026        return 0;
2027
2028error:
2029        strbuf_release(&sb);
2030        return -1;
2031}
2032
2033static int process_group_desc(struct perf_file_section *section __maybe_unused,
2034                              struct perf_header *ph, int fd,
2035                              void *data __maybe_unused)
2036{
2037        size_t ret = -1;
2038        u32 i, nr, nr_groups;
2039        struct perf_session *session;
2040        struct perf_evsel *evsel, *leader = NULL;
2041        struct group_desc {
2042                char *name;
2043                u32 leader_idx;
2044                u32 nr_members;
2045        } *desc;
2046
2047        if (readn(fd, &nr_groups, sizeof(nr_groups)) != sizeof(nr_groups))
2048                return -1;
2049
2050        if (ph->needs_swap)
2051                nr_groups = bswap_32(nr_groups);
2052
2053        ph->env.nr_groups = nr_groups;
2054        if (!nr_groups) {
2055                pr_debug("group desc not available\n");
2056                return 0;
2057        }
2058
2059        desc = calloc(nr_groups, sizeof(*desc));
2060        if (!desc)
2061                return -1;
2062
2063        for (i = 0; i < nr_groups; i++) {
2064                desc[i].name = do_read_string(fd, ph);
2065                if (!desc[i].name)
2066                        goto out_free;
2067
2068                if (readn(fd, &desc[i].leader_idx, sizeof(u32)) != sizeof(u32))
2069                        goto out_free;
2070
2071                if (readn(fd, &desc[i].nr_members, sizeof(u32)) != sizeof(u32))
2072                        goto out_free;
2073
2074                if (ph->needs_swap) {
2075                        desc[i].leader_idx = bswap_32(desc[i].leader_idx);
2076                        desc[i].nr_members = bswap_32(desc[i].nr_members);
2077                }
2078        }
2079
2080        /*
2081         * Rebuild group relationship based on the group_desc
2082         */
2083        session = container_of(ph, struct perf_session, header);
2084        session->evlist->nr_groups = nr_groups;
2085
2086        i = nr = 0;
2087        list_for_each_entry(evsel, &session->evlist->entries, node) {
2088                if (evsel->idx == (int) desc[i].leader_idx) {
2089                        evsel->leader = evsel;
2090                        /* {anon_group} is a dummy name */
2091                        if (strcmp(desc[i].name, "{anon_group}"))
2092                                evsel->group_name = desc[i].name;
2093                        evsel->nr_members = desc[i].nr_members;
2094
2095                        if (i >= nr_groups || nr > 0) {
2096                                pr_debug("invalid group desc\n");
2097                                goto out_free;
2098                        }
2099
2100                        leader = evsel;
2101                        nr = evsel->nr_members - 1;
2102                        i++;
2103                } else if (nr) {
2104                        /* This is a group member */
2105                        evsel->leader = leader;
2106
2107                        nr--;
2108                }
2109        }
2110
2111        if (i != nr_groups || nr != 0) {
2112                pr_debug("invalid group desc\n");
2113                goto out_free;
2114        }
2115
2116        ret = 0;
2117out_free:
2118        while ((int) --i >= 0)
2119                free(desc[i].name);
2120        free(desc);
2121
2122        return ret;
2123}
2124
2125struct feature_ops {
2126        int (*write)(int fd, struct perf_header *h, struct perf_evlist *evlist);
2127        void (*print)(struct perf_header *h, int fd, FILE *fp);
2128        int (*process)(struct perf_file_section *section,
2129                       struct perf_header *h, int fd, void *data);
2130        const char *name;
2131        bool full_only;
2132};
2133
2134#define FEAT_OPA(n, func) \
2135        [n] = { .name = #n, .write = write_##func, .print = print_##func }
2136#define FEAT_OPP(n, func) \
2137        [n] = { .name = #n, .write = write_##func, .print = print_##func, \
2138                .process = process_##func }
2139#define FEAT_OPF(n, func) \
2140        [n] = { .name = #n, .write = write_##func, .print = print_##func, \
2141                .process = process_##func, .full_only = true }
2142
2143/* feature_ops not implemented: */
2144#define print_tracing_data      NULL
2145#define print_build_id          NULL
2146
2147static const struct feature_ops feat_ops[HEADER_LAST_FEATURE] = {
2148        FEAT_OPP(HEADER_TRACING_DATA,   tracing_data),
2149        FEAT_OPP(HEADER_BUILD_ID,       build_id),
2150        FEAT_OPP(HEADER_HOSTNAME,       hostname),
2151        FEAT_OPP(HEADER_OSRELEASE,      osrelease),
2152        FEAT_OPP(HEADER_VERSION,        version),
2153        FEAT_OPP(HEADER_ARCH,           arch),
2154        FEAT_OPP(HEADER_NRCPUS,         nrcpus),
2155        FEAT_OPP(HEADER_CPUDESC,        cpudesc),
2156        FEAT_OPP(HEADER_CPUID,          cpuid),
2157        FEAT_OPP(HEADER_TOTAL_MEM,      total_mem),
2158        FEAT_OPP(HEADER_EVENT_DESC,     event_desc),
2159        FEAT_OPP(HEADER_CMDLINE,        cmdline),
2160        FEAT_OPF(HEADER_CPU_TOPOLOGY,   cpu_topology),
2161        FEAT_OPF(HEADER_NUMA_TOPOLOGY,  numa_topology),
2162        FEAT_OPA(HEADER_BRANCH_STACK,   branch_stack),
2163        FEAT_OPP(HEADER_PMU_MAPPINGS,   pmu_mappings),
2164        FEAT_OPP(HEADER_GROUP_DESC,     group_desc),
2165};
2166
2167struct header_print_data {
2168        FILE *fp;
2169        bool full; /* extended list of headers */
2170};
2171
2172static int perf_file_section__fprintf_info(struct perf_file_section *section,
2173                                           struct perf_header *ph,
2174                                           int feat, int fd, void *data)
2175{
2176        struct header_print_data *hd = data;
2177
2178        if (lseek(fd, section->offset, SEEK_SET) == (off_t)-1) {
2179                pr_debug("Failed to lseek to %" PRIu64 " offset for feature "
2180                                "%d, continuing...\n", section->offset, feat);
2181                return 0;
2182        }
2183        if (feat >= HEADER_LAST_FEATURE) {
2184                pr_warning("unknown feature %d\n", feat);
2185                return 0;
2186        }
2187        if (!feat_ops[feat].print)
2188                return 0;
2189
2190        if (!feat_ops[feat].full_only || hd->full)
2191                feat_ops[feat].print(ph, fd, hd->fp);
2192        else
2193                fprintf(hd->fp, "# %s info available, use -I to display\n",
2194                        feat_ops[feat].name);
2195
2196        return 0;
2197}
2198
2199int perf_header__fprintf_info(struct perf_session *session, FILE *fp, bool full)
2200{
2201        struct header_print_data hd;
2202        struct perf_header *header = &session->header;
2203        int fd = session->fd;
2204        hd.fp = fp;
2205        hd.full = full;
2206
2207        perf_header__process_sections(header, fd, &hd,
2208                                      perf_file_section__fprintf_info);
2209        return 0;
2210}
2211
2212static int do_write_feat(int fd, struct perf_header *h, int type,
2213                         struct perf_file_section **p,
2214                         struct perf_evlist *evlist)
2215{
2216        int err;
2217        int ret = 0;
2218
2219        if (perf_header__has_feat(h, type)) {
2220                if (!feat_ops[type].write)
2221                        return -1;
2222
2223                (*p)->offset = lseek(fd, 0, SEEK_CUR);
2224
2225                err = feat_ops[type].write(fd, h, evlist);
2226                if (err < 0) {
2227                        pr_debug("failed to write feature %d\n", type);
2228
2229                        /* undo anything written */
2230                        lseek(fd, (*p)->offset, SEEK_SET);
2231
2232                        return -1;
2233                }
2234                (*p)->size = lseek(fd, 0, SEEK_CUR) - (*p)->offset;
2235                (*p)++;
2236        }
2237        return ret;
2238}
2239
2240static int perf_header__adds_write(struct perf_header *header,
2241                                   struct perf_evlist *evlist, int fd)
2242{
2243        int nr_sections;
2244        struct perf_file_section *feat_sec, *p;
2245        int sec_size;
2246        u64 sec_start;
2247        int feat;
2248        int err;
2249
2250        nr_sections = bitmap_weight(header->adds_features, HEADER_FEAT_BITS);
2251        if (!nr_sections)
2252                return 0;
2253
2254        feat_sec = p = calloc(nr_sections, sizeof(*feat_sec));
2255        if (feat_sec == NULL)
2256                return -ENOMEM;
2257
2258        sec_size = sizeof(*feat_sec) * nr_sections;
2259
2260        sec_start = header->data_offset + header->data_size;
2261        lseek(fd, sec_start + sec_size, SEEK_SET);
2262
2263        for_each_set_bit(feat, header->adds_features, HEADER_FEAT_BITS) {
2264                if (do_write_feat(fd, header, feat, &p, evlist))
2265                        perf_header__clear_feat(header, feat);
2266        }
2267
2268        lseek(fd, sec_start, SEEK_SET);
2269        /*
2270         * may write more than needed due to dropped feature, but
2271         * this is okay, reader will skip the mising entries
2272         */
2273        err = do_write(fd, feat_sec, sec_size);
2274        if (err < 0)
2275                pr_debug("failed to write feature section\n");
2276        free(feat_sec);
2277        return err;
2278}
2279
2280int perf_header__write_pipe(int fd)
2281{
2282        struct perf_pipe_file_header f_header;
2283        int err;
2284
2285        f_header = (struct perf_pipe_file_header){
2286                .magic     = PERF_MAGIC,
2287                .size      = sizeof(f_header),
2288        };
2289
2290        err = do_write(fd, &f_header, sizeof(f_header));
2291        if (err < 0) {
2292                pr_debug("failed to write perf pipe header\n");
2293                return err;
2294        }
2295
2296        return 0;
2297}
2298
2299int perf_session__write_header(struct perf_session *session,
2300                               struct perf_evlist *evlist,
2301                               int fd, bool at_exit)
2302{
2303        struct perf_file_header f_header;
2304        struct perf_file_attr   f_attr;
2305        struct perf_header *header = &session->header;
2306        struct perf_evsel *evsel;
2307        int err;
2308
2309        lseek(fd, sizeof(f_header), SEEK_SET);
2310
2311        list_for_each_entry(evsel, &evlist->entries, node) {
2312                evsel->id_offset = lseek(fd, 0, SEEK_CUR);
2313                err = do_write(fd, evsel->id, evsel->ids * sizeof(u64));
2314                if (err < 0) {
2315                        pr_debug("failed to write perf header\n");
2316                        return err;
2317                }
2318        }
2319
2320        header->attr_offset = lseek(fd, 0, SEEK_CUR);
2321
2322        list_for_each_entry(evsel, &evlist->entries, node) {
2323                f_attr = (struct perf_file_attr){
2324                        .attr = evsel->attr,
2325                        .ids  = {
2326                                .offset = evsel->id_offset,
2327                                .size   = evsel->ids * sizeof(u64),
2328                        }
2329                };
2330                err = do_write(fd, &f_attr, sizeof(f_attr));
2331                if (err < 0) {
2332                        pr_debug("failed to write perf header attribute\n");
2333                        return err;
2334                }
2335        }
2336
2337        header->event_offset = lseek(fd, 0, SEEK_CUR);
2338        header->event_size = trace_event_count * sizeof(struct perf_trace_event_type);
2339        if (trace_events) {
2340                err = do_write(fd, trace_events, header->event_size);
2341                if (err < 0) {
2342                        pr_debug("failed to write perf header events\n");
2343                        return err;
2344                }
2345        }
2346
2347        header->data_offset = lseek(fd, 0, SEEK_CUR);
2348
2349        if (at_exit) {
2350                err = perf_header__adds_write(header, evlist, fd);
2351                if (err < 0)
2352                        return err;
2353        }
2354
2355        f_header = (struct perf_file_header){
2356                .magic     = PERF_MAGIC,
2357                .size      = sizeof(f_header),
2358                .attr_size = sizeof(f_attr),
2359                .attrs = {
2360                        .offset = header->attr_offset,
2361                        .size   = evlist->nr_entries * sizeof(f_attr),
2362                },
2363                .data = {
2364                        .offset = header->data_offset,
2365                        .size   = header->data_size,
2366                },
2367                .event_types = {
2368                        .offset = header->event_offset,
2369                        .size   = header->event_size,
2370                },
2371        };
2372
2373        memcpy(&f_header.adds_features, &header->adds_features, sizeof(header->adds_features));
2374
2375        lseek(fd, 0, SEEK_SET);
2376        err = do_write(fd, &f_header, sizeof(f_header));
2377        if (err < 0) {
2378                pr_debug("failed to write perf header\n");
2379                return err;
2380        }
2381        lseek(fd, header->data_offset + header->data_size, SEEK_SET);
2382
2383        return 0;
2384}
2385
2386static int perf_header__getbuffer64(struct perf_header *header,
2387                                    int fd, void *buf, size_t size)
2388{
2389        if (readn(fd, buf, size) <= 0)
2390                return -1;
2391
2392        if (header->needs_swap)
2393                mem_bswap_64(buf, size);
2394
2395        return 0;
2396}
2397
2398int perf_header__process_sections(struct perf_header *header, int fd,
2399                                  void *data,
2400                                  int (*process)(struct perf_file_section *section,
2401                                                 struct perf_header *ph,
2402                                                 int feat, int fd, void *data))
2403{
2404        struct perf_file_section *feat_sec, *sec;
2405        int nr_sections;
2406        int sec_size;
2407        int feat;
2408        int err;
2409
2410        nr_sections = bitmap_weight(header->adds_features, HEADER_FEAT_BITS);
2411        if (!nr_sections)
2412                return 0;
2413
2414        feat_sec = sec = calloc(nr_sections, sizeof(*feat_sec));
2415        if (!feat_sec)
2416                return -1;
2417
2418        sec_size = sizeof(*feat_sec) * nr_sections;
2419
2420        lseek(fd, header->data_offset + header->data_size, SEEK_SET);
2421
2422        err = perf_header__getbuffer64(header, fd, feat_sec, sec_size);
2423        if (err < 0)
2424                goto out_free;
2425
2426        for_each_set_bit(feat, header->adds_features, HEADER_LAST_FEATURE) {
2427                err = process(sec++, header, feat, fd, data);
2428                if (err < 0)
2429                        goto out_free;
2430        }
2431        err = 0;
2432out_free:
2433        free(feat_sec);
2434        return err;
2435}
2436
2437static const int attr_file_abi_sizes[] = {
2438        [0] = PERF_ATTR_SIZE_VER0,
2439        [1] = PERF_ATTR_SIZE_VER1,
2440        [2] = PERF_ATTR_SIZE_VER2,
2441        [3] = PERF_ATTR_SIZE_VER3,
2442        0,
2443};
2444
2445/*
2446 * In the legacy file format, the magic number is not used to encode endianness.
2447 * hdr_sz was used to encode endianness. But given that hdr_sz can vary based
2448 * on ABI revisions, we need to try all combinations for all endianness to
2449 * detect the endianness.
2450 */
2451static int try_all_file_abis(uint64_t hdr_sz, struct perf_header *ph)
2452{
2453        uint64_t ref_size, attr_size;
2454        int i;
2455
2456        for (i = 0 ; attr_file_abi_sizes[i]; i++) {
2457                ref_size = attr_file_abi_sizes[i]
2458                         + sizeof(struct perf_file_section);
2459                if (hdr_sz != ref_size) {
2460                        attr_size = bswap_64(hdr_sz);
2461                        if (attr_size != ref_size)
2462                                continue;
2463
2464                        ph->needs_swap = true;
2465                }
2466                pr_debug("ABI%d perf.data file detected, need_swap=%d\n",
2467                         i,
2468                         ph->needs_swap);
2469                return 0;
2470        }
2471        /* could not determine endianness */
2472        return -1;
2473}
2474
2475#define PERF_PIPE_HDR_VER0      16
2476
2477static const size_t attr_pipe_abi_sizes[] = {
2478        [0] = PERF_PIPE_HDR_VER0,
2479        0,
2480};
2481
2482/*
2483 * In the legacy pipe format, there is an implicit assumption that endiannesss
2484 * between host recording the samples, and host parsing the samples is the
2485 * same. This is not always the case given that the pipe output may always be
2486 * redirected into a file and analyzed on a different machine with possibly a
2487 * different endianness and perf_event ABI revsions in the perf tool itself.
2488 */
2489static int try_all_pipe_abis(uint64_t hdr_sz, struct perf_header *ph)
2490{
2491        u64 attr_size;
2492        int i;
2493
2494        for (i = 0 ; attr_pipe_abi_sizes[i]; i++) {
2495                if (hdr_sz != attr_pipe_abi_sizes[i]) {
2496                        attr_size = bswap_64(hdr_sz);
2497                        if (attr_size != hdr_sz)
2498                                continue;
2499
2500                        ph->needs_swap = true;
2501                }
2502                pr_debug("Pipe ABI%d perf.data file detected\n", i);
2503                return 0;
2504        }
2505        return -1;
2506}
2507
2508bool is_perf_magic(u64 magic)
2509{
2510        if (!memcmp(&magic, __perf_magic1, sizeof(magic))
2511                || magic == __perf_magic2
2512                || magic == __perf_magic2_sw)
2513                return true;
2514
2515        return false;
2516}
2517
2518static int check_magic_endian(u64 magic, uint64_t hdr_sz,
2519                              bool is_pipe, struct perf_header *ph)
2520{
2521        int ret;
2522
2523        /* check for legacy format */
2524        ret = memcmp(&magic, __perf_magic1, sizeof(magic));
2525        if (ret == 0) {
2526                pr_debug("legacy perf.data format\n");
2527                if (is_pipe)
2528                        return try_all_pipe_abis(hdr_sz, ph);
2529
2530                return try_all_file_abis(hdr_sz, ph);
2531        }
2532        /*
2533         * the new magic number serves two purposes:
2534         * - unique number to identify actual perf.data files
2535         * - encode endianness of file
2536         */
2537
2538        /* check magic number with one endianness */
2539        if (magic == __perf_magic2)
2540                return 0;
2541
2542        /* check magic number with opposite endianness */
2543        if (magic != __perf_magic2_sw)
2544                return -1;
2545
2546        ph->needs_swap = true;
2547
2548        return 0;
2549}
2550
2551int perf_file_header__read(struct perf_file_header *header,
2552                           struct perf_header *ph, int fd)
2553{
2554        int ret;
2555
2556        lseek(fd, 0, SEEK_SET);
2557
2558        ret = readn(fd, header, sizeof(*header));
2559        if (ret <= 0)
2560                return -1;
2561
2562        if (check_magic_endian(header->magic,
2563                               header->attr_size, false, ph) < 0) {
2564                pr_debug("magic/endian check failed\n");
2565                return -1;
2566        }
2567
2568        if (ph->needs_swap) {
2569                mem_bswap_64(header, offsetof(struct perf_file_header,
2570                             adds_features));
2571        }
2572
2573        if (header->size != sizeof(*header)) {
2574                /* Support the previous format */
2575                if (header->size == offsetof(typeof(*header), adds_features))
2576                        bitmap_zero(header->adds_features, HEADER_FEAT_BITS);
2577                else
2578                        return -1;
2579        } else if (ph->needs_swap) {
2580                /*
2581                 * feature bitmap is declared as an array of unsigned longs --
2582                 * not good since its size can differ between the host that
2583                 * generated the data file and the host analyzing the file.
2584                 *
2585                 * We need to handle endianness, but we don't know the size of
2586                 * the unsigned long where the file was generated. Take a best
2587                 * guess at determining it: try 64-bit swap first (ie., file
2588                 * created on a 64-bit host), and check if the hostname feature
2589                 * bit is set (this feature bit is forced on as of fbe96f2).
2590                 * If the bit is not, undo the 64-bit swap and try a 32-bit
2591                 * swap. If the hostname bit is still not set (e.g., older data
2592                 * file), punt and fallback to the original behavior --
2593                 * clearing all feature bits and setting buildid.
2594                 */
2595                mem_bswap_64(&header->adds_features,
2596                            BITS_TO_U64(HEADER_FEAT_BITS));
2597
2598                if (!test_bit(HEADER_HOSTNAME, header->adds_features)) {
2599                        /* unswap as u64 */
2600                        mem_bswap_64(&header->adds_features,
2601                                    BITS_TO_U64(HEADER_FEAT_BITS));
2602
2603                        /* unswap as u32 */
2604                        mem_bswap_32(&header->adds_features,
2605                                    BITS_TO_U32(HEADER_FEAT_BITS));
2606                }
2607
2608                if (!test_bit(HEADER_HOSTNAME, header->adds_features)) {
2609                        bitmap_zero(header->adds_features, HEADER_FEAT_BITS);
2610                        set_bit(HEADER_BUILD_ID, header->adds_features);
2611                }
2612        }
2613
2614        memcpy(&ph->adds_features, &header->adds_features,
2615               sizeof(ph->adds_features));
2616
2617        ph->event_offset = header->event_types.offset;
2618        ph->event_size   = header->event_types.size;
2619        ph->data_offset  = header->data.offset;
2620        ph->data_size    = header->data.size;
2621        return 0;
2622}
2623
2624static int perf_file_section__process(struct perf_file_section *section,
2625                                      struct perf_header *ph,
2626                                      int feat, int fd, void *data)
2627{
2628        if (lseek(fd, section->offset, SEEK_SET) == (off_t)-1) {
2629                pr_debug("Failed to lseek to %" PRIu64 " offset for feature "
2630                          "%d, continuing...\n", section->offset, feat);
2631                return 0;
2632        }
2633
2634        if (feat >= HEADER_LAST_FEATURE) {
2635                pr_debug("unknown feature %d, continuing...\n", feat);
2636                return 0;
2637        }
2638
2639        if (!feat_ops[feat].process)
2640                return 0;
2641
2642        return feat_ops[feat].process(section, ph, fd, data);
2643}
2644
2645static int perf_file_header__read_pipe(struct perf_pipe_file_header *header,
2646                                       struct perf_header *ph, int fd,
2647                                       bool repipe)
2648{
2649        int ret;
2650
2651        ret = readn(fd, header, sizeof(*header));
2652        if (ret <= 0)
2653                return -1;
2654
2655        if (check_magic_endian(header->magic, header->size, true, ph) < 0) {
2656                pr_debug("endian/magic failed\n");
2657                return -1;
2658        }
2659
2660        if (ph->needs_swap)
2661                header->size = bswap_64(header->size);
2662
2663        if (repipe && do_write(STDOUT_FILENO, header, sizeof(*header)) < 0)
2664                return -1;
2665
2666        return 0;
2667}
2668
2669static int perf_header__read_pipe(struct perf_session *session, int fd)
2670{
2671        struct perf_header *header = &session->header;
2672        struct perf_pipe_file_header f_header;
2673
2674        if (perf_file_header__read_pipe(&f_header, header, fd,
2675                                        session->repipe) < 0) {
2676                pr_debug("incompatible file format\n");
2677                return -EINVAL;
2678        }
2679
2680        session->fd = fd;
2681
2682        return 0;
2683}
2684
2685static int read_attr(int fd, struct perf_header *ph,
2686                     struct perf_file_attr *f_attr)
2687{
2688        struct perf_event_attr *attr = &f_attr->attr;
2689        size_t sz, left;
2690        size_t our_sz = sizeof(f_attr->attr);
2691        int ret;
2692
2693        memset(f_attr, 0, sizeof(*f_attr));
2694
2695        /* read minimal guaranteed structure */
2696        ret = readn(fd, attr, PERF_ATTR_SIZE_VER0);
2697        if (ret <= 0) {
2698                pr_debug("cannot read %d bytes of header attr\n",
2699                         PERF_ATTR_SIZE_VER0);
2700                return -1;
2701        }
2702
2703        /* on file perf_event_attr size */
2704        sz = attr->size;
2705
2706        if (ph->needs_swap)
2707                sz = bswap_32(sz);
2708
2709        if (sz == 0) {
2710                /* assume ABI0 */
2711                sz =  PERF_ATTR_SIZE_VER0;
2712        } else if (sz > our_sz) {
2713                pr_debug("file uses a more recent and unsupported ABI"
2714                         " (%zu bytes extra)\n", sz - our_sz);
2715                return -1;
2716        }
2717        /* what we have not yet read and that we know about */
2718        left = sz - PERF_ATTR_SIZE_VER0;
2719        if (left) {
2720                void *ptr = attr;
2721                ptr += PERF_ATTR_SIZE_VER0;
2722
2723                ret = readn(fd, ptr, left);
2724        }
2725        /* read perf_file_section, ids are read in caller */
2726        ret = readn(fd, &f_attr->ids, sizeof(f_attr->ids));
2727
2728        return ret <= 0 ? -1 : 0;
2729}
2730
2731static int perf_evsel__prepare_tracepoint_event(struct perf_evsel *evsel,
2732                                                struct pevent *pevent)
2733{
2734        struct event_format *event;
2735        char bf[128];
2736
2737        /* already prepared */
2738        if (evsel->tp_format)
2739                return 0;
2740
2741        if (pevent == NULL) {
2742                pr_debug("broken or missing trace data\n");
2743                return -1;
2744        }
2745
2746        event = pevent_find_event(pevent, evsel->attr.config);
2747        if (event == NULL)
2748                return -1;
2749
2750        if (!evsel->name) {
2751                snprintf(bf, sizeof(bf), "%s:%s", event->system, event->name);
2752                evsel->name = strdup(bf);
2753                if (evsel->name == NULL)
2754                        return -1;
2755        }
2756
2757        evsel->tp_format = event;
2758        return 0;
2759}
2760
2761static int perf_evlist__prepare_tracepoint_events(struct perf_evlist *evlist,
2762                                                  struct pevent *pevent)
2763{
2764        struct perf_evsel *pos;
2765
2766        list_for_each_entry(pos, &evlist->entries, node) {
2767                if (pos->attr.type == PERF_TYPE_TRACEPOINT &&
2768                    perf_evsel__prepare_tracepoint_event(pos, pevent))
2769                        return -1;
2770        }
2771
2772        return 0;
2773}
2774
2775int perf_session__read_header(struct perf_session *session, int fd)
2776{
2777        struct perf_header *header = &session->header;
2778        struct perf_file_header f_header;
2779        struct perf_file_attr   f_attr;
2780        u64                     f_id;
2781        int nr_attrs, nr_ids, i, j;
2782
2783        session->evlist = perf_evlist__new();
2784        if (session->evlist == NULL)
2785                return -ENOMEM;
2786
2787        if (session->fd_pipe)
2788                return perf_header__read_pipe(session, fd);
2789
2790        if (perf_file_header__read(&f_header, header, fd) < 0)
2791                return -EINVAL;
2792
2793        nr_attrs = f_header.attrs.size / f_header.attr_size;
2794        lseek(fd, f_header.attrs.offset, SEEK_SET);
2795
2796        for (i = 0; i < nr_attrs; i++) {
2797                struct perf_evsel *evsel;
2798                off_t tmp;
2799
2800                if (read_attr(fd, header, &f_attr) < 0)
2801                        goto out_errno;
2802
2803                if (header->needs_swap)
2804                        perf_event__attr_swap(&f_attr.attr);
2805
2806                tmp = lseek(fd, 0, SEEK_CUR);
2807                evsel = perf_evsel__new(&f_attr.attr, i);
2808
2809                if (evsel == NULL)
2810                        goto out_delete_evlist;
2811
2812                evsel->needs_swap = header->needs_swap;
2813                /*
2814                 * Do it before so that if perf_evsel__alloc_id fails, this
2815                 * entry gets purged too at perf_evlist__delete().
2816                 */
2817                perf_evlist__add(session->evlist, evsel);
2818
2819                nr_ids = f_attr.ids.size / sizeof(u64);
2820                /*
2821                 * We don't have the cpu and thread maps on the header, so
2822                 * for allocating the perf_sample_id table we fake 1 cpu and
2823                 * hattr->ids threads.
2824                 */
2825                if (perf_evsel__alloc_id(evsel, 1, nr_ids))
2826                        goto out_delete_evlist;
2827
2828                lseek(fd, f_attr.ids.offset, SEEK_SET);
2829
2830                for (j = 0; j < nr_ids; j++) {
2831                        if (perf_header__getbuffer64(header, fd, &f_id, sizeof(f_id)))
2832                                goto out_errno;
2833
2834                        perf_evlist__id_add(session->evlist, evsel, 0, j, f_id);
2835                }
2836
2837                lseek(fd, tmp, SEEK_SET);
2838        }
2839
2840        symbol_conf.nr_events = nr_attrs;
2841
2842        if (f_header.event_types.size) {
2843                lseek(fd, f_header.event_types.offset, SEEK_SET);
2844                trace_events = malloc(f_header.event_types.size);
2845                if (trace_events == NULL)
2846                        return -ENOMEM;
2847                if (perf_header__getbuffer64(header, fd, trace_events,
2848                                             f_header.event_types.size))
2849                        goto out_errno;
2850                trace_event_count =  f_header.event_types.size / sizeof(struct perf_trace_event_type);
2851        }
2852
2853        perf_header__process_sections(header, fd, &session->pevent,
2854                                      perf_file_section__process);
2855
2856        lseek(fd, header->data_offset, SEEK_SET);
2857
2858        if (perf_evlist__prepare_tracepoint_events(session->evlist,
2859                                                   session->pevent))
2860                goto out_delete_evlist;
2861
2862        return 0;
2863out_errno:
2864        return -errno;
2865
2866out_delete_evlist:
2867        perf_evlist__delete(session->evlist);
2868        session->evlist = NULL;
2869        return -ENOMEM;
2870}
2871
2872int perf_event__synthesize_attr(struct perf_tool *tool,
2873                                struct perf_event_attr *attr, u32 ids, u64 *id,
2874                                perf_event__handler_t process)
2875{
2876        union perf_event *ev;
2877        size_t size;
2878        int err;
2879
2880        size = sizeof(struct perf_event_attr);
2881        size = PERF_ALIGN(size, sizeof(u64));
2882        size += sizeof(struct perf_event_header);
2883        size += ids * sizeof(u64);
2884
2885        ev = malloc(size);
2886
2887        if (ev == NULL)
2888                return -ENOMEM;
2889
2890        ev->attr.attr = *attr;
2891        memcpy(ev->attr.id, id, ids * sizeof(u64));
2892
2893        ev->attr.header.type = PERF_RECORD_HEADER_ATTR;
2894        ev->attr.header.size = (u16)size;
2895
2896        if (ev->attr.header.size == size)
2897                err = process(tool, ev, NULL, NULL);
2898        else
2899                err = -E2BIG;
2900
2901        free(ev);
2902
2903        return err;
2904}
2905
2906int perf_event__synthesize_attrs(struct perf_tool *tool,
2907                                   struct perf_session *session,
2908                                   perf_event__handler_t process)
2909{
2910        struct perf_evsel *evsel;
2911        int err = 0;
2912
2913        list_for_each_entry(evsel, &session->evlist->entries, node) {
2914                err = perf_event__synthesize_attr(tool, &evsel->attr, evsel->ids,
2915                                                  evsel->id, process);
2916                if (err) {
2917                        pr_debug("failed to create perf header attribute\n");
2918                        return err;
2919                }
2920        }
2921
2922        return err;
2923}
2924
2925int perf_event__process_attr(union perf_event *event,
2926                             struct perf_evlist **pevlist)
2927{
2928        u32 i, ids, n_ids;
2929        struct perf_evsel *evsel;
2930        struct perf_evlist *evlist = *pevlist;
2931
2932        if (evlist == NULL) {
2933                *pevlist = evlist = perf_evlist__new();
2934                if (evlist == NULL)
2935                        return -ENOMEM;
2936        }
2937
2938        evsel = perf_evsel__new(&event->attr.attr, evlist->nr_entries);
2939        if (evsel == NULL)
2940                return -ENOMEM;
2941
2942        perf_evlist__add(evlist, evsel);
2943
2944        ids = event->header.size;
2945        ids -= (void *)&event->attr.id - (void *)event;
2946        n_ids = ids / sizeof(u64);
2947        /*
2948         * We don't have the cpu and thread maps on the header, so
2949         * for allocating the perf_sample_id table we fake 1 cpu and
2950         * hattr->ids threads.
2951         */
2952        if (perf_evsel__alloc_id(evsel, 1, n_ids))
2953                return -ENOMEM;
2954
2955        for (i = 0; i < n_ids; i++) {
2956                perf_evlist__id_add(evlist, evsel, 0, i, event->attr.id[i]);
2957        }
2958
2959        symbol_conf.nr_events = evlist->nr_entries;
2960
2961        return 0;
2962}
2963
2964int perf_event__synthesize_event_type(struct perf_tool *tool,
2965                                      u64 event_id, char *name,
2966                                      perf_event__handler_t process,
2967                                      struct machine *machine)
2968{
2969        union perf_event ev;
2970        size_t size = 0;
2971        int err = 0;
2972
2973        memset(&ev, 0, sizeof(ev));
2974
2975        ev.event_type.event_type.event_id = event_id;
2976        memset(ev.event_type.event_type.name, 0, MAX_EVENT_NAME);
2977        strncpy(ev.event_type.event_type.name, name, MAX_EVENT_NAME - 1);
2978
2979        ev.event_type.header.type = PERF_RECORD_HEADER_EVENT_TYPE;
2980        size = strlen(ev.event_type.event_type.name);
2981        size = PERF_ALIGN(size, sizeof(u64));
2982        ev.event_type.header.size = sizeof(ev.event_type) -
2983                (sizeof(ev.event_type.event_type.name) - size);
2984
2985        err = process(tool, &ev, NULL, machine);
2986
2987        return err;
2988}
2989
2990int perf_event__synthesize_event_types(struct perf_tool *tool,
2991                                       perf_event__handler_t process,
2992                                       struct machine *machine)
2993{
2994        struct perf_trace_event_type *type;
2995        int i, err = 0;
2996
2997        for (i = 0; i < trace_event_count; i++) {
2998                type = &trace_events[i];
2999
3000                err = perf_event__synthesize_event_type(tool, type->event_id,
3001                                                        type->name, process,
3002                                                        machine);
3003                if (err) {
3004                        pr_debug("failed to create perf header event type\n");
3005                        return err;
3006                }
3007        }
3008
3009        return err;
3010}
3011
3012int perf_event__process_event_type(struct perf_tool *tool __maybe_unused,
3013                                   union perf_event *event)
3014{
3015        if (perf_header__push_event(event->event_type.event_type.event_id,
3016                                    event->event_type.event_type.name) < 0)
3017                return -ENOMEM;
3018
3019        return 0;
3020}
3021
3022int perf_event__synthesize_tracing_data(struct perf_tool *tool, int fd,
3023                                        struct perf_evlist *evlist,
3024                                        perf_event__handler_t process)
3025{
3026        union perf_event ev;
3027        struct tracing_data *tdata;
3028        ssize_t size = 0, aligned_size = 0, padding;
3029        int err __maybe_unused = 0;
3030
3031        /*
3032         * We are going to store the size of the data followed
3033         * by the data contents. Since the fd descriptor is a pipe,
3034         * we cannot seek back to store the size of the data once
3035         * we know it. Instead we:
3036         *
3037         * - write the tracing data to the temp file
3038         * - get/write the data size to pipe
3039         * - write the tracing data from the temp file
3040         *   to the pipe
3041         */
3042        tdata = tracing_data_get(&evlist->entries, fd, true);
3043        if (!tdata)
3044                return -1;
3045
3046        memset(&ev, 0, sizeof(ev));
3047
3048        ev.tracing_data.header.type = PERF_RECORD_HEADER_TRACING_DATA;
3049        size = tdata->size;
3050        aligned_size = PERF_ALIGN(size, sizeof(u64));
3051        padding = aligned_size - size;
3052        ev.tracing_data.header.size = sizeof(ev.tracing_data);
3053        ev.tracing_data.size = aligned_size;
3054
3055        process(tool, &ev, NULL, NULL);
3056
3057        /*
3058         * The put function will copy all the tracing data
3059         * stored in temp file to the pipe.
3060         */
3061        tracing_data_put(tdata);
3062
3063        write_padded(fd, NULL, 0, padding);
3064
3065        return aligned_size;
3066}
3067
3068int perf_event__process_tracing_data(union perf_event *event,
3069                                     struct perf_session *session)
3070{
3071        ssize_t size_read, padding, size = event->tracing_data.size;
3072        off_t offset = lseek(session->fd, 0, SEEK_CUR);
3073        char buf[BUFSIZ];
3074
3075        /* setup for reading amidst mmap */
3076        lseek(session->fd, offset + sizeof(struct tracing_data_event),
3077              SEEK_SET);
3078
3079        size_read = trace_report(session->fd, &session->pevent,
3080                                 session->repipe);
3081        padding = PERF_ALIGN(size_read, sizeof(u64)) - size_read;
3082
3083        if (readn(session->fd, buf, padding) < 0) {
3084                pr_err("%s: reading input file", __func__);
3085                return -1;
3086        }
3087        if (session->repipe) {
3088                int retw = write(STDOUT_FILENO, buf, padding);
3089                if (retw <= 0 || retw != padding) {
3090                        pr_err("%s: repiping tracing data padding", __func__);
3091                        return -1;
3092                }
3093        }
3094
3095        if (size_read + padding != size) {
3096                pr_err("%s: tracing data size mismatch", __func__);
3097                return -1;
3098        }
3099
3100        perf_evlist__prepare_tracepoint_events(session->evlist,
3101                                               session->pevent);
3102
3103        return size_read + padding;
3104}
3105
3106int perf_event__synthesize_build_id(struct perf_tool *tool,
3107                                    struct dso *pos, u16 misc,
3108                                    perf_event__handler_t process,
3109                                    struct machine *machine)
3110{
3111        union perf_event ev;
3112        size_t len;
3113        int err = 0;
3114
3115        if (!pos->hit)
3116                return err;
3117
3118        memset(&ev, 0, sizeof(ev));
3119
3120        len = pos->long_name_len + 1;
3121        len = PERF_ALIGN(len, NAME_ALIGN);
3122        memcpy(&ev.build_id.build_id, pos->build_id, sizeof(pos->build_id));
3123        ev.build_id.header.type = PERF_RECORD_HEADER_BUILD_ID;
3124        ev.build_id.header.misc = misc;
3125        ev.build_id.pid = machine->pid;
3126        ev.build_id.header.size = sizeof(ev.build_id) + len;
3127        memcpy(&ev.build_id.filename, pos->long_name, pos->long_name_len);
3128
3129        err = process(tool, &ev, NULL, machine);
3130
3131        return err;
3132}
3133
3134int perf_event__process_build_id(struct perf_tool *tool __maybe_unused,
3135                                 union perf_event *event,
3136                                 struct perf_session *session)
3137{
3138        __event_process_build_id(&event->build_id,
3139                                 event->build_id.filename,
3140                                 session);
3141        return 0;
3142}
3143
3144void disable_buildid_cache(void)
3145{
3146        no_buildid_cache = true;
3147}
3148