// SPDX-License-Identifier: GPL-2.0-only
/*
 * Copyright (C) 2008,2009, Steven Rostedt <srostedt@redhat.com>
 */
#include <dirent.h>
#include <mntent.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdarg.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <sys/wait.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <stdbool.h>
#include <linux/list.h>
#include <linux/kernel.h>
#include <linux/zalloc.h>
#include <internal/lib.h> // page_size
#include <sys/param.h>

#include "trace-event.h"
#include "tracepoint.h"
#include <api/fs/tracing_path.h>
#include "evsel.h"
#include "debug.h"
#include "util.h"

#define VERSION "0.6"
#define MAX_EVENT_LENGTH 512

static int output_fd;

struct tracepoint_path {
	char *system;
	char *name;
	struct tracepoint_path *next;
};

/* unfortunately, you can not stat debugfs or proc files for size */
static int record_file(const char *file, ssize_t hdr_sz)
{
	unsigned long long size = 0;
	char buf[BUFSIZ], *sizep;
	off_t hdr_pos = lseek(output_fd, 0, SEEK_CUR);
	int r, fd;
	int err = -EIO;

	fd = open(file, O_RDONLY);
	if (fd < 0) {
		pr_debug("Can't read '%s'", file);
		return -errno;
	}

	/* put in zeros for file size, then fill true size later */
	if (hdr_sz) {
		if (write(output_fd, &size, hdr_sz) != hdr_sz)
			goto out;
	}

	do {
		r = read(fd, buf, BUFSIZ);
		if (r > 0) {
			size += r;
			if (write(output_fd, buf, r) != r)
				goto out;
		}
	} while (r > 0);

	/* ugh, handle big-endian hdr_size == 4 */
	sizep = (char*)&size;
	if (host_is_bigendian())
		sizep += sizeof(u64) - hdr_sz;

	if (hdr_sz && pwrite(output_fd, sizep, hdr_sz, hdr_pos) < 0) {
		pr_debug("writing file size failed\n");
		goto out;
	}

	err = 0;
out:
	close(fd);
	return err;
}

static int record_header_files(void)
{
	char *path = get_events_file("header_page");
	struct stat st;
	int err = -EIO;

	if (!path) {
		pr_debug("can't get tracing/events/header_page");
		return -ENOMEM;
	}

	if (stat(path, &st) < 0) {
		pr_debug("can't read '%s'", path);
		goto out;
	}

	if (write(output_fd, "header_page", 12) != 12) {
		pr_debug("can't write header_page\n");
		goto out;
	}

	if (record_file(path, 8) < 0) {
		pr_debug("can't record header_page file\n");
		goto out;
	}

	put_events_file(path);

	path = get_events_file("header_event");
	if (!path) {
		pr_debug("can't get tracing/events/header_event");
		err = -ENOMEM;
		goto out;
	}

	if (stat(path, &st) < 0) {
		pr_debug("can't read '%s'", path);
		goto out;
	}

	if (write(output_fd, "header_event", 13) != 13) {
		pr_debug("can't write header_event\n");
		goto out;
	}

	if (record_file(path, 8) < 0) {
		pr_debug("can't record header_event file\n");
		goto out;
	}

	err = 0;
out:
	put_events_file(path);
	return err;
}

static bool name_in_tp_list(char *sys, struct tracepoint_path *tps)
{
	while (tps) {
		if (!strcmp(sys, tps->name))
			return true;
		tps = tps->next;
	}

	return false;
}

#define for_each_event_tps(dir, dent, tps)			\
	while ((dent = readdir(dir)))				\
		if (dent->d_type == DT_DIR &&			\
		    (strcmp(dent->d_name, ".")) &&		\
		    (strcmp(dent->d_name, "..")))		\

static int copy_event_system(const char *sys, struct tracepoint_path *tps)
{
	struct dirent *dent;
	struct stat st;
	char *format;
	DIR *dir;
	int count = 0;
	int ret;
	int err;

	dir = opendir(sys);
	if (!dir) {
		pr_debug("can't read directory '%s'", sys);
		return -errno;
	}

	for_each_event_tps(dir, dent, tps) {
		if (!name_in_tp_list(dent->d_name, tps))
			continue;

		if (asprintf(&format, "%s/%s/format", sys, dent->d_name) < 0) {
			err = -ENOMEM;
			goto out;
		}
		ret = stat(format, &st);
		free(format);
		if (ret < 0)
			continue;
		count++;
	}

	if (write(output_fd, &count, 4) != 4) {
		err = -EIO;
		pr_debug("can't write count\n");
		goto out;
	}

	rewinddir(dir);
	for_each_event_tps(dir, dent, tps) {
		if (!name_in_tp_list(dent->d_name, tps))
			continue;

		if (asprintf(&format, "%s/%s/format", sys, dent->d_name) < 0) {
			err = -ENOMEM;
			goto out;
		}
		ret = stat(format, &st);

		if (ret >= 0) {
			err = record_file(format, 8);
			if (err) {
				free(format);
				goto out;
			}
		}
		free(format);
	}
	err = 0;
out:
	closedir(dir);
	return err;
}

static int record_ftrace_files(struct tracepoint_path *tps)
{
	char *path;
	int ret;

	path = get_events_file("ftrace");
	if (!path) {
		pr_debug("can't get tracing/events/ftrace");
		return -ENOMEM;
	}

	ret = copy_event_system(path, tps);

	put_tracing_file(path);

	return ret;
}

static bool system_in_tp_list(char *sys, struct tracepoint_path *tps)
{
	while (tps) {
		if (!strcmp(sys, tps->system))
			return true;
		tps = tps->next;
	}

	return false;
}

static int record_event_files(struct tracepoint_path *tps)
{
	struct dirent *dent;
	struct stat st;
	char *path;
	char *sys;
	DIR *dir;
	int count = 0;
	int ret;
	int err;

	path = get_tracing_file("events");
	if (!path) {
		pr_debug("can't get tracing/events");
		return -ENOMEM;
	}

	dir = opendir(path);
	if (!dir) {
		err = -errno;
		pr_debug("can't read directory '%s'", path);
		goto out;
	}

	for_each_event_tps(dir, dent, tps) {
		if (strcmp(dent->d_name, "ftrace") == 0 ||
		    !system_in_tp_list(dent->d_name, tps))
			continue;

		count++;
	}

	if (write(output_fd, &count, 4) != 4) {
		err = -EIO;
		pr_debug("can't write count\n");
		goto out;
	}

	rewinddir(dir);
	for_each_event_tps(dir, dent, tps) {
		if (strcmp(dent->d_name, "ftrace") == 0 ||
		    !system_in_tp_list(dent->d_name, tps))
			continue;

		if (asprintf(&sys, "%s/%s", path, dent->d_name) < 0) {
			err = -ENOMEM;
			goto out;
		}
		ret = stat(sys, &st);
		if (ret >= 0) {
			ssize_t size = strlen(dent->d_name) + 1;

			if (write(output_fd, dent->d_name, size) != size ||
			    copy_event_system(sys, tps) < 0) {
				err = -EIO;
				free(sys);
				goto out;
			}
		}
		free(sys);
	}
	err = 0;
out:
	closedir(dir);
	put_tracing_file(path);

	return err;
}

static int record_proc_kallsyms(void)
{
	unsigned long long size = 0;
	/*
	 * Just to keep older perf.data file parsers happy, record a zero
	 * sized kallsyms file, i.e. do the same thing that was done when
	 * /proc/kallsyms (or something specified via --kallsyms, in a
	 * different path) couldn't be read.
	 */
	return write(output_fd, &size, 4) != 4 ? -EIO : 0;
}

static int record_ftrace_printk(void)
{
	unsigned int size;
	char *path;
	struct stat st;
	int ret, err = 0;

	path = get_tracing_file("printk_formats");
	if (!path) {
		pr_debug("can't get tracing/printk_formats");
		return -ENOMEM;
	}

	ret = stat(path, &st);
	if (ret < 0) {
		/* not found */
		size = 0;
		if (write(output_fd, &size, 4) != 4)
			err = -EIO;
		goto out;
	}
	err = record_file(path, 4);

out:
	put_tracing_file(path);
	return err;
}

static int record_saved_cmdline(void)
{
	unsigned long long size;
	char *path;
	struct stat st;
	int ret, err = 0;

	path = get_tracing_file("saved_cmdlines");
	if (!path) {
		pr_debug("can't get tracing/saved_cmdline");
		return -ENOMEM;
	}

	ret = stat(path, &st);
	if (ret < 0) {
		/* not found */
		size = 0;
		if (write(output_fd, &size, 8) != 8)
			err = -EIO;
		goto out;
	}
	err = record_file(path, 8);

out:
	put_tracing_file(path);
	return err;
}

static void
put_tracepoints_path(struct tracepoint_path *tps)
{
	while (tps) {
		struct tracepoint_path *t = tps;

		tps = tps->next;
		zfree(&t->name);
		zfree(&t->system);
		free(t);
	}
}

static struct tracepoint_path *tracepoint_id_to_path(u64 config)
{
	struct tracepoint_path *path = NULL;
	DIR *sys_dir, *evt_dir;
	struct dirent *sys_dirent, *evt_dirent;
	char id_buf[24];
	int fd;
	u64 id;
	char evt_path[MAXPATHLEN];
	char *dir_path;

	sys_dir = tracing_events__opendir();
	if (!sys_dir)
		return NULL;

	for_each_subsystem(sys_dir, sys_dirent) {
		dir_path = get_events_file(sys_dirent->d_name);
		if (!dir_path)
			continue;
		evt_dir = opendir(dir_path);
		if (!evt_dir)
			goto next;

		for_each_event(dir_path, evt_dir, evt_dirent) {

			scnprintf(evt_path, MAXPATHLEN, "%s/%s/id", dir_path,
				  evt_dirent->d_name);
			fd = open(evt_path, O_RDONLY);
			if (fd < 0)
				continue;
			if (read(fd, id_buf, sizeof(id_buf)) < 0) {
				close(fd);
				continue;
			}
			close(fd);
			id = atoll(id_buf);
			if (id == config) {
				put_events_file(dir_path);
				closedir(evt_dir);
				closedir(sys_dir);
				path = zalloc(sizeof(*path));
				if (!path)
					return NULL;
				if (asprintf(&path->system, "%.*s",
					     MAX_EVENT_LENGTH, sys_dirent->d_name) < 0) {
					free(path);
					return NULL;
				}
				if (asprintf(&path->name, "%.*s",
					     MAX_EVENT_LENGTH, evt_dirent->d_name) < 0) {
					zfree(&path->system);
					free(path);
					return NULL;
				}
				return path;
			}
		}
		closedir(evt_dir);
next:
		put_events_file(dir_path);
	}

	closedir(sys_dir);
	return NULL;
}

static struct tracepoint_path *tracepoint_name_to_path(const char *name)
{
	struct tracepoint_path *path = zalloc(sizeof(*path));
	char *str = strchr(name, ':');

	if (path == NULL || str == NULL) {
		free(path);
		return NULL;
	}

	path->system = strndup(name, str - name);
	path->name = strdup(str+1);

	if (path->system == NULL || path->name == NULL) {
		zfree(&path->system);
		zfree(&path->name);
		zfree(&path);
	}

	return path;
}

static struct tracepoint_path *
get_tracepoints_path(struct list_head *pattrs)
{
	struct tracepoint_path path, *ppath = &path;
	struct evsel *pos;
	int nr_tracepoints = 0;

	list_for_each_entry(pos, pattrs, core.node) {
		if (pos->core.attr.type != PERF_TYPE_TRACEPOINT)
			continue;
		++nr_tracepoints;

		if (pos->name) {
			ppath->next = tracepoint_name_to_path(pos->name);
			if (ppath->next)
				goto next;

			if (strchr(pos->name, ':') == NULL)
				goto try_id;

			goto error;
		}

try_id:
		ppath->next = tracepoint_id_to_path(pos->core.attr.config);
		if (!ppath->next) {
error:
			pr_debug("No memory to alloc tracepoints list\n");
			put_tracepoints_path(path.next);
			return NULL;
		}
next:
		ppath = ppath->next;
	}

	return nr_tracepoints > 0 ? path.next : NULL;
}

bool have_tracepoints(struct list_head *pattrs)
{
	struct evsel *pos;

	list_for_each_entry(pos, pattrs, core.node)
		if (pos->core.attr.type == PERF_TYPE_TRACEPOINT)
			return true;

	return false;
}

static int tracing_data_header(void)
{
	char buf[20];
	ssize_t size;

	/* just guessing this is someone's birthday.. ;) */
	buf[0] = 23;
	buf[1] = 8;
	buf[2] = 68;
	memcpy(buf + 3, "tracing", 7);

	if (write(output_fd, buf, 10) != 10)
		return -1;

	size = strlen(VERSION) + 1;
	if (write(output_fd, VERSION, size) != size)
		return -1;

	/* save endian */
	if (host_is_bigendian())
		buf[0] = 1;
	else
		buf[0] = 0;

	if (write(output_fd, buf, 1) != 1)
		return -1;

	/* save size of long */
	buf[0] = sizeof(long);
	if (write(output_fd, buf, 1) != 1)
		return -1;

	/* save page_size */
	if (write(output_fd, &page_size, 4) != 4)
		return -1;

	return 0;
}

struct tracing_data *tracing_data_get(struct list_head *pattrs,
				      int fd, bool temp)
{
	struct tracepoint_path *tps;
	struct tracing_data *tdata;
	int err;

	output_fd = fd;

	tps = get_tracepoints_path(pattrs);
	if (!tps)
		return NULL;

	tdata = malloc(sizeof(*tdata));
	if (!tdata)
		return NULL;

	tdata->temp = temp;
	tdata->size = 0;

	if (temp) {
		int temp_fd;

		snprintf(tdata->temp_file, sizeof(tdata->temp_file),
			 "/tmp/perf-XXXXXX");
		if (!mkstemp(tdata->temp_file)) {
			pr_debug("Can't make temp file");
			free(tdata);
			return NULL;
		}

		temp_fd = open(tdata->temp_file, O_RDWR);
		if (temp_fd < 0) {
			pr_debug("Can't read '%s'", tdata->temp_file);
			free(tdata);
			return NULL;
		}

		/*
		 * Set the temp file the default output, so all the
		 * tracing data are stored into it.
		 */
		output_fd = temp_fd;
	}

	err = tracing_data_header();
	if (err)
		goto out;
	err = record_header_files();
	if (err)
		goto out;
	err = record_ftrace_files(tps);
	if (err)
		goto out;
	err = record_event_files(tps);
	if (err)
		goto out;
	err = record_proc_kallsyms();
	if (err)
		goto out;
	err = record_ftrace_printk();
	if (err)
		goto out;
	err = record_saved_cmdline();

out:
	/*
	 * All tracing data are stored by now, we can restore
	 * the default output file in case we used temp file.
	 */
	if (temp) {
		tdata->size = lseek(output_fd, 0, SEEK_CUR);
		close(output_fd);
		output_fd = fd;
	}

	if (err)
		zfree(&tdata);

	put_tracepoints_path(tps);
	return tdata;
}

int tracing_data_put(struct tracing_data *tdata)
{
	int err = 0;

	if (tdata->temp) {
		err = record_file(tdata->temp_file, 0);
		unlink(tdata->temp_file);
	}

	free(tdata);
	return err;
}

int read_tracing_data(int fd, struct list_head *pattrs)
{
	int err;
	struct tracing_data *tdata;

	/*
	 * We work over the real file, so we can write data
	 * directly, no temp file is needed.
	 */
	tdata = tracing_data_get(pattrs, fd, false);
	if (!tdata)
		return -ENOMEM;

	err = tracing_data_put(tdata);
	return err;
}
