diff options
Diffstat (limited to 'tools/perf/util/session.c')
| -rw-r--r-- | tools/perf/util/session.c | 80 |
1 files changed, 80 insertions, 0 deletions
diff --git a/tools/perf/util/session.c b/tools/perf/util/session.c new file mode 100644 index 000000000000..707ce1cb1621 --- /dev/null +++ b/tools/perf/util/session.c | |||
| @@ -0,0 +1,80 @@ | |||
| 1 | #include <linux/kernel.h> | ||
| 2 | |||
| 3 | #include <unistd.h> | ||
| 4 | #include <sys/types.h> | ||
| 5 | |||
| 6 | #include "session.h" | ||
| 7 | #include "util.h" | ||
| 8 | |||
| 9 | static int perf_session__open(struct perf_session *self, bool force) | ||
| 10 | { | ||
| 11 | struct stat input_stat; | ||
| 12 | |||
| 13 | self->fd = open(self->filename, O_RDONLY); | ||
| 14 | if (self->fd < 0) { | ||
| 15 | pr_err("failed to open file: %s", self->filename); | ||
| 16 | if (!strcmp(self->filename, "perf.data")) | ||
| 17 | pr_err(" (try 'perf record' first)"); | ||
| 18 | pr_err("\n"); | ||
| 19 | return -errno; | ||
| 20 | } | ||
| 21 | |||
| 22 | if (fstat(self->fd, &input_stat) < 0) | ||
| 23 | goto out_close; | ||
| 24 | |||
| 25 | if (!force && input_stat.st_uid && (input_stat.st_uid != geteuid())) { | ||
| 26 | pr_err("file %s not owned by current user or root\n", | ||
| 27 | self->filename); | ||
| 28 | goto out_close; | ||
| 29 | } | ||
| 30 | |||
| 31 | if (!input_stat.st_size) { | ||
| 32 | pr_info("zero-sized file (%s), nothing to do!\n", | ||
| 33 | self->filename); | ||
| 34 | goto out_close; | ||
| 35 | } | ||
| 36 | |||
| 37 | if (perf_header__read(&self->header, self->fd) < 0) { | ||
| 38 | pr_err("incompatible file format"); | ||
| 39 | goto out_close; | ||
| 40 | } | ||
| 41 | |||
| 42 | self->size = input_stat.st_size; | ||
| 43 | return 0; | ||
| 44 | |||
| 45 | out_close: | ||
| 46 | close(self->fd); | ||
| 47 | self->fd = -1; | ||
| 48 | return -1; | ||
| 49 | } | ||
| 50 | |||
| 51 | struct perf_session *perf_session__new(const char *filename, int mode, bool force) | ||
| 52 | { | ||
| 53 | size_t len = strlen(filename) + 1; | ||
| 54 | struct perf_session *self = zalloc(sizeof(*self) + len); | ||
| 55 | |||
| 56 | if (self == NULL) | ||
| 57 | goto out; | ||
| 58 | |||
| 59 | if (perf_header__init(&self->header) < 0) | ||
| 60 | goto out_delete; | ||
| 61 | |||
| 62 | memcpy(self->filename, filename, len); | ||
| 63 | |||
| 64 | if (mode == O_RDONLY && perf_session__open(self, force) < 0) { | ||
| 65 | perf_session__delete(self); | ||
| 66 | self = NULL; | ||
| 67 | } | ||
| 68 | out: | ||
| 69 | return self; | ||
| 70 | out_delete: | ||
| 71 | free(self); | ||
| 72 | return NULL; | ||
| 73 | } | ||
| 74 | |||
| 75 | void perf_session__delete(struct perf_session *self) | ||
| 76 | { | ||
| 77 | perf_header__exit(&self->header); | ||
| 78 | close(self->fd); | ||
| 79 | free(self); | ||
| 80 | } | ||
