// SPDX-License-Identifier: GPL-2.0
/*
 * trace_events_hist - trace event hist triggers
 *
 * Copyright (C) 2015 Tom Zanussi <tom.zanussi@linux.intel.com>
 */

#include <linux/module.h>
#include <linux/kallsyms.h>
#include <linux/security.h>
#include <linux/mutex.h>
#include <linux/slab.h>
#include <linux/stacktrace.h>
#include <linux/rculist.h>
#include <linux/tracefs.h>

/* for gfp flag names */
#include <linux/trace_events.h>
#include <trace/events/mmflags.h>

#include "tracing_map.h"
#include "trace.h"
#include "trace_dynevent.h"

#define SYNTH_SYSTEM		"synthetic"
#define SYNTH_FIELDS_MAX	32

#define STR_VAR_LEN_MAX		32 /* must be multiple of sizeof(u64) */

#define ERRORS								\
	C(NONE,			"No error"),				\
	C(DUPLICATE_VAR,	"Variable already defined"),		\
	C(VAR_NOT_UNIQUE,	"Variable name not unique, need to use fully qualified name (subsys.event.var) for variable"), \
	C(TOO_MANY_VARS,	"Too many variables defined"),		\
	C(MALFORMED_ASSIGNMENT,	"Malformed assignment"),		\
	C(NAMED_MISMATCH,	"Named hist trigger doesn't match existing named trigger (includes variables)"), \
	C(TRIGGER_EEXIST,	"Hist trigger already exists"),		\
	C(TRIGGER_ENOENT_CLEAR,	"Can't clear or continue a nonexistent hist trigger"), \
	C(SET_CLOCK_FAIL,	"Couldn't set trace_clock"),		\
	C(BAD_FIELD_MODIFIER,	"Invalid field modifier"),		\
	C(TOO_MANY_SUBEXPR,	"Too many subexpressions (3 max)"),	\
	C(TIMESTAMP_MISMATCH,	"Timestamp units in expression don't match"), \
	C(TOO_MANY_FIELD_VARS,	"Too many field variables defined"),	\
	C(EVENT_FILE_NOT_FOUND,	"Event file not found"),		\
	C(HIST_NOT_FOUND,	"Matching event histogram not found"),	\
	C(HIST_CREATE_FAIL,	"Couldn't create histogram for field"),	\
	C(SYNTH_VAR_NOT_FOUND,	"Couldn't find synthetic variable"),	\
	C(SYNTH_EVENT_NOT_FOUND,"Couldn't find synthetic event"),	\
	C(SYNTH_TYPE_MISMATCH,	"Param type doesn't match synthetic event field type"), \
	C(SYNTH_COUNT_MISMATCH,	"Param count doesn't match synthetic event field count"), \
	C(FIELD_VAR_PARSE_FAIL,	"Couldn't parse field variable"),	\
	C(VAR_CREATE_FIND_FAIL,	"Couldn't create or find variable"),	\
	C(ONX_NOT_VAR,		"For onmax(x) or onchange(x), x must be a variable"), \
	C(ONX_VAR_NOT_FOUND,	"Couldn't find onmax or onchange variable"), \
	C(ONX_VAR_CREATE_FAIL,	"Couldn't create onmax or onchange variable"), \
	C(FIELD_VAR_CREATE_FAIL,"Couldn't create field variable"),	\
	C(TOO_MANY_PARAMS,	"Too many action params"),		\
	C(PARAM_NOT_FOUND,	"Couldn't find param"),			\
	C(INVALID_PARAM,	"Invalid action param"),		\
	C(ACTION_NOT_FOUND,	"No action found"),			\
	C(NO_SAVE_PARAMS,	"No params found for save()"),		\
	C(TOO_MANY_SAVE_ACTIONS,"Can't have more than one save() action per hist"), \
	C(ACTION_MISMATCH,	"Handler doesn't support action"),	\
	C(NO_CLOSING_PAREN,	"No closing paren found"),		\
	C(SUBSYS_NOT_FOUND,	"Missing subsystem"),			\
	C(INVALID_SUBSYS_EVENT,	"Invalid subsystem or event name"),	\
	C(INVALID_REF_KEY,	"Using variable references in keys not supported"), \
	C(VAR_NOT_FOUND,	"Couldn't find variable"),		\
	C(FIELD_NOT_FOUND,	"Couldn't find field"),			\
	C(EMPTY_ASSIGNMENT,	"Empty assignment"),			\
	C(INVALID_SORT_MODIFIER,"Invalid sort modifier"),		\
	C(EMPTY_SORT_FIELD,	"Empty sort field"),			\
	C(TOO_MANY_SORT_FIELDS,	"Too many sort fields (Max = 2)"),	\
	C(INVALID_SORT_FIELD,	"Sort field must be a key or a val"),

#undef C
#define C(a, b)		HIST_ERR_##a

enum { ERRORS };

#undef C
#define C(a, b)		b

static const char *err_text[] = { ERRORS };

struct hist_field;

typedef u64 (*hist_field_fn_t) (struct hist_field *field,
				struct tracing_map_elt *elt,
				struct ring_buffer_event *rbe,
				void *event);

#define HIST_FIELD_OPERANDS_MAX	2
#define HIST_FIELDS_MAX		(TRACING_MAP_FIELDS_MAX + TRACING_MAP_VARS_MAX)
#define HIST_ACTIONS_MAX	8

enum field_op_id {
	FIELD_OP_NONE,
	FIELD_OP_PLUS,
	FIELD_OP_MINUS,
	FIELD_OP_UNARY_MINUS,
};

/*
 * A hist_var (histogram variable) contains variable information for
 * hist_fields having the HIST_FIELD_FL_VAR or HIST_FIELD_FL_VAR_REF
 * flag set.  A hist_var has a variable name e.g. ts0, and is
 * associated with a given histogram trigger, as specified by
 * hist_data.  The hist_var idx is the unique index assigned to the
 * variable by the hist trigger's tracing_map.  The idx is what is
 * used to set a variable's value and, by a variable reference, to
 * retrieve it.
 */
struct hist_var {
	char				*name;
	struct hist_trigger_data	*hist_data;
	unsigned int			idx;
};

struct hist_field {
	struct ftrace_event_field	*field;
	unsigned long			flags;
	hist_field_fn_t			fn;
	unsigned int			ref;
	unsigned int			size;
	unsigned int			offset;
	unsigned int                    is_signed;
	const char			*type;
	struct hist_field		*operands[HIST_FIELD_OPERANDS_MAX];
	struct hist_trigger_data	*hist_data;

	/*
	 * Variable fields contain variable-specific info in var.
	 */
	struct hist_var			var;
	enum field_op_id		operator;
	char				*system;
	char				*event_name;

	/*
	 * The name field is used for EXPR and VAR_REF fields.  VAR
	 * fields contain the variable name in var.name.
	 */
	char				*name;

	/*
	 * When a histogram trigger is hit, if it has any references
	 * to variables, the values of those variables are collected
	 * into a var_ref_vals array by resolve_var_refs().  The
	 * current value of each variable is read from the tracing_map
	 * using the hist field's hist_var.idx and entered into the
	 * var_ref_idx entry i.e. var_ref_vals[var_ref_idx].
	 */
	unsigned int			var_ref_idx;
	bool                            read_once;
};

static u64 hist_field_none(struct hist_field *field,
			   struct tracing_map_elt *elt,
			   struct ring_buffer_event *rbe,
			   void *event)
{
	return 0;
}

static u64 hist_field_counter(struct hist_field *field,
			      struct tracing_map_elt *elt,
			      struct ring_buffer_event *rbe,
			      void *event)
{
	return 1;
}

static u64 hist_field_string(struct hist_field *hist_field,
			     struct tracing_map_elt *elt,
			     struct ring_buffer_event *rbe,
			     void *event)
{
	char *addr = (char *)(event + hist_field->field->offset);

	return (u64)(unsigned long)addr;
}

static u64 hist_field_dynstring(struct hist_field *hist_field,
				struct tracing_map_elt *elt,
				struct ring_buffer_event *rbe,
				void *event)
{
	u32 str_item = *(u32 *)(event + hist_field->field->offset);
	int str_loc = str_item & 0xffff;
	char *addr = (char *)(event + str_loc);

	return (u64)(unsigned long)addr;
}

static u64 hist_field_pstring(struct hist_field *hist_field,
			      struct tracing_map_elt *elt,
			      struct ring_buffer_event *rbe,
			      void *event)
{
	char **addr = (char **)(event + hist_field->field->offset);

	return (u64)(unsigned long)*addr;
}

static u64 hist_field_log2(struct hist_field *hist_field,
			   struct tracing_map_elt *elt,
			   struct ring_buffer_event *rbe,
			   void *event)
{
	struct hist_field *operand = hist_field->operands[0];

	u64 val = operand->fn(operand, elt, rbe, event);

	return (u64) ilog2(roundup_pow_of_two(val));
}

static u64 hist_field_plus(struct hist_field *hist_field,
			   struct tracing_map_elt *elt,
			   struct ring_buffer_event *rbe,
			   void *event)
{
	struct hist_field *operand1 = hist_field->operands[0];
	struct hist_field *operand2 = hist_field->operands[1];

	u64 val1 = operand1->fn(operand1, elt, rbe, event);
	u64 val2 = operand2->fn(operand2, elt, rbe, event);

	return val1 + val2;
}

static u64 hist_field_minus(struct hist_field *hist_field,
			    struct tracing_map_elt *elt,
			    struct ring_buffer_event *rbe,
			    void *event)
{
	struct hist_field *operand1 = hist_field->operands[0];
	struct hist_field *operand2 = hist_field->operands[1];

	u64 val1 = operand1->fn(operand1, elt, rbe, event);
	u64 val2 = operand2->fn(operand2, elt, rbe, event);

	return val1 - val2;
}

static u64 hist_field_unary_minus(struct hist_field *hist_field,
				  struct tracing_map_elt *elt,
				  struct ring_buffer_event *rbe,
				  void *event)
{
	struct hist_field *operand = hist_field->operands[0];

	s64 sval = (s64)operand->fn(operand, elt, rbe, event);
	u64 val = (u64)-sval;

	return val;
}

#define DEFINE_HIST_FIELD_FN(type)					\
	static u64 hist_field_##type(struct hist_field *hist_field,	\
				     struct tracing_map_elt *elt,	\
				     struct ring_buffer_event *rbe,	\
				     void *event)			\
{									\
	type *addr = (type *)(event + hist_field->field->offset);	\
									\
	return (u64)(unsigned long)*addr;				\
}

DEFINE_HIST_FIELD_FN(s64);
DEFINE_HIST_FIELD_FN(u64);
DEFINE_HIST_FIELD_FN(s32);
DEFINE_HIST_FIELD_FN(u32);
DEFINE_HIST_FIELD_FN(s16);
DEFINE_HIST_FIELD_FN(u16);
DEFINE_HIST_FIELD_FN(s8);
DEFINE_HIST_FIELD_FN(u8);

#define for_each_hist_field(i, hist_data)	\
	for ((i) = 0; (i) < (hist_data)->n_fields; (i)++)

#define for_each_hist_val_field(i, hist_data)	\
	for ((i) = 0; (i) < (hist_data)->n_vals; (i)++)

#define for_each_hist_key_field(i, hist_data)	\
	for ((i) = (hist_data)->n_vals; (i) < (hist_data)->n_fields; (i)++)

#define HIST_STACKTRACE_DEPTH	16
#define HIST_STACKTRACE_SIZE	(HIST_STACKTRACE_DEPTH * sizeof(unsigned long))
#define HIST_STACKTRACE_SKIP	5

#define HITCOUNT_IDX		0
#define HIST_KEY_SIZE_MAX	(MAX_FILTER_STR_VAL + HIST_STACKTRACE_SIZE)

enum hist_field_flags {
	HIST_FIELD_FL_HITCOUNT		= 1 << 0,
	HIST_FIELD_FL_KEY		= 1 << 1,
	HIST_FIELD_FL_STRING		= 1 << 2,
	HIST_FIELD_FL_HEX		= 1 << 3,
	HIST_FIELD_FL_SYM		= 1 << 4,
	HIST_FIELD_FL_SYM_OFFSET	= 1 << 5,
	HIST_FIELD_FL_EXECNAME		= 1 << 6,
	HIST_FIELD_FL_SYSCALL		= 1 << 7,
	HIST_FIELD_FL_STACKTRACE	= 1 << 8,
	HIST_FIELD_FL_LOG2		= 1 << 9,
	HIST_FIELD_FL_TIMESTAMP		= 1 << 10,
	HIST_FIELD_FL_TIMESTAMP_USECS	= 1 << 11,
	HIST_FIELD_FL_VAR		= 1 << 12,
	HIST_FIELD_FL_EXPR		= 1 << 13,
	HIST_FIELD_FL_VAR_REF		= 1 << 14,
	HIST_FIELD_FL_CPU		= 1 << 15,
	HIST_FIELD_FL_ALIAS		= 1 << 16,
};

struct var_defs {
	unsigned int	n_vars;
	char		*name[TRACING_MAP_VARS_MAX];
	char		*expr[TRACING_MAP_VARS_MAX];
};

struct hist_trigger_attrs {
	char		*keys_str;
	char		*vals_str;
	char		*sort_key_str;
	char		*name;
	char		*clock;
	bool		pause;
	bool		cont;
	bool		clear;
	bool		ts_in_usecs;
	unsigned int	map_bits;

	char		*assignment_str[TRACING_MAP_VARS_MAX];
	unsigned int	n_assignments;

	char		*action_str[HIST_ACTIONS_MAX];
	unsigned int	n_actions;

	struct var_defs	var_defs;
};

struct field_var {
	struct hist_field	*var;
	struct hist_field	*val;
};

struct field_var_hist {
	struct hist_trigger_data	*hist_data;
	char				*cmd;
};

struct hist_trigger_data {
	struct hist_field               *fields[HIST_FIELDS_MAX];
	unsigned int			n_vals;
	unsigned int			n_keys;
	unsigned int			n_fields;
	unsigned int			n_vars;
	unsigned int			key_size;
	struct tracing_map_sort_key	sort_keys[TRACING_MAP_SORT_KEYS_MAX];
	unsigned int			n_sort_keys;
	struct trace_event_file		*event_file;
	struct hist_trigger_attrs	*attrs;
	struct tracing_map		*map;
	bool				enable_timestamps;
	bool				remove;
	struct hist_field               *var_refs[TRACING_MAP_VARS_MAX];
	unsigned int			n_var_refs;

	struct action_data		*actions[HIST_ACTIONS_MAX];
	unsigned int			n_actions;

	struct field_var		*field_vars[SYNTH_FIELDS_MAX];
	unsigned int			n_field_vars;
	unsigned int			n_field_var_str;
	struct field_var_hist		*field_var_hists[SYNTH_FIELDS_MAX];
	unsigned int			n_field_var_hists;

	struct field_var		*save_vars[SYNTH_FIELDS_MAX];
	unsigned int			n_save_vars;
	unsigned int			n_save_var_str;
};

static int create_synth_event(int argc, const char **argv);
static int synth_event_show(struct seq_file *m, struct dyn_event *ev);
static int synth_event_release(struct dyn_event *ev);
static bool synth_event_is_busy(struct dyn_event *ev);
static bool synth_event_match(const char *system, const char *event,
			int argc, const char **argv, struct dyn_event *ev);

static struct dyn_event_operations synth_event_ops = {
	.create = create_synth_event,
	.show = synth_event_show,
	.is_busy = synth_event_is_busy,
	.free = synth_event_release,
	.match = synth_event_match,
};

struct synth_field {
	char *type;
	char *name;
	size_t size;
	unsigned int offset;
	bool is_signed;
	bool is_string;
};

struct synth_event {
	struct dyn_event			devent;
	int					ref;
	char					*name;
	struct synth_field			**fields;
	unsigned int				n_fields;
	unsigned int				n_u64;
	struct trace_event_class		class;
	struct trace_event_call			call;
	struct tracepoint			*tp;
	struct module				*mod;
};

static bool is_synth_event(struct dyn_event *ev)
{
	return ev->ops == &synth_event_ops;
}

static struct synth_event *to_synth_event(struct dyn_event *ev)
{
	return container_of(ev, struct synth_event, devent);
}

static bool synth_event_is_busy(struct dyn_event *ev)
{
	struct synth_event *event = to_synth_event(ev);

	return event->ref != 0;
}

static bool synth_event_match(const char *system, const char *event,
			int argc, const char **argv, struct dyn_event *ev)
{
	struct synth_event *sev = to_synth_event(ev);

	return strcmp(sev->name, event) == 0 &&
		(!system || strcmp(system, SYNTH_SYSTEM) == 0);
}

struct action_data;

typedef void (*action_fn_t) (struct hist_trigger_data *hist_data,
			     struct tracing_map_elt *elt, void *rec,
			     struct ring_buffer_event *rbe, void *key,
			     struct action_data *data, u64 *var_ref_vals);

typedef bool (*check_track_val_fn_t) (u64 track_val, u64 var_val);

enum handler_id {
	HANDLER_ONMATCH = 1,
	HANDLER_ONMAX,
	HANDLER_ONCHANGE,
};

enum action_id {
	ACTION_SAVE = 1,
	ACTION_TRACE,
	ACTION_SNAPSHOT,
};

struct action_data {
	enum handler_id		handler;
	enum action_id		action;
	char			*action_name;
	action_fn_t		fn;

	unsigned int		n_params;
	char			*params[SYNTH_FIELDS_MAX];

	/*
	 * When a histogram trigger is hit, the values of any
	 * references to variables, including variables being passed
	 * as parameters to synthetic events, are collected into a
	 * var_ref_vals array.  This var_ref_idx array is an array of
	 * indices into the var_ref_vals array, one for each synthetic
	 * event param, and is passed to the synthetic event
	 * invocation.
	 */
	unsigned int		var_ref_idx[TRACING_MAP_VARS_MAX];
	struct synth_event	*synth_event;
	bool			use_trace_keyword;
	char			*synth_event_name;

	union {
		struct {
			char			*event;
			char			*event_system;
		} match_data;

		struct {
			/*
			 * var_str contains the $-unstripped variable
			 * name referenced by var_ref, and used when
			 * printing the action.  Because var_ref
			 * creation is deferred to create_actions(),
			 * we need a per-action way to save it until
			 * then, thus var_str.
			 */
			char			*var_str;

			/*
			 * var_ref refers to the variable being
			 * tracked e.g onmax($var).
			 */
			struct hist_field	*var_ref;

			/*
			 * track_var contains the 'invisible' tracking
			 * variable created to keep the current
			 * e.g. max value.
			 */
			struct hist_field	*track_var;

			check_track_val_fn_t	check_val;
			action_fn_t		save_data;
		} track_data;
	};
};

struct track_data {
	u64				track_val;
	bool				updated;

	unsigned int			key_len;
	void				*key;
	struct tracing_map_elt		elt;

	struct action_data		*action_data;
	struct hist_trigger_data	*hist_data;
};

struct hist_elt_data {
	char *comm;
	u64 *var_ref_vals;
	char *field_var_str[SYNTH_FIELDS_MAX];
};

struct snapshot_context {
	struct tracing_map_elt	*elt;
	void			*key;
};

static void track_data_free(struct track_data *track_data)
{
	struct hist_elt_data *elt_data;

	if (!track_data)
		return;

	kfree(track_data->key);

	elt_data = track_data->elt.private_data;
	if (elt_data) {
		kfree(elt_data->comm);
		kfree(elt_data);
	}

	kfree(track_data);
}

static struct track_data *track_data_alloc(unsigned int key_len,
					   struct action_data *action_data,
					   struct hist_trigger_data *hist_data)
{
	struct track_data *data = kzalloc(sizeof(*data), GFP_KERNEL);
	struct hist_elt_data *elt_data;

	if (!data)
		return ERR_PTR(-ENOMEM);

	data->key = kzalloc(key_len, GFP_KERNEL);
	if (!data->key) {
		track_data_free(data);
		return ERR_PTR(-ENOMEM);
	}

	data->key_len = key_len;
	data->action_data = action_data;
	data->hist_data = hist_data;

	elt_data = kzalloc(sizeof(*elt_data), GFP_KERNEL);
	if (!elt_data) {
		track_data_free(data);
		return ERR_PTR(-ENOMEM);
	}
	data->elt.private_data = elt_data;

	elt_data->comm = kzalloc(TASK_COMM_LEN, GFP_KERNEL);
	if (!elt_data->comm) {
		track_data_free(data);
		return ERR_PTR(-ENOMEM);
	}

	return data;
}

static char last_cmd[MAX_FILTER_STR_VAL];
static char last_cmd_loc[MAX_FILTER_STR_VAL];

static int errpos(char *str)
{
	return err_pos(last_cmd, str);
}

static void last_cmd_set(struct trace_event_file *file, char *str)
{
	const char *system = NULL, *name = NULL;
	struct trace_event_call *call;

	if (!str)
		return;

	strcpy(last_cmd, "hist:");
	strncat(last_cmd, str, MAX_FILTER_STR_VAL - 1 - sizeof("hist:"));

	if (file) {
		call = file->event_call;

		system = call->class->system;
		if (system) {
			name = trace_event_name(call);
			if (!name)
				system = NULL;
		}
	}

	if (system)
		snprintf(last_cmd_loc, MAX_FILTER_STR_VAL, "hist:%s:%s", system, name);
}

static void hist_err(struct trace_array *tr, u8 err_type, u8 err_pos)
{
	tracing_log_err(tr, last_cmd_loc, last_cmd, err_text,
			err_type, err_pos);
}

static void hist_err_clear(void)
{
	last_cmd[0] = '\0';
	last_cmd_loc[0] = '\0';
}

struct synth_trace_event {
	struct trace_entry	ent;
	u64			fields[];
};

static int synth_event_define_fields(struct trace_event_call *call)
{
	struct synth_trace_event trace;
	int offset = offsetof(typeof(trace), fields);
	struct synth_event *event = call->data;
	unsigned int i, size, n_u64;
	char *name, *type;
	bool is_signed;
	int ret = 0;

	for (i = 0, n_u64 = 0; i < event->n_fields; i++) {
		size = event->fields[i]->size;
		is_signed = event->fields[i]->is_signed;
		type = event->fields[i]->type;
		name = event->fields[i]->name;
		ret = trace_define_field(call, type, name, offset, size,
					 is_signed, FILTER_OTHER);
		if (ret)
			break;

		event->fields[i]->offset = n_u64;

		if (event->fields[i]->is_string) {
			offset += STR_VAR_LEN_MAX;
			n_u64 += STR_VAR_LEN_MAX / sizeof(u64);
		} else {
			offset += sizeof(u64);
			n_u64++;
		}
	}

	event->n_u64 = n_u64;

	return ret;
}

static bool synth_field_signed(char *type)
{
	if (str_has_prefix(type, "u"))
		return false;
	if (strcmp(type, "gfp_t") == 0)
		return false;

	return true;
}

static int synth_field_is_string(char *type)
{
	if (strstr(type, "char[") != NULL)
		return true;

	return false;
}

static int synth_field_string_size(char *type)
{
	char buf[4], *end, *start;
	unsigned int len;
	int size, err;

	start = strstr(type, "char[");
	if (start == NULL)
		return -EINVAL;
	start += sizeof("char[") - 1;

	end = strchr(type, ']');
	if (!end || end < start)
		return -EINVAL;

	len = end - start;
	if (len > 3)
		return -EINVAL;

	strncpy(buf, start, len);
	buf[len] = '\0';

	err = kstrtouint(buf, 0, &size);
	if (err)
		return err;

	if (size > STR_VAR_LEN_MAX)
		return -EINVAL;

	return size;
}

static int synth_field_size(char *type)
{
	int size = 0;

	if (strcmp(type, "s64") == 0)
		size = sizeof(s64);
	else if (strcmp(type, "u64") == 0)
		size = sizeof(u64);
	else if (strcmp(type, "s32") == 0)
		size = sizeof(s32);
	else if (strcmp(type, "u32") == 0)
		size = sizeof(u32);
	else if (strcmp(type, "s16") == 0)
		size = sizeof(s16);
	else if (strcmp(type, "u16") == 0)
		size = sizeof(u16);
	else if (strcmp(type, "s8") == 0)
		size = sizeof(s8);
	else if (strcmp(type, "u8") == 0)
		size = sizeof(u8);
	else if (strcmp(type, "char") == 0)
		size = sizeof(char);
	else if (strcmp(type, "unsigned char") == 0)
		size = sizeof(unsigned char);
	else if (strcmp(type, "int") == 0)
		size = sizeof(int);
	else if (strcmp(type, "unsigned int") == 0)
		size = sizeof(unsigned int);
	else if (strcmp(type, "long") == 0)
		size = sizeof(long);
	else if (strcmp(type, "unsigned long") == 0)
		size = sizeof(unsigned long);
	else if (strcmp(type, "pid_t") == 0)
		size = sizeof(pid_t);
	else if (strcmp(type, "gfp_t") == 0)
		size = sizeof(gfp_t);
	else if (synth_field_is_string(type))
		size = synth_field_string_size(type);

	return size;
}

static const char *synth_field_fmt(char *type)
{
	const char *fmt = "%llu";

	if (strcmp(type, "s64") == 0)
		fmt = "%lld";
	else if (strcmp(type, "u64") == 0)
		fmt = "%llu";
	else if (strcmp(type, "s32") == 0)
		fmt = "%d";
	else if (strcmp(type, "u32") == 0)
		fmt = "%u";
	else if (strcmp(type, "s16") == 0)
		fmt = "%d";
	else if (strcmp(type, "u16") == 0)
		fmt = "%u";
	else if (strcmp(type, "s8") == 0)
		fmt = "%d";
	else if (strcmp(type, "u8") == 0)
		fmt = "%u";
	else if (strcmp(type, "char") == 0)
		fmt = "%d";
	else if (strcmp(type, "unsigned char") == 0)
		fmt = "%u";
	else if (strcmp(type, "int") == 0)
		fmt = "%d";
	else if (strcmp(type, "unsigned int") == 0)
		fmt = "%u";
	else if (strcmp(type, "long") == 0)
		fmt = "%ld";
	else if (strcmp(type, "unsigned long") == 0)
		fmt = "%lu";
	else if (strcmp(type, "pid_t") == 0)
		fmt = "%d";
	else if (strcmp(type, "gfp_t") == 0)
		fmt = "%x";
	else if (synth_field_is_string(type))
		fmt = "%s";

	return fmt;
}

static enum print_line_t print_synth_event(struct trace_iterator *iter,
					   int flags,
					   struct trace_event *event)
{
	struct trace_array *tr = iter->tr;
	struct trace_seq *s = &iter->seq;
	struct synth_trace_event *entry;
	struct synth_event *se;
	unsigned int i, n_u64;
	char print_fmt[32];
	const char *fmt;

	entry = (struct synth_trace_event *)iter->ent;
	se = container_of(event, struct synth_event, call.event);

	trace_seq_printf(s, "%s: ", se->name);

	for (i = 0, n_u64 = 0; i < se->n_fields; i++) {
		if (trace_seq_has_overflowed(s))
			goto end;

		fmt = synth_field_fmt(se->fields[i]->type);

		/* parameter types */
		if (tr && tr->trace_flags & TRACE_ITER_VERBOSE)
			trace_seq_printf(s, "%s ", fmt);

		snprintf(print_fmt, sizeof(print_fmt), "%%s=%s%%s", fmt);

		/* parameter values */
		if (se->fields[i]->is_string) {
			trace_seq_printf(s, print_fmt, se->fields[i]->name,
					 (char *)&entry->fields[n_u64],
					 i == se->n_fields - 1 ? "" : " ");
			n_u64 += STR_VAR_LEN_MAX / sizeof(u64);
		} else {
			struct trace_print_flags __flags[] = {
			    __def_gfpflag_names, {-1, NULL} };

			trace_seq_printf(s, print_fmt, se->fields[i]->name,
					 entry->fields[n_u64],
					 i == se->n_fields - 1 ? "" : " ");

			if (strcmp(se->fields[i]->type, "gfp_t") == 0) {
				trace_seq_puts(s, " (");
				trace_print_flags_seq(s, "|",
						      entry->fields[n_u64],
						      __flags);
				trace_seq_putc(s, ')');
			}
			n_u64++;
		}
	}
end:
	trace_seq_putc(s, '\n');

	return trace_handle_return(s);
}

static struct trace_event_functions synth_event_funcs = {
	.trace		= print_synth_event
};

static notrace void trace_event_raw_event_synth(void *__data,
						u64 *var_ref_vals,
						unsigned int *var_ref_idx)
{
	struct trace_event_file *trace_file = __data;
	struct synth_trace_event *entry;
	struct trace_event_buffer fbuffer;
	struct trace_buffer *buffer;
	struct synth_event *event;
	unsigned int i, n_u64, val_idx;
	int fields_size = 0;

	event = trace_file->event_call->data;

	if (trace_trigger_soft_disabled(trace_file))
		return;

	fields_size = event->n_u64 * sizeof(u64);

	/*
	 * Avoid ring buffer recursion detection, as this event
	 * is being performed within another event.
	 */
	buffer = trace_file->tr->array_buffer.buffer;
	ring_buffer_nest_start(buffer);

	entry = trace_event_buffer_reserve(&fbuffer, trace_file,
					   sizeof(*entry) + fields_size);
	if (!entry)
		goto out;

	for (i = 0, n_u64 = 0; i < event->n_fields; i++) {
		val_idx = var_ref_idx[i];
		if (event->fields[i]->is_string) {
			char *str_val = (char *)(long)var_ref_vals[val_idx];
			char *str_field = (char *)&entry->fields[n_u64];

			strscpy(str_field, str_val, STR_VAR_LEN_MAX);
			n_u64 += STR_VAR_LEN_MAX / sizeof(u64);
		} else {
			struct synth_field *field = event->fields[i];
			u64 val = var_ref_vals[val_idx];

			switch (field->size) {
			case 1:
				*(u8 *)&entry->fields[n_u64] = (u8)val;
				break;

			case 2:
				*(u16 *)&entry->fields[n_u64] = (u16)val;
				break;

			case 4:
				*(u32 *)&entry->fields[n_u64] = (u32)val;
				break;

			default:
				entry->fields[n_u64] = val;
				break;
			}
			n_u64++;
		}
	}

	trace_event_buffer_commit(&fbuffer);
out:
	ring_buffer_nest_end(buffer);
}

static void free_synth_event_print_fmt(struct trace_event_call *call)
{
	if (call) {
		kfree(call->print_fmt);
		call->print_fmt = NULL;
	}
}

static int __set_synth_event_print_fmt(struct synth_event *event,
				       char *buf, int len)
{
	const char *fmt;
	int pos = 0;
	int i;

	/* When len=0, we just calculate the needed length */
#define LEN_OR_ZERO (len ? len - pos : 0)

	pos += snprintf(buf + pos, LEN_OR_ZERO, "\"");
	for (i = 0; i < event->n_fields; i++) {
		fmt = synth_field_fmt(event->fields[i]->type);
		pos += snprintf(buf + pos, LEN_OR_ZERO, "%s=%s%s",
				event->fields[i]->name, fmt,
				i == event->n_fields - 1 ? "" : ", ");
	}
	pos += snprintf(buf + pos, LEN_OR_ZERO, "\"");

	for (i = 0; i < event->n_fields; i++) {
		pos += snprintf(buf + pos, LEN_OR_ZERO,
				", REC->%s", event->fields[i]->name);
	}

#undef LEN_OR_ZERO

	/* return the length of print_fmt */
	return pos;
}

static int set_synth_event_print_fmt(struct trace_event_call *call)
{
	struct synth_event *event = call->data;
	char *print_fmt;
	int len;

	/* First: called with 0 length to calculate the needed length */
	len = __set_synth_event_print_fmt(event, NULL, 0);

	print_fmt = kmalloc(len + 1, GFP_KERNEL);
	if (!print_fmt)
		return -ENOMEM;

	/* Second: actually write the @print_fmt */
	__set_synth_event_print_fmt(event, print_fmt, len + 1);
	call->print_fmt = print_fmt;

	return 0;
}

static void free_synth_field(struct synth_field *field)
{
	kfree(field->type);
	kfree(field->name);
	kfree(field);
}

static struct synth_field *parse_synth_field(int argc, const char **argv,
					     int *consumed)
{
	struct synth_field *field;
	const char *prefix = NULL, *field_type = argv[0], *field_name, *array;
	int len, ret = 0;

	if (field_type[0] == ';')
		field_type++;

	if (!strcmp(field_type, "unsigned")) {
		if (argc < 3)
			return ERR_PTR(-EINVAL);
		prefix = "unsigned ";
		field_type = argv[1];
		field_name = argv[2];
		*consumed = 3;
	} else {
		field_name = argv[1];
		*consumed = 2;
	}

	field = kzalloc(sizeof(*field), GFP_KERNEL);
	if (!field)
		return ERR_PTR(-ENOMEM);

	len = strlen(field_name);
	array = strchr(field_name, '[');
	if (array)
		len -= strlen(array);
	else if (field_name[len - 1] == ';')
		len--;

	field->name = kmemdup_nul(field_name, len, GFP_KERNEL);
	if (!field->name) {
		ret = -ENOMEM;
		goto free;
	}

	if (field_type[0] == ';')
		field_type++;
	len = strlen(field_type) + 1;
	if (array)
		len += strlen(array);
	if (prefix)
		len += strlen(prefix);

	field->type = kzalloc(len, GFP_KERNEL);
	if (!field->type) {
		ret = -ENOMEM;
		goto free;
	}
	if (prefix)
		strcat(field->type, prefix);
	strcat(field->type, field_type);
	if (array) {
		strcat(field->type, array);
		if (field->type[len - 1] == ';')
			field->type[len - 1] = '\0';
	}

	field->size = synth_field_size(field->type);
	if (!field->size) {
		ret = -EINVAL;
		goto free;
	}

	if (synth_field_is_string(field->type))
		field->is_string = true;

	field->is_signed = synth_field_signed(field->type);

 out:
	return field;
 free:
	free_synth_field(field);
	field = ERR_PTR(ret);
	goto out;
}

static void free_synth_tracepoint(struct tracepoint *tp)
{
	if (!tp)
		return;

	kfree(tp->name);
	kfree(tp);
}

static struct tracepoint *alloc_synth_tracepoint(char *name)
{
	struct tracepoint *tp;

	tp = kzalloc(sizeof(*tp), GFP_KERNEL);
	if (!tp)
		return ERR_PTR(-ENOMEM);

	tp->name = kstrdup(name, GFP_KERNEL);
	if (!tp->name) {
		kfree(tp);
		return ERR_PTR(-ENOMEM);
	}

	return tp;
}

typedef void (*synth_probe_func_t) (void *__data, u64 *var_ref_vals,
				    unsigned int *var_ref_idx);

static inline void trace_synth(struct synth_event *event, u64 *var_ref_vals,
			       unsigned int *var_ref_idx)
{
	struct tracepoint *tp = event->tp;

	if (unlikely(atomic_read(&tp->key.enabled) > 0)) {
		struct tracepoint_func *probe_func_ptr;
		synth_probe_func_t probe_func;
		void *__data;

		if (!(cpu_online(raw_smp_processor_id())))
			return;

		probe_func_ptr = rcu_dereference_sched((tp)->funcs);
		if (probe_func_ptr) {
			do {
				probe_func = probe_func_ptr->func;
				__data = probe_func_ptr->data;
				probe_func(__data, var_ref_vals, var_ref_idx);
			} while ((++probe_func_ptr)->func);
		}
	}
}

static struct synth_event *find_synth_event(const char *name)
{
	struct dyn_event *pos;
	struct synth_event *event;

	for_each_dyn_event(pos) {
		if (!is_synth_event(pos))
			continue;
		event = to_synth_event(pos);
		if (strcmp(event->name, name) == 0)
			return event;
	}

	return NULL;
}

static struct trace_event_fields synth_event_fields_array[] = {
	{ .type = TRACE_FUNCTION_TYPE,
	  .define_fields = synth_event_define_fields },
	{}
};

static int register_synth_event(struct synth_event *event)
{
	struct trace_event_call *call = &event->call;
	int ret = 0;

	event->call.class = &event->class;
	event->class.system = kstrdup(SYNTH_SYSTEM, GFP_KERNEL);
	if (!event->class.system) {
		ret = -ENOMEM;
		goto out;
	}

	event->tp = alloc_synth_tracepoint(event->name);
	if (IS_ERR(event->tp)) {
		ret = PTR_ERR(event->tp);
		event->tp = NULL;
		goto out;
	}

	INIT_LIST_HEAD(&call->class->fields);
	call->event.funcs = &synth_event_funcs;
	call->class->fields_array = synth_event_fields_array;

	ret = register_trace_event(&call->event);
	if (!ret) {
		ret = -ENODEV;
		goto out;
	}
	call->flags = TRACE_EVENT_FL_TRACEPOINT;
	call->class->reg = trace_event_reg;
	call->class->probe = trace_event_raw_event_synth;
	call->data = event;
	call->tp = event->tp;

	ret = trace_add_event_call(call);
	if (ret) {
		pr_warn("Failed to register synthetic event: %s\n",
			trace_event_name(call));
		goto err;
	}

	ret = set_synth_event_print_fmt(call);
	if (ret < 0) {
		trace_remove_event_call(call);
		goto err;
	}
 out:
	return ret;
 err:
	unregister_trace_event(&call->event);
	goto out;
}

static int unregister_synth_event(struct synth_event *event)
{
	struct trace_event_call *call = &event->call;
	int ret;

	ret = trace_remove_event_call(call);

	return ret;
}

static void free_synth_event(struct synth_event *event)
{
	unsigned int i;

	if (!event)
		return;

	for (i = 0; i < event->n_fields; i++)
		free_synth_field(event->fields[i]);

	kfree(event->fields);
	kfree(event->name);
	kfree(event->class.system);
	free_synth_tracepoint(event->tp);
	free_synth_event_print_fmt(&event->call);
	kfree(event);
}

static struct synth_event *alloc_synth_event(const char *name, int n_fields,
					     struct synth_field **fields)
{
	struct synth_event *event;
	unsigned int i;

	event = kzalloc(sizeof(*event), GFP_KERNEL);
	if (!event) {
		event = ERR_PTR(-ENOMEM);
		goto out;
	}

	event->name = kstrdup(name, GFP_KERNEL);
	if (!event->name) {
		kfree(event);
		event = ERR_PTR(-ENOMEM);
		goto out;
	}

	event->fields = kcalloc(n_fields, sizeof(*event->fields), GFP_KERNEL);
	if (!event->fields) {
		free_synth_event(event);
		event = ERR_PTR(-ENOMEM);
		goto out;
	}

	dyn_event_init(&event->devent, &synth_event_ops);

	for (i = 0; i < n_fields; i++)
		event->fields[i] = fields[i];

	event->n_fields = n_fields;
 out:
	return event;
}

static void action_trace(struct hist_trigger_data *hist_data,
			 struct tracing_map_elt *elt, void *rec,
			 struct ring_buffer_event *rbe, void *key,
			 struct action_data *data, u64 *var_ref_vals)
{
	struct synth_event *event = data->synth_event;

	trace_synth(event, var_ref_vals, data->var_ref_idx);
}

struct hist_var_data {
	struct list_head list;
	struct hist_trigger_data *hist_data;
};

static int synth_event_check_arg_fn(void *data)
{
	struct dynevent_arg_pair *arg_pair = data;
	int size;

	size = synth_field_size((char *)arg_pair->lhs);

	return size ? 0 : -EINVAL;
}

/**
 * synth_event_add_field - Add a new field to a synthetic event cmd
 * @cmd: A pointer to the dynevent_cmd struct representing the new event
 * @type: The type of the new field to add
 * @name: The name of the new field to add
 *
 * Add a new field to a synthetic event cmd object.  Field ordering is in
 * the same order the fields are added.
 *
 * See synth_field_size() for available types. If field_name contains
 * [n] the field is considered to be an array.
 *
 * Return: 0 if successful, error otherwise.
 */
int synth_event_add_field(struct dynevent_cmd *cmd, const char *type,
			  const char *name)
{
	struct dynevent_arg_pair arg_pair;
	int ret;

	if (cmd->type != DYNEVENT_TYPE_SYNTH)
		return -EINVAL;

	if (!type || !name)
		return -EINVAL;

	dynevent_arg_pair_init(&arg_pair, 0, ';');

	arg_pair.lhs = type;
	arg_pair.rhs = name;

	ret = dynevent_arg_pair_add(cmd, &arg_pair, synth_event_check_arg_fn);
	if (ret)
		return ret;

	if (++cmd->n_fields > SYNTH_FIELDS_MAX)
		ret = -EINVAL;

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_add_field);

/**
 * synth_event_add_field_str - Add a new field to a synthetic event cmd
 * @cmd: A pointer to the dynevent_cmd struct representing the new event
 * @type_name: The type and name of the new field to add, as a single string
 *
 * Add a new field to a synthetic event cmd object, as a single
 * string.  The @type_name string is expected to be of the form 'type
 * name', which will be appended by ';'.  No sanity checking is done -
 * what's passed in is assumed to already be well-formed.  Field
 * ordering is in the same order the fields are added.
 *
 * See synth_field_size() for available types. If field_name contains
 * [n] the field is considered to be an array.
 *
 * Return: 0 if successful, error otherwise.
 */
int synth_event_add_field_str(struct dynevent_cmd *cmd, const char *type_name)
{
	struct dynevent_arg arg;
	int ret;

	if (cmd->type != DYNEVENT_TYPE_SYNTH)
		return -EINVAL;

	if (!type_name)
		return -EINVAL;

	dynevent_arg_init(&arg, ';');

	arg.str = type_name;

	ret = dynevent_arg_add(cmd, &arg, NULL);
	if (ret)
		return ret;

	if (++cmd->n_fields > SYNTH_FIELDS_MAX)
		ret = -EINVAL;

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_add_field_str);

/**
 * synth_event_add_fields - Add multiple fields to a synthetic event cmd
 * @cmd: A pointer to the dynevent_cmd struct representing the new event
 * @fields: An array of type/name field descriptions
 * @n_fields: The number of field descriptions contained in the fields array
 *
 * Add a new set of fields to a synthetic event cmd object.  The event
 * fields that will be defined for the event should be passed in as an
 * array of struct synth_field_desc, and the number of elements in the
 * array passed in as n_fields.  Field ordering will retain the
 * ordering given in the fields array.
 *
 * See synth_field_size() for available types. If field_name contains
 * [n] the field is considered to be an array.
 *
 * Return: 0 if successful, error otherwise.
 */
int synth_event_add_fields(struct dynevent_cmd *cmd,
			   struct synth_field_desc *fields,
			   unsigned int n_fields)
{
	unsigned int i;
	int ret = 0;

	for (i = 0; i < n_fields; i++) {
		if (fields[i].type == NULL || fields[i].name == NULL) {
			ret = -EINVAL;
			break;
		}

		ret = synth_event_add_field(cmd, fields[i].type, fields[i].name);
		if (ret)
			break;
	}

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_add_fields);

/**
 * __synth_event_gen_cmd_start - Start a synthetic event command from arg list
 * @cmd: A pointer to the dynevent_cmd struct representing the new event
 * @name: The name of the synthetic event
 * @mod: The module creating the event, NULL if not created from a module
 * @args: Variable number of arg (pairs), one pair for each field
 *
 * NOTE: Users normally won't want to call this function directly, but
 * rather use the synth_event_gen_cmd_start() wrapper, which
 * automatically adds a NULL to the end of the arg list.  If this
 * function is used directly, make sure the last arg in the variable
 * arg list is NULL.
 *
 * Generate a synthetic event command to be executed by
 * synth_event_gen_cmd_end().  This function can be used to generate
 * the complete command or only the first part of it; in the latter
 * case, synth_event_add_field(), synth_event_add_field_str(), or
 * synth_event_add_fields() can be used to add more fields following
 * this.
 *
 * There should be an even number variable args, each pair consisting
 * of a type followed by a field name.
 *
 * See synth_field_size() for available types. If field_name contains
 * [n] the field is considered to be an array.
 *
 * Return: 0 if successful, error otherwise.
 */
int __synth_event_gen_cmd_start(struct dynevent_cmd *cmd, const char *name,
				struct module *mod, ...)
{
	struct dynevent_arg arg;
	va_list args;
	int ret;

	cmd->event_name = name;
	cmd->private_data = mod;

	if (cmd->type != DYNEVENT_TYPE_SYNTH)
		return -EINVAL;

	dynevent_arg_init(&arg, 0);
	arg.str = name;
	ret = dynevent_arg_add(cmd, &arg, NULL);
	if (ret)
		return ret;

	va_start(args, mod);
	for (;;) {
		const char *type, *name;

		type = va_arg(args, const char *);
		if (!type)
			break;
		name = va_arg(args, const char *);
		if (!name)
			break;

		if (++cmd->n_fields > SYNTH_FIELDS_MAX) {
			ret = -EINVAL;
			break;
		}

		ret = synth_event_add_field(cmd, type, name);
		if (ret)
			break;
	}
	va_end(args);

	return ret;
}
EXPORT_SYMBOL_GPL(__synth_event_gen_cmd_start);

/**
 * synth_event_gen_cmd_array_start - Start synthetic event command from an array
 * @cmd: A pointer to the dynevent_cmd struct representing the new event
 * @name: The name of the synthetic event
 * @fields: An array of type/name field descriptions
 * @n_fields: The number of field descriptions contained in the fields array
 *
 * Generate a synthetic event command to be executed by
 * synth_event_gen_cmd_end().  This function can be used to generate
 * the complete command or only the first part of it; in the latter
 * case, synth_event_add_field(), synth_event_add_field_str(), or
 * synth_event_add_fields() can be used to add more fields following
 * this.
 *
 * The event fields that will be defined for the event should be
 * passed in as an array of struct synth_field_desc, and the number of
 * elements in the array passed in as n_fields.  Field ordering will
 * retain the ordering given in the fields array.
 *
 * See synth_field_size() for available types. If field_name contains
 * [n] the field is considered to be an array.
 *
 * Return: 0 if successful, error otherwise.
 */
int synth_event_gen_cmd_array_start(struct dynevent_cmd *cmd, const char *name,
				    struct module *mod,
				    struct synth_field_desc *fields,
				    unsigned int n_fields)
{
	struct dynevent_arg arg;
	unsigned int i;
	int ret = 0;

	cmd->event_name = name;
	cmd->private_data = mod;

	if (cmd->type != DYNEVENT_TYPE_SYNTH)
		return -EINVAL;

	if (n_fields > SYNTH_FIELDS_MAX)
		return -EINVAL;

	dynevent_arg_init(&arg, 0);
	arg.str = name;
	ret = dynevent_arg_add(cmd, &arg, NULL);
	if (ret)
		return ret;

	for (i = 0; i < n_fields; i++) {
		if (fields[i].type == NULL || fields[i].name == NULL)
			return -EINVAL;

		ret = synth_event_add_field(cmd, fields[i].type, fields[i].name);
		if (ret)
			break;
	}

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_gen_cmd_array_start);

static int __create_synth_event(int argc, const char *name, const char **argv)
{
	struct synth_field *field, *fields[SYNTH_FIELDS_MAX];
	struct synth_event *event = NULL;
	int i, consumed = 0, n_fields = 0, ret = 0;

	/*
	 * Argument syntax:
	 *  - Add synthetic event: <event_name> field[;field] ...
	 *  - Remove synthetic event: !<event_name> field[;field] ...
	 *      where 'field' = type field_name
	 */

	if (name[0] == '\0' || argc < 1)
		return -EINVAL;

	mutex_lock(&event_mutex);

	event = find_synth_event(name);
	if (event) {
		ret = -EEXIST;
		goto out;
	}

	for (i = 0; i < argc - 1; i++) {
		if (strcmp(argv[i], ";") == 0)
			continue;
		if (n_fields == SYNTH_FIELDS_MAX) {
			ret = -EINVAL;
			goto err;
		}

		field = parse_synth_field(argc - i, &argv[i], &consumed);
		if (IS_ERR(field)) {
			ret = PTR_ERR(field);
			goto err;
		}
		fields[n_fields++] = field;
		i += consumed - 1;
	}

	if (i < argc && strcmp(argv[i], ";") != 0) {
		ret = -EINVAL;
		goto err;
	}

	event = alloc_synth_event(name, n_fields, fields);
	if (IS_ERR(event)) {
		ret = PTR_ERR(event);
		event = NULL;
		goto err;
	}
	ret = register_synth_event(event);
	if (!ret)
		dyn_event_add(&event->devent);
	else
		free_synth_event(event);
 out:
	mutex_unlock(&event_mutex);

	return ret;
 err:
	for (i = 0; i < n_fields; i++)
		free_synth_field(fields[i]);

	goto out;
}

/**
 * synth_event_create - Create a new synthetic event
 * @name: The name of the new sythetic event
 * @fields: An array of type/name field descriptions
 * @n_fields: The number of field descriptions contained in the fields array
 * @mod: The module creating the event, NULL if not created from a module
 *
 * Create a new synthetic event with the given name under the
 * trace/events/synthetic/ directory.  The event fields that will be
 * defined for the event should be passed in as an array of struct
 * synth_field_desc, and the number elements in the array passed in as
 * n_fields. Field ordering will retain the ordering given in the
 * fields array.
 *
 * If the new synthetic event is being created from a module, the mod
 * param must be non-NULL.  This will ensure that the trace buffer
 * won't contain unreadable events.
 *
 * The new synth event should be deleted using synth_event_delete()
 * function.  The new synthetic event can be generated from modules or
 * other kernel code using trace_synth_event() and related functions.
 *
 * Return: 0 if successful, error otherwise.
 */
int synth_event_create(const char *name, struct synth_field_desc *fields,
		       unsigned int n_fields, struct module *mod)
{
	struct dynevent_cmd cmd;
	char *buf;
	int ret;

	buf = kzalloc(MAX_DYNEVENT_CMD_LEN, GFP_KERNEL);
	if (!buf)
		return -ENOMEM;

	synth_event_cmd_init(&cmd, buf, MAX_DYNEVENT_CMD_LEN);

	ret = synth_event_gen_cmd_array_start(&cmd, name, mod,
					      fields, n_fields);
	if (ret)
		goto out;

	ret = synth_event_gen_cmd_end(&cmd);
 out:
	kfree(buf);

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_create);

static int destroy_synth_event(struct synth_event *se)
{
	int ret;

	if (se->ref)
		ret = -EBUSY;
	else {
		ret = unregister_synth_event(se);
		if (!ret) {
			dyn_event_remove(&se->devent);
			free_synth_event(se);
		}
	}

	return ret;
}

/**
 * synth_event_delete - Delete a synthetic event
 * @event_name: The name of the new sythetic event
 *
 * Delete a synthetic event that was created with synth_event_create().
 *
 * Return: 0 if successful, error otherwise.
 */
int synth_event_delete(const char *event_name)
{
	struct synth_event *se = NULL;
	struct module *mod = NULL;
	int ret = -ENOENT;

	mutex_lock(&event_mutex);
	se = find_synth_event(event_name);
	if (se) {
		mod = se->mod;
		ret = destroy_synth_event(se);
	}
	mutex_unlock(&event_mutex);

	if (mod) {
		mutex_lock(&trace_types_lock);
		/*
		 * It is safest to reset the ring buffer if the module
		 * being unloaded registered any events that were
		 * used. The only worry is if a new module gets
		 * loaded, and takes on the same id as the events of
		 * this module. When printing out the buffer, traced
		 * events left over from this module may be passed to
		 * the new module events and unexpected results may
		 * occur.
		 */
		tracing_reset_all_online_cpus();
		mutex_unlock(&trace_types_lock);
	}

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_delete);

static int create_or_delete_synth_event(int argc, char **argv)
{
	const char *name = argv[0];
	int ret;

	/* trace_run_command() ensures argc != 0 */
	if (name[0] == '!') {
		ret = synth_event_delete(name + 1);
		return ret;
	}

	ret = __create_synth_event(argc - 1, name, (const char **)argv + 1);
	return ret == -ECANCELED ? -EINVAL : ret;
}

static int synth_event_run_command(struct dynevent_cmd *cmd)
{
	struct synth_event *se;
	int ret;

	ret = trace_run_command(cmd->seq.buffer, create_or_delete_synth_event);
	if (ret)
		return ret;

	se = find_synth_event(cmd->event_name);
	if (WARN_ON(!se))
		return -ENOENT;

	se->mod = cmd->private_data;

	return ret;
}

/**
 * synth_event_cmd_init - Initialize a synthetic event command object
 * @cmd: A pointer to the dynevent_cmd struct representing the new event
 * @buf: A pointer to the buffer used to build the command
 * @maxlen: The length of the buffer passed in @buf
 *
 * Initialize a synthetic event command object.  Use this before
 * calling any of the other dyenvent_cmd functions.
 */
void synth_event_cmd_init(struct dynevent_cmd *cmd, char *buf, int maxlen)
{
	dynevent_cmd_init(cmd, buf, maxlen, DYNEVENT_TYPE_SYNTH,
			  synth_event_run_command);
}
EXPORT_SYMBOL_GPL(synth_event_cmd_init);

/**
 * synth_event_trace - Trace a synthetic event
 * @file: The trace_event_file representing the synthetic event
 * @n_vals: The number of values in vals
 * @args: Variable number of args containing the event values
 *
 * Trace a synthetic event using the values passed in the variable
 * argument list.
 *
 * The argument list should be a list 'n_vals' u64 values.  The number
 * of vals must match the number of field in the synthetic event, and
 * must be in the same order as the synthetic event fields.
 *
 * All vals should be cast to u64, and string vals are just pointers
 * to strings, cast to u64.  Strings will be copied into space
 * reserved in the event for the string, using these pointers.
 *
 * Return: 0 on success, err otherwise.
 */
int synth_event_trace(struct trace_event_file *file, unsigned int n_vals, ...)
{
	struct trace_event_buffer fbuffer;
	struct synth_trace_event *entry;
	struct trace_buffer *buffer;
	struct synth_event *event;
	unsigned int i, n_u64;
	int fields_size = 0;
	va_list args;
	int ret = 0;

	/*
	 * Normal event generation doesn't get called at all unless
	 * the ENABLED bit is set (which attaches the probe thus
	 * allowing this code to be called, etc).  Because this is
	 * called directly by the user, we don't have that but we
	 * still need to honor not logging when disabled.
	 */
	if (!(file->flags & EVENT_FILE_FL_ENABLED))
		return 0;

	event = file->event_call->data;

	if (n_vals != event->n_fields)
		return -EINVAL;

	if (trace_trigger_soft_disabled(file))
		return -EINVAL;

	fields_size = event->n_u64 * sizeof(u64);

	/*
	 * Avoid ring buffer recursion detection, as this event
	 * is being performed within another event.
	 */
	buffer = file->tr->array_buffer.buffer;
	ring_buffer_nest_start(buffer);

	entry = trace_event_buffer_reserve(&fbuffer, file,
					   sizeof(*entry) + fields_size);
	if (!entry) {
		ret = -EINVAL;
		goto out;
	}

	va_start(args, n_vals);
	for (i = 0, n_u64 = 0; i < event->n_fields; i++) {
		u64 val;

		val = va_arg(args, u64);

		if (event->fields[i]->is_string) {
			char *str_val = (char *)(long)val;
			char *str_field = (char *)&entry->fields[n_u64];

			strscpy(str_field, str_val, STR_VAR_LEN_MAX);
			n_u64 += STR_VAR_LEN_MAX / sizeof(u64);
		} else {
			entry->fields[n_u64] = val;
			n_u64++;
		}
	}
	va_end(args);

	trace_event_buffer_commit(&fbuffer);
out:
	ring_buffer_nest_end(buffer);

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_trace);

/**
 * synth_event_trace_array - Trace a synthetic event from an array
 * @file: The trace_event_file representing the synthetic event
 * @vals: Array of values
 * @n_vals: The number of values in vals
 *
 * Trace a synthetic event using the values passed in as 'vals'.
 *
 * The 'vals' array is just an array of 'n_vals' u64.  The number of
 * vals must match the number of field in the synthetic event, and
 * must be in the same order as the synthetic event fields.
 *
 * All vals should be cast to u64, and string vals are just pointers
 * to strings, cast to u64.  Strings will be copied into space
 * reserved in the event for the string, using these pointers.
 *
 * Return: 0 on success, err otherwise.
 */
int synth_event_trace_array(struct trace_event_file *file, u64 *vals,
			    unsigned int n_vals)
{
	struct trace_event_buffer fbuffer;
	struct synth_trace_event *entry;
	struct trace_buffer *buffer;
	struct synth_event *event;
	unsigned int i, n_u64;
	int fields_size = 0;
	int ret = 0;

	/*
	 * Normal event generation doesn't get called at all unless
	 * the ENABLED bit is set (which attaches the probe thus
	 * allowing this code to be called, etc).  Because this is
	 * called directly by the user, we don't have that but we
	 * still need to honor not logging when disabled.
	 */
	if (!(file->flags & EVENT_FILE_FL_ENABLED))
		return 0;

	event = file->event_call->data;

	if (n_vals != event->n_fields)
		return -EINVAL;

	if (trace_trigger_soft_disabled(file))
		return -EINVAL;

	fields_size = event->n_u64 * sizeof(u64);

	/*
	 * Avoid ring buffer recursion detection, as this event
	 * is being performed within another event.
	 */
	buffer = file->tr->array_buffer.buffer;
	ring_buffer_nest_start(buffer);

	entry = trace_event_buffer_reserve(&fbuffer, file,
					   sizeof(*entry) + fields_size);
	if (!entry) {
		ret = -EINVAL;
		goto out;
	}

	for (i = 0, n_u64 = 0; i < event->n_fields; i++) {
		if (event->fields[i]->is_string) {
			char *str_val = (char *)(long)vals[i];
			char *str_field = (char *)&entry->fields[n_u64];

			strscpy(str_field, str_val, STR_VAR_LEN_MAX);
			n_u64 += STR_VAR_LEN_MAX / sizeof(u64);
		} else {
			entry->fields[n_u64] = vals[i];
			n_u64++;
		}
	}

	trace_event_buffer_commit(&fbuffer);
out:
	ring_buffer_nest_end(buffer);

	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_trace_array);

/**
 * synth_event_trace_start - Start piecewise synthetic event trace
 * @file: The trace_event_file representing the synthetic event
 * @trace_state: A pointer to object tracking the piecewise trace state
 *
 * Start the trace of a synthetic event field-by-field rather than all
 * at once.
 *
 * This function 'opens' an event trace, which means space is reserved
 * for the event in the trace buffer, after which the event's
 * individual field values can be set through either
 * synth_event_add_next_val() or synth_event_add_val().
 *
 * A pointer to a trace_state object is passed in, which will keep
 * track of the current event trace state until the event trace is
 * closed (and the event finally traced) using
 * synth_event_trace_end().
 *
 * Note that synth_event_trace_end() must be called after all values
 * have been added for each event trace, regardless of whether adding
 * all field values succeeded or not.
 *
 * Note also that for a given event trace, all fields must be added
 * using either synth_event_add_next_val() or synth_event_add_val()
 * but not both together or interleaved.
 *
 * Return: 0 on success, err otherwise.
 */
int synth_event_trace_start(struct trace_event_file *file,
			    struct synth_event_trace_state *trace_state)
{
	struct synth_trace_event *entry;
	int fields_size = 0;
	int ret = 0;

	if (!trace_state) {
		ret = -EINVAL;
		goto out;
	}

	memset(trace_state, '\0', sizeof(*trace_state));

	/*
	 * Normal event tracing doesn't get called at all unless the
	 * ENABLED bit is set (which attaches the probe thus allowing
	 * this code to be called, etc).  Because this is called
	 * directly by the user, we don't have that but we still need
	 * to honor not logging when disabled.  For the the iterated
	 * trace case, we save the enabed state upon start and just
	 * ignore the following data calls.
	 */
	if (!(file->flags & EVENT_FILE_FL_ENABLED)) {
		trace_state->enabled = false;
		goto out;
	}

	trace_state->enabled = true;

	trace_state->event = file->event_call->data;

	if (trace_trigger_soft_disabled(file)) {
		ret = -EINVAL;
		goto out;
	}

	fields_size = trace_state->event->n_u64 * sizeof(u64);

	/*
	 * Avoid ring buffer recursion detection, as this event
	 * is being performed within another event.
	 */
	trace_state->buffer = file->tr->array_buffer.buffer;
	ring_buffer_nest_start(trace_state->buffer);

	entry = trace_event_buffer_reserve(&trace_state->fbuffer, file,
					   sizeof(*entry) + fields_size);
	if (!entry) {
		ret = -EINVAL;
		goto out;
	}

	trace_state->entry = entry;
out:
	return ret;
}
EXPORT_SYMBOL_GPL(synth_event_trace_start);

static int __synth_event_add_val(const char *field_name, u64 val,
				 struct synth_event_trace_state *trace_state)
{
	struct synth_field *field = NULL;
	struct synth_trace_event *entry;
	struct synth_event *event;
	int i, ret = 0;

	if (!trace_state) {
		ret = -EINVAL;
		goto out;
	}

	/* can't mix add_next_synth_val() with add_synth_val() */
	if (field_name) {
		if (trace_state->add_next) {
			ret = -EINVAL;
			goto out;
		}
		trace_state->add_name = true;
	} else {
		if (trace_state->add_name) {
			ret = -EINVAL;
			goto out;
		}
		trace_state->add_next = true;
	}

	if (!trace_state->enabled)
		goto out;

	event = trace_state->event;
	if (trace_state->add_name) {
		for (i = 0; i < event->n_fields; i++) {
			field = event->fields[i];
			if (strcmp(field->name, field_name) == 0)
				break;
		}
		if (!field) {
			ret = -EINVAL;
			goto out;
		}
	} else {
		if (trace_state->cur_field >= event->n_fields) {
			ret = -EINVAL;
			goto out;
		}
		field = event->fields[trace_state->cur_field++];
	}

	entry = trace_state->entry;
	if (field->is_string) {
		char *str_val = (char *)(long)val;
		char *str_field;

		if (!str_val) {
			ret = -EINVAL;
			goto out;
		}

		str_field = (char *)&entry->fields[field->offset];
		strscpy(str_field, str_val, STR_VAR_LEN_MAX);
	} else
		entry->fields[field->offset] = val;
 out:
	return ret;
}

/**
 * synth_event_add_next_val - Add the next field's value to an open synth trace
 * @val: The value to set the next field to
 * @trace_state: A pointer to object tracking the piecewise trace state
 *
 * Set the value of the next field in an event that's been opened by
 * synth_event_trace_start().
 *
 * The val param should be the value cast to u64.  If the value points
 * to a string, the val param should be a char * cast to u64.
 *
 * This function assumes all the fields in an event are to be set one
 * after another - successive calls to this function are made, one for
 * each field, in the order of the fields in the event, until all
 * fields have been set.  If you'd rather set each field individually
 * without regard to ordering, synth_event_add_val() can be used
 * instead.
 *
 * Note however that synth_event_add_next_val() and
 * synth_event_add_val() can't be intermixed for a given event trace -
 * one or the other but not both can be used at the same time.
 *
 * Note also that synth_event_trace_end() must be called after all
 * values have been added for each event trace, regardless of whether
 * adding all field values succeeded or not.
 *
 * Return: 0 on success, err otherwise.
 */
int synth_event_add_next_val(u64 val,
			     struct synth_event_trace_state *trace_state)
{
	return __synth_event_add_val(NULL, val, trace_state);
}
EXPORT_SYMBOL_GPL(synth_event_add_next_val);

/**
 * synth_event_add_val - Add a named field's value to an open synth trace
 * @field_name: The name of the synthetic event field value to set
 * @val: The value to set the next field to
 * @trace_state: A pointer to object tracking the piecewise trace state
 *
 * Set the value of the named field in an event that's been opened by
 * synth_event_trace_start().
 *
 * The val param should be the value cast to u64.  If the value points
 * to a string, the val param should be a char * cast to u64.
 *
 * This function looks up the field name, and if found, sets the field
 * to the specified value.  This lookup makes this function more
 * expensive than synth_event_add_next_val(), so use that or the
 * none-piecewise synth_event_trace() instead if efficiency is more
 * important.
 *
 * Note however that synth_event_add_next_val() and
 * synth_event_add_val() can't be intermixed for a given event trace -
 * one or the other but not both can be used at the same time.
 *
 * Note also that synth_event_trace_end() must be called after all
 * values have been added for each event trace, regardless of whether
 * adding all field values succeeded or not.
 *
 * Return: 0 on success, err otherwise.
 */
int synth_event_add_val(const char *field_name, u64 val,
			struct synth_event_trace_state *trace_state)
{
	return __synth_event_add_val(field_name, val, trace_state);
}
EXPORT_SYMBOL_GPL(synth_event_add_val);

/**
 * synth_event_trace_end - End piecewise synthetic event trace
 * @trace_state: A pointer to object tracking the piecewise trace state
 *
 * End the trace of a synthetic event opened by
 * synth_event_trace__start().
 *
 * This function 'closes' an event trace, which basically means that
 * it commits the reserved event and cleans up other loose ends.
 *
 * A pointer to a trace_state object is passed in, which will keep
 * track of the current event trace state opened with
 * synth_event_trace_start().
 *
 * Note that this function must be called after all values have been
 * added for each event trace, regardless of whether adding all field
 * values succeeded or not.
 *
 * Return: 0 on success, err otherwise.
 */
int synth_event_trace_end(struct synth_event_trace_state *trace_state)
{
	if (!trace_state)
		return -EINVAL;

	trace_event_buffer_commit(&trace_state->fbuffer);

	ring_buffer_nest_end(trace_state->buffer);

	return 0;
}
EXPORT_SYMBOL_GPL(synth_event_trace_end);

static int create_synth_event(int argc, const char **argv)
{
	const char *name = argv[0];
	int len;

	if (name[0] != 's' || name[1] != ':')
		return -ECANCELED;
	name += 2;

	/* This interface accepts group name prefix */
	if (strchr(name, '/')) {
		len = str_has_prefix(name, SYNTH_SYSTEM "/");
		if (len == 0)
			return -EINVAL;
		name += len;
	}
	return __create_synth_event(argc - 1, name, argv + 1);
}

static int synth_event_release(struct dyn_event *ev)
{
	struct synth_event *event = to_synth_event(ev);
	int ret;

	if (event->ref)
		return -EBUSY;

	ret = unregister_synth_event(event);
	if (ret)
		return ret;

	dyn_event_remove(ev);
	free_synth_event(event);
	return 0;
}

static int __synth_event_show(struct seq_file *m, struct synth_event *event)
{
	struct synth_field *field;
	unsigned int i;

	seq_printf(m, "%s\t", event->name);

	for (i = 0; i < event->n_fields; i++) {
		field = event->fields[i];

		/* parameter values */
		seq_printf(m, "%s %s%s", field->type, field->name,
			   i == event->n_fields - 1 ? "" : "; ");
	}

	seq_putc(m, '\n');

	return 0;
}

static int synth_event_show(struct seq_file *m, struct dyn_event *ev)
{
	struct synth_event *event = to_synth_event(ev);

	seq_printf(m, "s:%s/", event->class.system);

	return __synth_event_show(m, event);
}

static int synth_events_seq_show(struct seq_file *m, void *v)
{
	struct dyn_event *ev = v;

	if (!is_synth_event(ev))
		return 0;

	return __synth_event_show(m, to_synth_event(ev));
}

static const struct seq_operations synth_events_seq_op = {
	.start	= dyn_event_seq_start,
	.next	= dyn_event_seq_next,
	.stop	= dyn_event_seq_stop,
	.show	= synth_events_seq_show,
};

static int synth_events_open(struct inode *inode, struct file *file)
{
	int ret;

	ret = security_locked_down(LOCKDOWN_TRACEFS);
	if (ret)
		return ret;

	if ((file->f_mode & FMODE_WRITE) && (file->f_flags & O_TRUNC)) {
		ret = dyn_events_release_all(&synth_event_ops);
		if (ret < 0)
			return ret;
	}

	return seq_open(file, &synth_events_seq_op);
}

static ssize_t synth_events_write(struct file *file,
				  const char __user *buffer,
				  size_t count, loff_t *ppos)
{
	return trace_parse_run_command(file, buffer, count, ppos,
				       create_or_delete_synth_event);
}

static const struct file_operations synth_events_fops = {
	.open           = synth_events_open,
	.write		= synth_events_write,
	.read           = seq_read,
	.llseek         = seq_lseek,
	.release        = seq_release,
};

static u64 hist_field_timestamp(struct hist_field *hist_field,
				struct tracing_map_elt *elt,
				struct ring_buffer_event *rbe,
				void *event)
{
	struct hist_trigger_data *hist_data = hist_field->hist_data;
	struct trace_array *tr = hist_data->event_file->tr;

	u64 ts = ring_buffer_event_time_stamp(rbe);

	if (hist_data->attrs->ts_in_usecs && trace_clock_in_ns(tr))
		ts = ns2usecs(ts);

	return ts;
}

static u64 hist_field_cpu(struct hist_field *hist_field,
			  struct tracing_map_elt *elt,
			  struct ring_buffer_event *rbe,
			  void *event)
{
	int cpu = smp_processor_id();

	return cpu;
}

/**
 * check_field_for_var_ref - Check if a VAR_REF field references a variable
 * @hist_field: The VAR_REF field to check
 * @var_data: The hist trigger that owns the variable
 * @var_idx: The trigger variable identifier
 *
 * Check the given VAR_REF field to see whether or not it references
 * the given variable associated with the given trigger.
 *
 * Return: The VAR_REF field if it does reference the variable, NULL if not
 */
static struct hist_field *
check_field_for_var_ref(struct hist_field *hist_field,
			struct hist_trigger_data *var_data,
			unsigned int var_idx)
{
	WARN_ON(!(hist_field && hist_field->flags & HIST_FIELD_FL_VAR_REF));

	if (hist_field && hist_field->var.idx == var_idx &&
	    hist_field->var.hist_data == var_data)
		return hist_field;

	return NULL;
}

/**
 * find_var_ref - Check if a trigger has a reference to a trigger variable
 * @hist_data: The hist trigger that might have a reference to the variable
 * @var_data: The hist trigger that owns the variable
 * @var_idx: The trigger variable identifier
 *
 * Check the list of var_refs[] on the first hist trigger to see
 * whether any of them are references to the variable on the second
 * trigger.
 *
 * Return: The VAR_REF field referencing the variable if so, NULL if not
 */
static struct hist_field *find_var_ref(struct hist_trigger_data *hist_data,
				       struct hist_trigger_data *var_data,
				       unsigned int var_idx)
{
	struct hist_field *hist_field;
	unsigned int i;

	for (i = 0; i < hist_data->n_var_refs; i++) {
		hist_field = hist_data->var_refs[i];
		if (check_field_for_var_ref(hist_field, var_data, var_idx))
			return hist_field;
	}

	return NULL;
}

/**
 * find_any_var_ref - Check if there is a reference to a given trigger variable
 * @hist_data: The hist trigger
 * @var_idx: The trigger variable identifier
 *
 * Check to see whether the given variable is currently referenced by
 * any other trigger.
 *
 * The trigger the variable is defined on is explicitly excluded - the
 * assumption being that a self-reference doesn't prevent a trigger
 * from being removed.
 *
 * Return: The VAR_REF field referencing the variable if so, NULL if not
 */
static struct hist_field *find_any_var_ref(struct hist_trigger_data *hist_data,
					   unsigned int var_idx)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_field *found = NULL;
	struct hist_var_data *var_data;

	list_for_each_entry(var_data, &tr->hist_vars, list) {
		if (var_data->hist_data == hist_data)
			continue;
		found = find_var_ref(var_data->hist_data, hist_data, var_idx);
		if (found)
			break;
	}

	return found;
}

/**
 * check_var_refs - Check if there is a reference to any of trigger's variables
 * @hist_data: The hist trigger
 *
 * A trigger can define one or more variables.  If any one of them is
 * currently referenced by any other trigger, this function will
 * determine that.

 * Typically used to determine whether or not a trigger can be removed
 * - if there are any references to a trigger's variables, it cannot.
 *
 * Return: True if there is a reference to any of trigger's variables
 */
static bool check_var_refs(struct hist_trigger_data *hist_data)
{
	struct hist_field *field;
	bool found = false;
	int i;

	for_each_hist_field(i, hist_data) {
		field = hist_data->fields[i];
		if (field && field->flags & HIST_FIELD_FL_VAR) {
			if (find_any_var_ref(hist_data, field->var.idx)) {
				found = true;
				break;
			}
		}
	}

	return found;
}

static struct hist_var_data *find_hist_vars(struct hist_trigger_data *hist_data)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_var_data *var_data, *found = NULL;

	list_for_each_entry(var_data, &tr->hist_vars, list) {
		if (var_data->hist_data == hist_data) {
			found = var_data;
			break;
		}
	}

	return found;
}

static bool field_has_hist_vars(struct hist_field *hist_field,
				unsigned int level)
{
	int i;

	if (level > 3)
		return false;

	if (!hist_field)
		return false;

	if (hist_field->flags & HIST_FIELD_FL_VAR ||
	    hist_field->flags & HIST_FIELD_FL_VAR_REF)
		return true;

	for (i = 0; i < HIST_FIELD_OPERANDS_MAX; i++) {
		struct hist_field *operand;

		operand = hist_field->operands[i];
		if (field_has_hist_vars(operand, level + 1))
			return true;
	}

	return false;
}

static bool has_hist_vars(struct hist_trigger_data *hist_data)
{
	struct hist_field *hist_field;
	int i;

	for_each_hist_field(i, hist_data) {
		hist_field = hist_data->fields[i];
		if (field_has_hist_vars(hist_field, 0))
			return true;
	}

	return false;
}

static int save_hist_vars(struct hist_trigger_data *hist_data)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_var_data *var_data;

	var_data = find_hist_vars(hist_data);
	if (var_data)
		return 0;

	if (tracing_check_open_get_tr(tr))
		return -ENODEV;

	var_data = kzalloc(sizeof(*var_data), GFP_KERNEL);
	if (!var_data) {
		trace_array_put(tr);
		return -ENOMEM;
	}

	var_data->hist_data = hist_data;
	list_add(&var_data->list, &tr->hist_vars);

	return 0;
}

static void remove_hist_vars(struct hist_trigger_data *hist_data)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_var_data *var_data;

	var_data = find_hist_vars(hist_data);
	if (!var_data)
		return;

	if (WARN_ON(check_var_refs(hist_data)))
		return;

	list_del(&var_data->list);

	kfree(var_data);

	trace_array_put(tr);
}

static struct hist_field *find_var_field(struct hist_trigger_data *hist_data,
					 const char *var_name)
{
	struct hist_field *hist_field, *found = NULL;
	int i;

	for_each_hist_field(i, hist_data) {
		hist_field = hist_data->fields[i];
		if (hist_field && hist_field->flags & HIST_FIELD_FL_VAR &&
		    strcmp(hist_field->var.name, var_name) == 0) {
			found = hist_field;
			break;
		}
	}

	return found;
}

static struct hist_field *find_var(struct hist_trigger_data *hist_data,
				   struct trace_event_file *file,
				   const char *var_name)
{
	struct hist_trigger_data *test_data;
	struct event_trigger_data *test;
	struct hist_field *hist_field;

	lockdep_assert_held(&event_mutex);

	hist_field = find_var_field(hist_data, var_name);
	if (hist_field)
		return hist_field;

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			test_data = test->private_data;
			hist_field = find_var_field(test_data, var_name);
			if (hist_field)
				return hist_field;
		}
	}

	return NULL;
}

static struct trace_event_file *find_var_file(struct trace_array *tr,
					      char *system,
					      char *event_name,
					      char *var_name)
{
	struct hist_trigger_data *var_hist_data;
	struct hist_var_data *var_data;
	struct trace_event_file *file, *found = NULL;

	if (system)
		return find_event_file(tr, system, event_name);

	list_for_each_entry(var_data, &tr->hist_vars, list) {
		var_hist_data = var_data->hist_data;
		file = var_hist_data->event_file;
		if (file == found)
			continue;

		if (find_var_field(var_hist_data, var_name)) {
			if (found) {
				hist_err(tr, HIST_ERR_VAR_NOT_UNIQUE, errpos(var_name));
				return NULL;
			}

			found = file;
		}
	}

	return found;
}

static struct hist_field *find_file_var(struct trace_event_file *file,
					const char *var_name)
{
	struct hist_trigger_data *test_data;
	struct event_trigger_data *test;
	struct hist_field *hist_field;

	lockdep_assert_held(&event_mutex);

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			test_data = test->private_data;
			hist_field = find_var_field(test_data, var_name);
			if (hist_field)
				return hist_field;
		}
	}

	return NULL;
}

static struct hist_field *
find_match_var(struct hist_trigger_data *hist_data, char *var_name)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_field *hist_field, *found = NULL;
	struct trace_event_file *file;
	unsigned int i;

	for (i = 0; i < hist_data->n_actions; i++) {
		struct action_data *data = hist_data->actions[i];

		if (data->handler == HANDLER_ONMATCH) {
			char *system = data->match_data.event_system;
			char *event_name = data->match_data.event;

			file = find_var_file(tr, system, event_name, var_name);
			if (!file)
				continue;
			hist_field = find_file_var(file, var_name);
			if (hist_field) {
				if (found) {
					hist_err(tr, HIST_ERR_VAR_NOT_UNIQUE,
						 errpos(var_name));
					return ERR_PTR(-EINVAL);
				}

				found = hist_field;
			}
		}
	}
	return found;
}

static struct hist_field *find_event_var(struct hist_trigger_data *hist_data,
					 char *system,
					 char *event_name,
					 char *var_name)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_field *hist_field = NULL;
	struct trace_event_file *file;

	if (!system || !event_name) {
		hist_field = find_match_var(hist_data, var_name);
		if (IS_ERR(hist_field))
			return NULL;
		if (hist_field)
			return hist_field;
	}

	file = find_var_file(tr, system, event_name, var_name);
	if (!file)
		return NULL;

	hist_field = find_file_var(file, var_name);

	return hist_field;
}

static u64 hist_field_var_ref(struct hist_field *hist_field,
			      struct tracing_map_elt *elt,
			      struct ring_buffer_event *rbe,
			      void *event)
{
	struct hist_elt_data *elt_data;
	u64 var_val = 0;

	if (WARN_ON_ONCE(!elt))
		return var_val;

	elt_data = elt->private_data;
	var_val = elt_data->var_ref_vals[hist_field->var_ref_idx];

	return var_val;
}

static bool resolve_var_refs(struct hist_trigger_data *hist_data, void *key,
			     u64 *var_ref_vals, bool self)
{
	struct hist_trigger_data *var_data;
	struct tracing_map_elt *var_elt;
	struct hist_field *hist_field;
	unsigned int i, var_idx;
	bool resolved = true;
	u64 var_val = 0;

	for (i = 0; i < hist_data->n_var_refs; i++) {
		hist_field = hist_data->var_refs[i];
		var_idx = hist_field->var.idx;
		var_data = hist_field->var.hist_data;

		if (var_data == NULL) {
			resolved = false;
			break;
		}

		if ((self && var_data != hist_data) ||
		    (!self && var_data == hist_data))
			continue;

		var_elt = tracing_map_lookup(var_data->map, key);
		if (!var_elt) {
			resolved = false;
			break;
		}

		if (!tracing_map_var_set(var_elt, var_idx)) {
			resolved = false;
			break;
		}

		if (self || !hist_field->read_once)
			var_val = tracing_map_read_var(var_elt, var_idx);
		else
			var_val = tracing_map_read_var_once(var_elt, var_idx);

		var_ref_vals[i] = var_val;
	}

	return resolved;
}

static const char *hist_field_name(struct hist_field *field,
				   unsigned int level)
{
	const char *field_name = "";

	if (level > 1)
		return field_name;

	if (field->field)
		field_name = field->field->name;
	else if (field->flags & HIST_FIELD_FL_LOG2 ||
		 field->flags & HIST_FIELD_FL_ALIAS)
		field_name = hist_field_name(field->operands[0], ++level);
	else if (field->flags & HIST_FIELD_FL_CPU)
		field_name = "cpu";
	else if (field->flags & HIST_FIELD_FL_EXPR ||
		 field->flags & HIST_FIELD_FL_VAR_REF) {
		if (field->system) {
			static char full_name[MAX_FILTER_STR_VAL];

			strcat(full_name, field->system);
			strcat(full_name, ".");
			strcat(full_name, field->event_name);
			strcat(full_name, ".");
			strcat(full_name, field->name);
			field_name = full_name;
		} else
			field_name = field->name;
	} else if (field->flags & HIST_FIELD_FL_TIMESTAMP)
		field_name = "common_timestamp";

	if (field_name == NULL)
		field_name = "";

	return field_name;
}

static hist_field_fn_t select_value_fn(int field_size, int field_is_signed)
{
	hist_field_fn_t fn = NULL;

	switch (field_size) {
	case 8:
		if (field_is_signed)
			fn = hist_field_s64;
		else
			fn = hist_field_u64;
		break;
	case 4:
		if (field_is_signed)
			fn = hist_field_s32;
		else
			fn = hist_field_u32;
		break;
	case 2:
		if (field_is_signed)
			fn = hist_field_s16;
		else
			fn = hist_field_u16;
		break;
	case 1:
		if (field_is_signed)
			fn = hist_field_s8;
		else
			fn = hist_field_u8;
		break;
	}

	return fn;
}

static int parse_map_size(char *str)
{
	unsigned long size, map_bits;
	int ret;

	ret = kstrtoul(str, 0, &size);
	if (ret)
		goto out;

	map_bits = ilog2(roundup_pow_of_two(size));
	if (map_bits < TRACING_MAP_BITS_MIN ||
	    map_bits > TRACING_MAP_BITS_MAX)
		ret = -EINVAL;
	else
		ret = map_bits;
 out:
	return ret;
}

static void destroy_hist_trigger_attrs(struct hist_trigger_attrs *attrs)
{
	unsigned int i;

	if (!attrs)
		return;

	for (i = 0; i < attrs->n_assignments; i++)
		kfree(attrs->assignment_str[i]);

	for (i = 0; i < attrs->n_actions; i++)
		kfree(attrs->action_str[i]);

	kfree(attrs->name);
	kfree(attrs->sort_key_str);
	kfree(attrs->keys_str);
	kfree(attrs->vals_str);
	kfree(attrs->clock);
	kfree(attrs);
}

static int parse_action(char *str, struct hist_trigger_attrs *attrs)
{
	int ret = -EINVAL;

	if (attrs->n_actions >= HIST_ACTIONS_MAX)
		return ret;

	if ((str_has_prefix(str, "onmatch(")) ||
	    (str_has_prefix(str, "onmax(")) ||
	    (str_has_prefix(str, "onchange("))) {
		attrs->action_str[attrs->n_actions] = kstrdup(str, GFP_KERNEL);
		if (!attrs->action_str[attrs->n_actions]) {
			ret = -ENOMEM;
			return ret;
		}
		attrs->n_actions++;
		ret = 0;
	}
	return ret;
}

static int parse_assignment(struct trace_array *tr,
			    char *str, struct hist_trigger_attrs *attrs)
{
	int len, ret = 0;

	if ((len = str_has_prefix(str, "key=")) ||
	    (len = str_has_prefix(str, "keys="))) {
		attrs->keys_str = kstrdup(str + len, GFP_KERNEL);
		if (!attrs->keys_str) {
			ret = -ENOMEM;
			goto out;
		}
	} else if ((len = str_has_prefix(str, "val=")) ||
		   (len = str_has_prefix(str, "vals=")) ||
		   (len = str_has_prefix(str, "values="))) {
		attrs->vals_str = kstrdup(str + len, GFP_KERNEL);
		if (!attrs->vals_str) {
			ret = -ENOMEM;
			goto out;
		}
	} else if ((len = str_has_prefix(str, "sort="))) {
		attrs->sort_key_str = kstrdup(str + len, GFP_KERNEL);
		if (!attrs->sort_key_str) {
			ret = -ENOMEM;
			goto out;
		}
	} else if (str_has_prefix(str, "name=")) {
		attrs->name = kstrdup(str, GFP_KERNEL);
		if (!attrs->name) {
			ret = -ENOMEM;
			goto out;
		}
	} else if ((len = str_has_prefix(str, "clock="))) {
		str += len;

		str = strstrip(str);
		attrs->clock = kstrdup(str, GFP_KERNEL);
		if (!attrs->clock) {
			ret = -ENOMEM;
			goto out;
		}
	} else if ((len = str_has_prefix(str, "size="))) {
		int map_bits = parse_map_size(str + len);

		if (map_bits < 0) {
			ret = map_bits;
			goto out;
		}
		attrs->map_bits = map_bits;
	} else {
		char *assignment;

		if (attrs->n_assignments == TRACING_MAP_VARS_MAX) {
			hist_err(tr, HIST_ERR_TOO_MANY_VARS, errpos(str));
			ret = -EINVAL;
			goto out;
		}

		assignment = kstrdup(str, GFP_KERNEL);
		if (!assignment) {
			ret = -ENOMEM;
			goto out;
		}

		attrs->assignment_str[attrs->n_assignments++] = assignment;
	}
 out:
	return ret;
}

static struct hist_trigger_attrs *
parse_hist_trigger_attrs(struct trace_array *tr, char *trigger_str)
{
	struct hist_trigger_attrs *attrs;
	int ret = 0;

	attrs = kzalloc(sizeof(*attrs), GFP_KERNEL);
	if (!attrs)
		return ERR_PTR(-ENOMEM);

	while (trigger_str) {
		char *str = strsep(&trigger_str, ":");
		char *rhs;

		rhs = strchr(str, '=');
		if (rhs) {
			if (!strlen(++rhs)) {
				ret = -EINVAL;
				hist_err(tr, HIST_ERR_EMPTY_ASSIGNMENT, errpos(str));
				goto free;
			}
			ret = parse_assignment(tr, str, attrs);
			if (ret)
				goto free;
		} else if (strcmp(str, "pause") == 0)
			attrs->pause = true;
		else if ((strcmp(str, "cont") == 0) ||
			 (strcmp(str, "continue") == 0))
			attrs->cont = true;
		else if (strcmp(str, "clear") == 0)
			attrs->clear = true;
		else {
			ret = parse_action(str, attrs);
			if (ret)
				goto free;
		}
	}

	if (!attrs->keys_str) {
		ret = -EINVAL;
		goto free;
	}

	if (!attrs->clock) {
		attrs->clock = kstrdup("global", GFP_KERNEL);
		if (!attrs->clock) {
			ret = -ENOMEM;
			goto free;
		}
	}

	return attrs;
 free:
	destroy_hist_trigger_attrs(attrs);

	return ERR_PTR(ret);
}

static inline void save_comm(char *comm, struct task_struct *task)
{
	if (!task->pid) {
		strcpy(comm, "<idle>");
		return;
	}

	if (WARN_ON_ONCE(task->pid < 0)) {
		strcpy(comm, "<XXX>");
		return;
	}

	strncpy(comm, task->comm, TASK_COMM_LEN);
}

static void hist_elt_data_free(struct hist_elt_data *elt_data)
{
	unsigned int i;

	for (i = 0; i < SYNTH_FIELDS_MAX; i++)
		kfree(elt_data->field_var_str[i]);

	kfree(elt_data->comm);
	kfree(elt_data);
}

static void hist_trigger_elt_data_free(struct tracing_map_elt *elt)
{
	struct hist_elt_data *elt_data = elt->private_data;

	hist_elt_data_free(elt_data);
}

static int hist_trigger_elt_data_alloc(struct tracing_map_elt *elt)
{
	struct hist_trigger_data *hist_data = elt->map->private_data;
	unsigned int size = TASK_COMM_LEN;
	struct hist_elt_data *elt_data;
	struct hist_field *key_field;
	unsigned int i, n_str;

	elt_data = kzalloc(sizeof(*elt_data), GFP_KERNEL);
	if (!elt_data)
		return -ENOMEM;

	for_each_hist_key_field(i, hist_data) {
		key_field = hist_data->fields[i];

		if (key_field->flags & HIST_FIELD_FL_EXECNAME) {
			elt_data->comm = kzalloc(size, GFP_KERNEL);
			if (!elt_data->comm) {
				kfree(elt_data);
				return -ENOMEM;
			}
			break;
		}
	}

	n_str = hist_data->n_field_var_str + hist_data->n_save_var_str;

	size = STR_VAR_LEN_MAX;

	for (i = 0; i < n_str; i++) {
		elt_data->field_var_str[i] = kzalloc(size, GFP_KERNEL);
		if (!elt_data->field_var_str[i]) {
			hist_elt_data_free(elt_data);
			return -ENOMEM;
		}
	}

	elt->private_data = elt_data;

	return 0;
}

static void hist_trigger_elt_data_init(struct tracing_map_elt *elt)
{
	struct hist_elt_data *elt_data = elt->private_data;

	if (elt_data->comm)
		save_comm(elt_data->comm, current);
}

static const struct tracing_map_ops hist_trigger_elt_data_ops = {
	.elt_alloc	= hist_trigger_elt_data_alloc,
	.elt_free	= hist_trigger_elt_data_free,
	.elt_init	= hist_trigger_elt_data_init,
};

static const char *get_hist_field_flags(struct hist_field *hist_field)
{
	const char *flags_str = NULL;

	if (hist_field->flags & HIST_FIELD_FL_HEX)
		flags_str = "hex";
	else if (hist_field->flags & HIST_FIELD_FL_SYM)
		flags_str = "sym";
	else if (hist_field->flags & HIST_FIELD_FL_SYM_OFFSET)
		flags_str = "sym-offset";
	else if (hist_field->flags & HIST_FIELD_FL_EXECNAME)
		flags_str = "execname";
	else if (hist_field->flags & HIST_FIELD_FL_SYSCALL)
		flags_str = "syscall";
	else if (hist_field->flags & HIST_FIELD_FL_LOG2)
		flags_str = "log2";
	else if (hist_field->flags & HIST_FIELD_FL_TIMESTAMP_USECS)
		flags_str = "usecs";

	return flags_str;
}

static void expr_field_str(struct hist_field *field, char *expr)
{
	if (field->flags & HIST_FIELD_FL_VAR_REF)
		strcat(expr, "$");

	strcat(expr, hist_field_name(field, 0));

	if (field->flags && !(field->flags & HIST_FIELD_FL_VAR_REF)) {
		const char *flags_str = get_hist_field_flags(field);

		if (flags_str) {
			strcat(expr, ".");
			strcat(expr, flags_str);
		}
	}
}

static char *expr_str(struct hist_field *field, unsigned int level)
{
	char *expr;

	if (level > 1)
		return NULL;

	expr = kzalloc(MAX_FILTER_STR_VAL, GFP_KERNEL);
	if (!expr)
		return NULL;

	if (!field->operands[0]) {
		expr_field_str(field, expr);
		return expr;
	}

	if (field->operator == FIELD_OP_UNARY_MINUS) {
		char *subexpr;

		strcat(expr, "-(");
		subexpr = expr_str(field->operands[0], ++level);
		if (!subexpr) {
			kfree(expr);
			return NULL;
		}
		strcat(expr, subexpr);
		strcat(expr, ")");

		kfree(subexpr);

		return expr;
	}

	expr_field_str(field->operands[0], expr);

	switch (field->operator) {
	case FIELD_OP_MINUS:
		strcat(expr, "-");
		break;
	case FIELD_OP_PLUS:
		strcat(expr, "+");
		break;
	default:
		kfree(expr);
		return NULL;
	}

	expr_field_str(field->operands[1], expr);

	return expr;
}

static int contains_operator(char *str)
{
	enum field_op_id field_op = FIELD_OP_NONE;
	char *op;

	op = strpbrk(str, "+-");
	if (!op)
		return FIELD_OP_NONE;

	switch (*op) {
	case '-':
		if (*str == '-')
			field_op = FIELD_OP_UNARY_MINUS;
		else
			field_op = FIELD_OP_MINUS;
		break;
	case '+':
		field_op = FIELD_OP_PLUS;
		break;
	default:
		break;
	}

	return field_op;
}

static void get_hist_field(struct hist_field *hist_field)
{
	hist_field->ref++;
}

static void __destroy_hist_field(struct hist_field *hist_field)
{
	if (--hist_field->ref > 1)
		return;

	kfree(hist_field->var.name);
	kfree(hist_field->name);
	kfree(hist_field->type);

	kfree(hist_field);
}

static void destroy_hist_field(struct hist_field *hist_field,
			       unsigned int level)
{
	unsigned int i;

	if (level > 3)
		return;

	if (!hist_field)
		return;

	if (hist_field->flags & HIST_FIELD_FL_VAR_REF)
		return; /* var refs will be destroyed separately */

	for (i = 0; i < HIST_FIELD_OPERANDS_MAX; i++)
		destroy_hist_field(hist_field->operands[i], level + 1);

	__destroy_hist_field(hist_field);
}

static struct hist_field *create_hist_field(struct hist_trigger_data *hist_data,
					    struct ftrace_event_field *field,
					    unsigned long flags,
					    char *var_name)
{
	struct hist_field *hist_field;

	if (field && is_function_field(field))
		return NULL;

	hist_field = kzalloc(sizeof(struct hist_field), GFP_KERNEL);
	if (!hist_field)
		return NULL;

	hist_field->ref = 1;

	hist_field->hist_data = hist_data;

	if (flags & HIST_FIELD_FL_EXPR || flags & HIST_FIELD_FL_ALIAS)
		goto out; /* caller will populate */

	if (flags & HIST_FIELD_FL_VAR_REF) {
		hist_field->fn = hist_field_var_ref;
		goto out;
	}

	if (flags & HIST_FIELD_FL_HITCOUNT) {
		hist_field->fn = hist_field_counter;
		hist_field->size = sizeof(u64);
		hist_field->type = kstrdup("u64", GFP_KERNEL);
		if (!hist_field->type)
			goto free;
		goto out;
	}

	if (flags & HIST_FIELD_FL_STACKTRACE) {
		hist_field->fn = hist_field_none;
		goto out;
	}

	if (flags & HIST_FIELD_FL_LOG2) {
		unsigned long fl = flags & ~HIST_FIELD_FL_LOG2;
		hist_field->fn = hist_field_log2;
		hist_field->operands[0] = create_hist_field(hist_data, field, fl, NULL);
		hist_field->size = hist_field->operands[0]->size;
		hist_field->type = kstrdup(hist_field->operands[0]->type, GFP_KERNEL);
		if (!hist_field->type)
			goto free;
		goto out;
	}

	if (flags & HIST_FIELD_FL_TIMESTAMP) {
		hist_field->fn = hist_field_timestamp;
		hist_field->size = sizeof(u64);
		hist_field->type = kstrdup("u64", GFP_KERNEL);
		if (!hist_field->type)
			goto free;
		goto out;
	}

	if (flags & HIST_FIELD_FL_CPU) {
		hist_field->fn = hist_field_cpu;
		hist_field->size = sizeof(int);
		hist_field->type = kstrdup("unsigned int", GFP_KERNEL);
		if (!hist_field->type)
			goto free;
		goto out;
	}

	if (WARN_ON_ONCE(!field))
		goto out;

	if (is_string_field(field)) {
		flags |= HIST_FIELD_FL_STRING;

		hist_field->size = MAX_FILTER_STR_VAL;
		hist_field->type = kstrdup(field->type, GFP_KERNEL);
		if (!hist_field->type)
			goto free;

		if (field->filter_type == FILTER_STATIC_STRING)
			hist_field->fn = hist_field_string;
		else if (field->filter_type == FILTER_DYN_STRING)
			hist_field->fn = hist_field_dynstring;
		else
			hist_field->fn = hist_field_pstring;
	} else {
		hist_field->size = field->size;
		hist_field->is_signed = field->is_signed;
		hist_field->type = kstrdup(field->type, GFP_KERNEL);
		if (!hist_field->type)
			goto free;

		hist_field->fn = select_value_fn(field->size,
						 field->is_signed);
		if (!hist_field->fn) {
			destroy_hist_field(hist_field, 0);
			return NULL;
		}
	}
 out:
	hist_field->field = field;
	hist_field->flags = flags;

	if (var_name) {
		hist_field->var.name = kstrdup(var_name, GFP_KERNEL);
		if (!hist_field->var.name)
			goto free;
	}

	return hist_field;
 free:
	destroy_hist_field(hist_field, 0);
	return NULL;
}

static void destroy_hist_fields(struct hist_trigger_data *hist_data)
{
	unsigned int i;

	for (i = 0; i < HIST_FIELDS_MAX; i++) {
		if (hist_data->fields[i]) {
			destroy_hist_field(hist_data->fields[i], 0);
			hist_data->fields[i] = NULL;
		}
	}

	for (i = 0; i < hist_data->n_var_refs; i++) {
		WARN_ON(!(hist_data->var_refs[i]->flags & HIST_FIELD_FL_VAR_REF));
		__destroy_hist_field(hist_data->var_refs[i]);
		hist_data->var_refs[i] = NULL;
	}
}

static int init_var_ref(struct hist_field *ref_field,
			struct hist_field *var_field,
			char *system, char *event_name)
{
	int err = 0;

	ref_field->var.idx = var_field->var.idx;
	ref_field->var.hist_data = var_field->hist_data;
	ref_field->size = var_field->size;
	ref_field->is_signed = var_field->is_signed;
	ref_field->flags |= var_field->flags &
		(HIST_FIELD_FL_TIMESTAMP | HIST_FIELD_FL_TIMESTAMP_USECS);

	if (system) {
		ref_field->system = kstrdup(system, GFP_KERNEL);
		if (!ref_field->system)
			return -ENOMEM;
	}

	if (event_name) {
		ref_field->event_name = kstrdup(event_name, GFP_KERNEL);
		if (!ref_field->event_name) {
			err = -ENOMEM;
			goto free;
		}
	}

	if (var_field->var.name) {
		ref_field->name = kstrdup(var_field->var.name, GFP_KERNEL);
		if (!ref_field->name) {
			err = -ENOMEM;
			goto free;
		}
	} else if (var_field->name) {
		ref_field->name = kstrdup(var_field->name, GFP_KERNEL);
		if (!ref_field->name) {
			err = -ENOMEM;
			goto free;
		}
	}

	ref_field->type = kstrdup(var_field->type, GFP_KERNEL);
	if (!ref_field->type) {
		err = -ENOMEM;
		goto free;
	}
 out:
	return err;
 free:
	kfree(ref_field->system);
	kfree(ref_field->event_name);
	kfree(ref_field->name);

	goto out;
}

static int find_var_ref_idx(struct hist_trigger_data *hist_data,
			    struct hist_field *var_field)
{
	struct hist_field *ref_field;
	int i;

	for (i = 0; i < hist_data->n_var_refs; i++) {
		ref_field = hist_data->var_refs[i];
		if (ref_field->var.idx == var_field->var.idx &&
		    ref_field->var.hist_data == var_field->hist_data)
			return i;
	}

	return -ENOENT;
}

/**
 * create_var_ref - Create a variable reference and attach it to trigger
 * @hist_data: The trigger that will be referencing the variable
 * @var_field: The VAR field to create a reference to
 * @system: The optional system string
 * @event_name: The optional event_name string
 *
 * Given a variable hist_field, create a VAR_REF hist_field that
 * represents a reference to it.
 *
 * This function also adds the reference to the trigger that
 * now references the variable.
 *
 * Return: The VAR_REF field if successful, NULL if not
 */
static struct hist_field *create_var_ref(struct hist_trigger_data *hist_data,
					 struct hist_field *var_field,
					 char *system, char *event_name)
{
	unsigned long flags = HIST_FIELD_FL_VAR_REF;
	struct hist_field *ref_field;
	int i;

	/* Check if the variable already exists */
	for (i = 0; i < hist_data->n_var_refs; i++) {
		ref_field = hist_data->var_refs[i];
		if (ref_field->var.idx == var_field->var.idx &&
		    ref_field->var.hist_data == var_field->hist_data) {
			get_hist_field(ref_field);
			return ref_field;
		}
	}

	ref_field = create_hist_field(var_field->hist_data, NULL, flags, NULL);
	if (ref_field) {
		if (init_var_ref(ref_field, var_field, system, event_name)) {
			destroy_hist_field(ref_field, 0);
			return NULL;
		}

		hist_data->var_refs[hist_data->n_var_refs] = ref_field;
		ref_field->var_ref_idx = hist_data->n_var_refs++;
	}

	return ref_field;
}

static bool is_var_ref(char *var_name)
{
	if (!var_name || strlen(var_name) < 2 || var_name[0] != '$')
		return false;

	return true;
}

static char *field_name_from_var(struct hist_trigger_data *hist_data,
				 char *var_name)
{
	char *name, *field;
	unsigned int i;

	for (i = 0; i < hist_data->attrs->var_defs.n_vars; i++) {
		name = hist_data->attrs->var_defs.name[i];

		if (strcmp(var_name, name) == 0) {
			field = hist_data->attrs->var_defs.expr[i];
			if (contains_operator(field) || is_var_ref(field))
				continue;
			return field;
		}
	}

	return NULL;
}

static char *local_field_var_ref(struct hist_trigger_data *hist_data,
				 char *system, char *event_name,
				 char *var_name)
{
	struct trace_event_call *call;

	if (system && event_name) {
		call = hist_data->event_file->event_call;

		if (strcmp(system, call->class->system) != 0)
			return NULL;

		if (strcmp(event_name, trace_event_name(call)) != 0)
			return NULL;
	}

	if (!!system != !!event_name)
		return NULL;

	if (!is_var_ref(var_name))
		return NULL;

	var_name++;

	return field_name_from_var(hist_data, var_name);
}

static struct hist_field *parse_var_ref(struct hist_trigger_data *hist_data,
					char *system, char *event_name,
					char *var_name)
{
	struct hist_field *var_field = NULL, *ref_field = NULL;
	struct trace_array *tr = hist_data->event_file->tr;

	if (!is_var_ref(var_name))
		return NULL;

	var_name++;

	var_field = find_event_var(hist_data, system, event_name, var_name);
	if (var_field)
		ref_field = create_var_ref(hist_data, var_field,
					   system, event_name);

	if (!ref_field)
		hist_err(tr, HIST_ERR_VAR_NOT_FOUND, errpos(var_name));

	return ref_field;
}

static struct ftrace_event_field *
parse_field(struct hist_trigger_data *hist_data, struct trace_event_file *file,
	    char *field_str, unsigned long *flags)
{
	struct ftrace_event_field *field = NULL;
	char *field_name, *modifier, *str;
	struct trace_array *tr = file->tr;

	modifier = str = kstrdup(field_str, GFP_KERNEL);
	if (!modifier)
		return ERR_PTR(-ENOMEM);

	field_name = strsep(&modifier, ".");
	if (modifier) {
		if (strcmp(modifier, "hex") == 0)
			*flags |= HIST_FIELD_FL_HEX;
		else if (strcmp(modifier, "sym") == 0)
			*flags |= HIST_FIELD_FL_SYM;
		else if (strcmp(modifier, "sym-offset") == 0)
			*flags |= HIST_FIELD_FL_SYM_OFFSET;
		else if ((strcmp(modifier, "execname") == 0) &&
			 (strcmp(field_name, "common_pid") == 0))
			*flags |= HIST_FIELD_FL_EXECNAME;
		else if (strcmp(modifier, "syscall") == 0)
			*flags |= HIST_FIELD_FL_SYSCALL;
		else if (strcmp(modifier, "log2") == 0)
			*flags |= HIST_FIELD_FL_LOG2;
		else if (strcmp(modifier, "usecs") == 0)
			*flags |= HIST_FIELD_FL_TIMESTAMP_USECS;
		else {
			hist_err(tr, HIST_ERR_BAD_FIELD_MODIFIER, errpos(modifier));
			field = ERR_PTR(-EINVAL);
			goto out;
		}
	}

	if (strcmp(field_name, "common_timestamp") == 0) {
		*flags |= HIST_FIELD_FL_TIMESTAMP;
		hist_data->enable_timestamps = true;
		if (*flags & HIST_FIELD_FL_TIMESTAMP_USECS)
			hist_data->attrs->ts_in_usecs = true;
	} else if (strcmp(field_name, "cpu") == 0)
		*flags |= HIST_FIELD_FL_CPU;
	else {
		field = trace_find_event_field(file->event_call, field_name);
		if (!field || !field->size) {
			hist_err(tr, HIST_ERR_FIELD_NOT_FOUND, errpos(field_name));
			field = ERR_PTR(-EINVAL);
			goto out;
		}
	}
 out:
	kfree(str);

	return field;
}

static struct hist_field *create_alias(struct hist_trigger_data *hist_data,
				       struct hist_field *var_ref,
				       char *var_name)
{
	struct hist_field *alias = NULL;
	unsigned long flags = HIST_FIELD_FL_ALIAS | HIST_FIELD_FL_VAR;

	alias = create_hist_field(hist_data, NULL, flags, var_name);
	if (!alias)
		return NULL;

	alias->fn = var_ref->fn;
	alias->operands[0] = var_ref;

	if (init_var_ref(alias, var_ref, var_ref->system, var_ref->event_name)) {
		destroy_hist_field(alias, 0);
		return NULL;
	}

	alias->var_ref_idx = var_ref->var_ref_idx;

	return alias;
}

static struct hist_field *parse_atom(struct hist_trigger_data *hist_data,
				     struct trace_event_file *file, char *str,
				     unsigned long *flags, char *var_name)
{
	char *s, *ref_system = NULL, *ref_event = NULL, *ref_var = str;
	struct ftrace_event_field *field = NULL;
	struct hist_field *hist_field = NULL;
	int ret = 0;

	s = strchr(str, '.');
	if (s) {
		s = strchr(++s, '.');
		if (s) {
			ref_system = strsep(&str, ".");
			if (!str) {
				ret = -EINVAL;
				goto out;
			}
			ref_event = strsep(&str, ".");
			if (!str) {
				ret = -EINVAL;
				goto out;
			}
			ref_var = str;
		}
	}

	s = local_field_var_ref(hist_data, ref_system, ref_event, ref_var);
	if (!s) {
		hist_field = parse_var_ref(hist_data, ref_system,
					   ref_event, ref_var);
		if (hist_field) {
			if (var_name) {
				hist_field = create_alias(hist_data, hist_field, var_name);
				if (!hist_field) {
					ret = -ENOMEM;
					goto out;
				}
			}
			return hist_field;
		}
	} else
		str = s;

	field = parse_field(hist_data, file, str, flags);
	if (IS_ERR(field)) {
		ret = PTR_ERR(field);
		goto out;
	}

	hist_field = create_hist_field(hist_data, field, *flags, var_name);
	if (!hist_field) {
		ret = -ENOMEM;
		goto out;
	}

	return hist_field;
 out:
	return ERR_PTR(ret);
}

static struct hist_field *parse_expr(struct hist_trigger_data *hist_data,
				     struct trace_event_file *file,
				     char *str, unsigned long flags,
				     char *var_name, unsigned int level);

static struct hist_field *parse_unary(struct hist_trigger_data *hist_data,
				      struct trace_event_file *file,
				      char *str, unsigned long flags,
				      char *var_name, unsigned int level)
{
	struct hist_field *operand1, *expr = NULL;
	unsigned long operand_flags;
	int ret = 0;
	char *s;

	/* we support only -(xxx) i.e. explicit parens required */

	if (level > 3) {
		hist_err(file->tr, HIST_ERR_TOO_MANY_SUBEXPR, errpos(str));
		ret = -EINVAL;
		goto free;
	}

	str++; /* skip leading '-' */

	s = strchr(str, '(');
	if (s)
		str++;
	else {
		ret = -EINVAL;
		goto free;
	}

	s = strrchr(str, ')');
	if (s)
		*s = '\0';
	else {
		ret = -EINVAL; /* no closing ')' */
		goto free;
	}

	flags |= HIST_FIELD_FL_EXPR;
	expr = create_hist_field(hist_data, NULL, flags, var_name);
	if (!expr) {
		ret = -ENOMEM;
		goto free;
	}

	operand_flags = 0;
	operand1 = parse_expr(hist_data, file, str, operand_flags, NULL, ++level);
	if (IS_ERR(operand1)) {
		ret = PTR_ERR(operand1);
		goto free;
	}

	expr->flags |= operand1->flags &
		(HIST_FIELD_FL_TIMESTAMP | HIST_FIELD_FL_TIMESTAMP_USECS);
	expr->fn = hist_field_unary_minus;
	expr->operands[0] = operand1;
	expr->operator = FIELD_OP_UNARY_MINUS;
	expr->name = expr_str(expr, 0);
	expr->type = kstrdup(operand1->type, GFP_KERNEL);
	if (!expr->type) {
		ret = -ENOMEM;
		goto free;
	}

	return expr;
 free:
	destroy_hist_field(expr, 0);
	return ERR_PTR(ret);
}

static int check_expr_operands(struct trace_array *tr,
			       struct hist_field *operand1,
			       struct hist_field *operand2)
{
	unsigned long operand1_flags = operand1->flags;
	unsigned long operand2_flags = operand2->flags;

	if ((operand1_flags & HIST_FIELD_FL_VAR_REF) ||
	    (operand1_flags & HIST_FIELD_FL_ALIAS)) {
		struct hist_field *var;

		var = find_var_field(operand1->var.hist_data, operand1->name);
		if (!var)
			return -EINVAL;
		operand1_flags = var->flags;
	}

	if ((operand2_flags & HIST_FIELD_FL_VAR_REF) ||
	    (operand2_flags & HIST_FIELD_FL_ALIAS)) {
		struct hist_field *var;

		var = find_var_field(operand2->var.hist_data, operand2->name);
		if (!var)
			return -EINVAL;
		operand2_flags = var->flags;
	}

	if ((operand1_flags & HIST_FIELD_FL_TIMESTAMP_USECS) !=
	    (operand2_flags & HIST_FIELD_FL_TIMESTAMP_USECS)) {
		hist_err(tr, HIST_ERR_TIMESTAMP_MISMATCH, 0);
		return -EINVAL;
	}

	return 0;
}

static struct hist_field *parse_expr(struct hist_trigger_data *hist_data,
				     struct trace_event_file *file,
				     char *str, unsigned long flags,
				     char *var_name, unsigned int level)
{
	struct hist_field *operand1 = NULL, *operand2 = NULL, *expr = NULL;
	unsigned long operand_flags;
	int field_op, ret = -EINVAL;
	char *sep, *operand1_str;

	if (level > 3) {
		hist_err(file->tr, HIST_ERR_TOO_MANY_SUBEXPR, errpos(str));
		return ERR_PTR(-EINVAL);
	}

	field_op = contains_operator(str);

	if (field_op == FIELD_OP_NONE)
		return parse_atom(hist_data, file, str, &flags, var_name);

	if (field_op == FIELD_OP_UNARY_MINUS)
		return parse_unary(hist_data, file, str, flags, var_name, ++level);

	switch (field_op) {
	case FIELD_OP_MINUS:
		sep = "-";
		break;
	case FIELD_OP_PLUS:
		sep = "+";
		break;
	default:
		goto free;
	}

	operand1_str = strsep(&str, sep);
	if (!operand1_str || !str)
		goto free;

	operand_flags = 0;
	operand1 = parse_atom(hist_data, file, operand1_str,
			      &operand_flags, NULL);
	if (IS_ERR(operand1)) {
		ret = PTR_ERR(operand1);
		operand1 = NULL;
		goto free;
	}

	/* rest of string could be another expression e.g. b+c in a+b+c */
	operand_flags = 0;
	operand2 = parse_expr(hist_data, file, str, operand_flags, NULL, ++level);
	if (IS_ERR(operand2)) {
		ret = PTR_ERR(operand2);
		operand2 = NULL;
		goto free;
	}

	ret = check_expr_operands(file->tr, operand1, operand2);
	if (ret)
		goto free;

	flags |= HIST_FIELD_FL_EXPR;

	flags |= operand1->flags &
		(HIST_FIELD_FL_TIMESTAMP | HIST_FIELD_FL_TIMESTAMP_USECS);

	expr = create_hist_field(hist_data, NULL, flags, var_name);
	if (!expr) {
		ret = -ENOMEM;
		goto free;
	}

	operand1->read_once = true;
	operand2->read_once = true;

	expr->operands[0] = operand1;
	expr->operands[1] = operand2;
	expr->operator = field_op;
	expr->name = expr_str(expr, 0);
	expr->type = kstrdup(operand1->type, GFP_KERNEL);
	if (!expr->type) {
		ret = -ENOMEM;
		goto free;
	}

	switch (field_op) {
	case FIELD_OP_MINUS:
		expr->fn = hist_field_minus;
		break;
	case FIELD_OP_PLUS:
		expr->fn = hist_field_plus;
		break;
	default:
		ret = -EINVAL;
		goto free;
	}

	return expr;
 free:
	destroy_hist_field(operand1, 0);
	destroy_hist_field(operand2, 0);
	destroy_hist_field(expr, 0);

	return ERR_PTR(ret);
}

static char *find_trigger_filter(struct hist_trigger_data *hist_data,
				 struct trace_event_file *file)
{
	struct event_trigger_data *test;

	lockdep_assert_held(&event_mutex);

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			if (test->private_data == hist_data)
				return test->filter_str;
		}
	}

	return NULL;
}

static struct event_command trigger_hist_cmd;
static int event_hist_trigger_func(struct event_command *cmd_ops,
				   struct trace_event_file *file,
				   char *glob, char *cmd, char *param);

static bool compatible_keys(struct hist_trigger_data *target_hist_data,
			    struct hist_trigger_data *hist_data,
			    unsigned int n_keys)
{
	struct hist_field *target_hist_field, *hist_field;
	unsigned int n, i, j;

	if (hist_data->n_fields - hist_data->n_vals != n_keys)
		return false;

	i = hist_data->n_vals;
	j = target_hist_data->n_vals;

	for (n = 0; n < n_keys; n++) {
		hist_field = hist_data->fields[i + n];
		target_hist_field = target_hist_data->fields[j + n];

		if (strcmp(hist_field->type, target_hist_field->type) != 0)
			return false;
		if (hist_field->size != target_hist_field->size)
			return false;
		if (hist_field->is_signed != target_hist_field->is_signed)
			return false;
	}

	return true;
}

static struct hist_trigger_data *
find_compatible_hist(struct hist_trigger_data *target_hist_data,
		     struct trace_event_file *file)
{
	struct hist_trigger_data *hist_data;
	struct event_trigger_data *test;
	unsigned int n_keys;

	lockdep_assert_held(&event_mutex);

	n_keys = target_hist_data->n_fields - target_hist_data->n_vals;

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			hist_data = test->private_data;

			if (compatible_keys(target_hist_data, hist_data, n_keys))
				return hist_data;
		}
	}

	return NULL;
}

static struct trace_event_file *event_file(struct trace_array *tr,
					   char *system, char *event_name)
{
	struct trace_event_file *file;

	file = __find_event_file(tr, system, event_name);
	if (!file)
		return ERR_PTR(-EINVAL);

	return file;
}

static struct hist_field *
find_synthetic_field_var(struct hist_trigger_data *target_hist_data,
			 char *system, char *event_name, char *field_name)
{
	struct hist_field *event_var;
	char *synthetic_name;

	synthetic_name = kzalloc(MAX_FILTER_STR_VAL, GFP_KERNEL);
	if (!synthetic_name)
		return ERR_PTR(-ENOMEM);

	strcpy(synthetic_name, "synthetic_");
	strcat(synthetic_name, field_name);

	event_var = find_event_var(target_hist_data, system, event_name, synthetic_name);

	kfree(synthetic_name);

	return event_var;
}

/**
 * create_field_var_hist - Automatically create a histogram and var for a field
 * @target_hist_data: The target hist trigger
 * @subsys_name: Optional subsystem name
 * @event_name: Optional event name
 * @field_name: The name of the field (and the resulting variable)
 *
 * Hist trigger actions fetch data from variables, not directly from
 * events.  However, for convenience, users are allowed to directly
 * specify an event field in an action, which will be automatically
 * converted into a variable on their behalf.

 * If a user specifies a field on an event that isn't the event the
 * histogram currently being defined (the target event histogram), the
 * only way that can be accomplished is if a new hist trigger is
 * created and the field variable defined on that.
 *
 * This function creates a new histogram compatible with the target
 * event (meaning a histogram with the same key as the target
 * histogram), and creates a variable for the specified field, but
 * with 'synthetic_' prepended to the variable name in order to avoid
 * collision with normal field variables.
 *
 * Return: The variable created for the field.
 */
static struct hist_field *
create_field_var_hist(struct hist_trigger_data *target_hist_data,
		      char *subsys_name, char *event_name, char *field_name)
{
	struct trace_array *tr = target_hist_data->event_file->tr;
	struct hist_field *event_var = ERR_PTR(-EINVAL);
	struct hist_trigger_data *hist_data;
	unsigned int i, n, first = true;
	struct field_var_hist *var_hist;
	struct trace_event_file *file;
	struct hist_field *key_field;
	char *saved_filter;
	char *cmd;
	int ret;

	if (target_hist_data->n_field_var_hists >= SYNTH_FIELDS_MAX) {
		hist_err(tr, HIST_ERR_TOO_MANY_FIELD_VARS, errpos(field_name));
		return ERR_PTR(-EINVAL);
	}

	file = event_file(tr, subsys_name, event_name);

	if (IS_ERR(file)) {
		hist_err(tr, HIST_ERR_EVENT_FILE_NOT_FOUND, errpos(field_name));
		ret = PTR_ERR(file);
		return ERR_PTR(ret);
	}

	/*
	 * Look for a histogram compatible with target.  We'll use the
	 * found histogram specification to create a new matching
	 * histogram with our variable on it.  target_hist_data is not
	 * yet a registered histogram so we can't use that.
	 */
	hist_data = find_compatible_hist(target_hist_data, file);
	if (!hist_data) {
		hist_err(tr, HIST_ERR_HIST_NOT_FOUND, errpos(field_name));
		return ERR_PTR(-EINVAL);
	}

	/* See if a synthetic field variable has already been created */
	event_var = find_synthetic_field_var(target_hist_data, subsys_name,
					     event_name, field_name);
	if (!IS_ERR_OR_NULL(event_var))
		return event_var;

	var_hist = kzalloc(sizeof(*var_hist), GFP_KERNEL);
	if (!var_hist)
		return ERR_PTR(-ENOMEM);

	cmd = kzalloc(MAX_FILTER_STR_VAL, GFP_KERNEL);
	if (!cmd) {
		kfree(var_hist);
		return ERR_PTR(-ENOMEM);
	}

	/* Use the same keys as the compatible histogram */
	strcat(cmd, "keys=");

	for_each_hist_key_field(i, hist_data) {
		key_field = hist_data->fields[i];
		if (!first)
			strcat(cmd, ",");
		strcat(cmd, key_field->field->name);
		first = false;
	}

	/* Create the synthetic field variable specification */
	strcat(cmd, ":synthetic_");
	strcat(cmd, field_name);
	strcat(cmd, "=");
	strcat(cmd, field_name);

	/* Use the same filter as the compatible histogram */
	saved_filter = find_trigger_filter(hist_data, file);
	if (saved_filter) {
		strcat(cmd, " if ");
		strcat(cmd, saved_filter);
	}

	var_hist->cmd = kstrdup(cmd, GFP_KERNEL);
	if (!var_hist->cmd) {
		kfree(cmd);
		kfree(var_hist);
		return ERR_PTR(-ENOMEM);
	}

	/* Save the compatible histogram information */
	var_hist->hist_data = hist_data;

	/* Create the new histogram with our variable */
	ret = event_hist_trigger_func(&trigger_hist_cmd, file,
				      "", "hist", cmd);
	if (ret) {
		kfree(cmd);
		kfree(var_hist->cmd);
		kfree(var_hist);
		hist_err(tr, HIST_ERR_HIST_CREATE_FAIL, errpos(field_name));
		return ERR_PTR(ret);
	}

	kfree(cmd);

	/* If we can't find the variable, something went wrong */
	event_var = find_synthetic_field_var(target_hist_data, subsys_name,
					     event_name, field_name);
	if (IS_ERR_OR_NULL(event_var)) {
		kfree(var_hist->cmd);
		kfree(var_hist);
		hist_err(tr, HIST_ERR_SYNTH_VAR_NOT_FOUND, errpos(field_name));
		return ERR_PTR(-EINVAL);
	}

	n = target_hist_data->n_field_var_hists;
	target_hist_data->field_var_hists[n] = var_hist;
	target_hist_data->n_field_var_hists++;

	return event_var;
}

static struct hist_field *
find_target_event_var(struct hist_trigger_data *hist_data,
		      char *subsys_name, char *event_name, char *var_name)
{
	struct trace_event_file *file = hist_data->event_file;
	struct hist_field *hist_field = NULL;

	if (subsys_name) {
		struct trace_event_call *call;

		if (!event_name)
			return NULL;

		call = file->event_call;

		if (strcmp(subsys_name, call->class->system) != 0)
			return NULL;

		if (strcmp(event_name, trace_event_name(call)) != 0)
			return NULL;
	}

	hist_field = find_var_field(hist_data, var_name);

	return hist_field;
}

static inline void __update_field_vars(struct tracing_map_elt *elt,
				       struct ring_buffer_event *rbe,
				       void *rec,
				       struct field_var **field_vars,
				       unsigned int n_field_vars,
				       unsigned int field_var_str_start)
{
	struct hist_elt_data *elt_data = elt->private_data;
	unsigned int i, j, var_idx;
	u64 var_val;

	for (i = 0, j = field_var_str_start; i < n_field_vars; i++) {
		struct field_var *field_var = field_vars[i];
		struct hist_field *var = field_var->var;
		struct hist_field *val = field_var->val;

		var_val = val->fn(val, elt, rbe, rec);
		var_idx = var->var.idx;

		if (val->flags & HIST_FIELD_FL_STRING) {
			char *str = elt_data->field_var_str[j++];
			char *val_str = (char *)(uintptr_t)var_val;

			strscpy(str, val_str, STR_VAR_LEN_MAX);
			var_val = (u64)(uintptr_t)str;
		}
		tracing_map_set_var(elt, var_idx, var_val);
	}
}

static void update_field_vars(struct hist_trigger_data *hist_data,
			      struct tracing_map_elt *elt,
			      struct ring_buffer_event *rbe,
			      void *rec)
{
	__update_field_vars(elt, rbe, rec, hist_data->field_vars,
			    hist_data->n_field_vars, 0);
}

static void save_track_data_vars(struct hist_trigger_data *hist_data,
				 struct tracing_map_elt *elt, void *rec,
				 struct ring_buffer_event *rbe, void *key,
				 struct action_data *data, u64 *var_ref_vals)
{
	__update_field_vars(elt, rbe, rec, hist_data->save_vars,
			    hist_data->n_save_vars, hist_data->n_field_var_str);
}

static struct hist_field *create_var(struct hist_trigger_data *hist_data,
				     struct trace_event_file *file,
				     char *name, int size, const char *type)
{
	struct hist_field *var;
	int idx;

	if (find_var(hist_data, file, name) && !hist_data->remove) {
		var = ERR_PTR(-EINVAL);
		goto out;
	}

	var = kzalloc(sizeof(struct hist_field), GFP_KERNEL);
	if (!var) {
		var = ERR_PTR(-ENOMEM);
		goto out;
	}

	idx = tracing_map_add_var(hist_data->map);
	if (idx < 0) {
		kfree(var);
		var = ERR_PTR(-EINVAL);
		goto out;
	}

	var->flags = HIST_FIELD_FL_VAR;
	var->var.idx = idx;
	var->var.hist_data = var->hist_data = hist_data;
	var->size = size;
	var->var.name = kstrdup(name, GFP_KERNEL);
	var->type = kstrdup(type, GFP_KERNEL);
	if (!var->var.name || !var->type) {
		kfree(var->var.name);
		kfree(var->type);
		kfree(var);
		var = ERR_PTR(-ENOMEM);
	}
 out:
	return var;
}

static struct field_var *create_field_var(struct hist_trigger_data *hist_data,
					  struct trace_event_file *file,
					  char *field_name)
{
	struct hist_field *val = NULL, *var = NULL;
	unsigned long flags = HIST_FIELD_FL_VAR;
	struct trace_array *tr = file->tr;
	struct field_var *field_var;
	int ret = 0;

	if (hist_data->n_field_vars >= SYNTH_FIELDS_MAX) {
		hist_err(tr, HIST_ERR_TOO_MANY_FIELD_VARS, errpos(field_name));
		ret = -EINVAL;
		goto err;
	}

	val = parse_atom(hist_data, file, field_name, &flags, NULL);
	if (IS_ERR(val)) {
		hist_err(tr, HIST_ERR_FIELD_VAR_PARSE_FAIL, errpos(field_name));
		ret = PTR_ERR(val);
		goto err;
	}

	var = create_var(hist_data, file, field_name, val->size, val->type);
	if (IS_ERR(var)) {
		hist_err(tr, HIST_ERR_VAR_CREATE_FIND_FAIL, errpos(field_name));
		kfree(val);
		ret = PTR_ERR(var);
		goto err;
	}

	field_var = kzalloc(sizeof(struct field_var), GFP_KERNEL);
	if (!field_var) {
		kfree(val);
		kfree(var);
		ret =  -ENOMEM;
		goto err;
	}

	field_var->var = var;
	field_var->val = val;
 out:
	return field_var;
 err:
	field_var = ERR_PTR(ret);
	goto out;
}

/**
 * create_target_field_var - Automatically create a variable for a field
 * @target_hist_data: The target hist trigger
 * @subsys_name: Optional subsystem name
 * @event_name: Optional event name
 * @var_name: The name of the field (and the resulting variable)
 *
 * Hist trigger actions fetch data from variables, not directly from
 * events.  However, for convenience, users are allowed to directly
 * specify an event field in an action, which will be automatically
 * converted into a variable on their behalf.

 * This function creates a field variable with the name var_name on
 * the hist trigger currently being defined on the target event.  If
 * subsys_name and event_name are specified, this function simply
 * verifies that they do in fact match the target event subsystem and
 * event name.
 *
 * Return: The variable created for the field.
 */
static struct field_var *
create_target_field_var(struct hist_trigger_data *target_hist_data,
			char *subsys_name, char *event_name, char *var_name)
{
	struct trace_event_file *file = target_hist_data->event_file;

	if (subsys_name) {
		struct trace_event_call *call;

		if (!event_name)
			return NULL;

		call = file->event_call;

		if (strcmp(subsys_name, call->class->system) != 0)
			return NULL;

		if (strcmp(event_name, trace_event_name(call)) != 0)
			return NULL;
	}

	return create_field_var(target_hist_data, file, var_name);
}

static bool check_track_val_max(u64 track_val, u64 var_val)
{
	if (var_val <= track_val)
		return false;

	return true;
}

static bool check_track_val_changed(u64 track_val, u64 var_val)
{
	if (var_val == track_val)
		return false;

	return true;
}

static u64 get_track_val(struct hist_trigger_data *hist_data,
			 struct tracing_map_elt *elt,
			 struct action_data *data)
{
	unsigned int track_var_idx = data->track_data.track_var->var.idx;
	u64 track_val;

	track_val = tracing_map_read_var(elt, track_var_idx);

	return track_val;
}

static void save_track_val(struct hist_trigger_data *hist_data,
			   struct tracing_map_elt *elt,
			   struct action_data *data, u64 var_val)
{
	unsigned int track_var_idx = data->track_data.track_var->var.idx;

	tracing_map_set_var(elt, track_var_idx, var_val);
}

static void save_track_data(struct hist_trigger_data *hist_data,
			    struct tracing_map_elt *elt, void *rec,
			    struct ring_buffer_event *rbe, void *key,
			    struct action_data *data, u64 *var_ref_vals)
{
	if (data->track_data.save_data)
		data->track_data.save_data(hist_data, elt, rec, rbe, key, data, var_ref_vals);
}

static bool check_track_val(struct tracing_map_elt *elt,
			    struct action_data *data,
			    u64 var_val)
{
	struct hist_trigger_data *hist_data;
	u64 track_val;

	hist_data = data->track_data.track_var->hist_data;
	track_val = get_track_val(hist_data, elt, data);

	return data->track_data.check_val(track_val, var_val);
}

#ifdef CONFIG_TRACER_SNAPSHOT
static bool cond_snapshot_update(struct trace_array *tr, void *cond_data)
{
	/* called with tr->max_lock held */
	struct track_data *track_data = tr->cond_snapshot->cond_data;
	struct hist_elt_data *elt_data, *track_elt_data;
	struct snapshot_context *context = cond_data;
	struct action_data *action;
	u64 track_val;

	if (!track_data)
		return false;

	action = track_data->action_data;

	track_val = get_track_val(track_data->hist_data, context->elt,
				  track_data->action_data);

	if (!action->track_data.check_val(track_data->track_val, track_val))
		return false;

	track_data->track_val = track_val;
	memcpy(track_data->key, context->key, track_data->key_len);

	elt_data = context->elt->private_data;
	track_elt_data = track_data->elt.private_data;
	if (elt_data->comm)
		strncpy(track_elt_data->comm, elt_data->comm, TASK_COMM_LEN);

	track_data->updated = true;

	return true;
}

static void save_track_data_snapshot(struct hist_trigger_data *hist_data,
				     struct tracing_map_elt *elt, void *rec,
				     struct ring_buffer_event *rbe, void *key,
				     struct action_data *data,
				     u64 *var_ref_vals)
{
	struct trace_event_file *file = hist_data->event_file;
	struct snapshot_context context;

	context.elt = elt;
	context.key = key;

	tracing_snapshot_cond(file->tr, &context);
}

static void hist_trigger_print_key(struct seq_file *m,
				   struct hist_trigger_data *hist_data,
				   void *key,
				   struct tracing_map_elt *elt);

static struct action_data *snapshot_action(struct hist_trigger_data *hist_data)
{
	unsigned int i;

	if (!hist_data->n_actions)
		return NULL;

	for (i = 0; i < hist_data->n_actions; i++) {
		struct action_data *data = hist_data->actions[i];

		if (data->action == ACTION_SNAPSHOT)
			return data;
	}

	return NULL;
}

static void track_data_snapshot_print(struct seq_file *m,
				      struct hist_trigger_data *hist_data)
{
	struct trace_event_file *file = hist_data->event_file;
	struct track_data *track_data;
	struct action_data *action;

	track_data = tracing_cond_snapshot_data(file->tr);
	if (!track_data)
		return;

	if (!track_data->updated)
		return;

	action = snapshot_action(hist_data);
	if (!action)
		return;

	seq_puts(m, "\nSnapshot taken (see tracing/snapshot).  Details:\n");
	seq_printf(m, "\ttriggering value { %s(%s) }: %10llu",
		   action->handler == HANDLER_ONMAX ? "onmax" : "onchange",
		   action->track_data.var_str, track_data->track_val);

	seq_puts(m, "\ttriggered by event with key: ");
	hist_trigger_print_key(m, hist_data, track_data->key, &track_data->elt);
	seq_putc(m, '\n');
}
#else
static bool cond_snapshot_update(struct trace_array *tr, void *cond_data)
{
	return false;
}
static void save_track_data_snapshot(struct hist_trigger_data *hist_data,
				     struct tracing_map_elt *elt, void *rec,
				     struct ring_buffer_event *rbe, void *key,
				     struct action_data *data,
				     u64 *var_ref_vals) {}
static void track_data_snapshot_print(struct seq_file *m,
				      struct hist_trigger_data *hist_data) {}
#endif /* CONFIG_TRACER_SNAPSHOT */

static void track_data_print(struct seq_file *m,
			     struct hist_trigger_data *hist_data,
			     struct tracing_map_elt *elt,
			     struct action_data *data)
{
	u64 track_val = get_track_val(hist_data, elt, data);
	unsigned int i, save_var_idx;

	if (data->handler == HANDLER_ONMAX)
		seq_printf(m, "\n\tmax: %10llu", track_val);
	else if (data->handler == HANDLER_ONCHANGE)
		seq_printf(m, "\n\tchanged: %10llu", track_val);

	if (data->action == ACTION_SNAPSHOT)
		return;

	for (i = 0; i < hist_data->n_save_vars; i++) {
		struct hist_field *save_val = hist_data->save_vars[i]->val;
		struct hist_field *save_var = hist_data->save_vars[i]->var;
		u64 val;

		save_var_idx = save_var->var.idx;

		val = tracing_map_read_var(elt, save_var_idx);

		if (save_val->flags & HIST_FIELD_FL_STRING) {
			seq_printf(m, "  %s: %-32s", save_var->var.name,
				   (char *)(uintptr_t)(val));
		} else
			seq_printf(m, "  %s: %10llu", save_var->var.name, val);
	}
}

static void ontrack_action(struct hist_trigger_data *hist_data,
			   struct tracing_map_elt *elt, void *rec,
			   struct ring_buffer_event *rbe, void *key,
			   struct action_data *data, u64 *var_ref_vals)
{
	u64 var_val = var_ref_vals[data->track_data.var_ref->var_ref_idx];

	if (check_track_val(elt, data, var_val)) {
		save_track_val(hist_data, elt, data, var_val);
		save_track_data(hist_data, elt, rec, rbe, key, data, var_ref_vals);
	}
}

static void action_data_destroy(struct action_data *data)
{
	unsigned int i;

	lockdep_assert_held(&event_mutex);

	kfree(data->action_name);

	for (i = 0; i < data->n_params; i++)
		kfree(data->params[i]);

	if (data->synth_event)
		data->synth_event->ref--;

	kfree(data->synth_event_name);

	kfree(data);
}

static void track_data_destroy(struct hist_trigger_data *hist_data,
			       struct action_data *data)
{
	struct trace_event_file *file = hist_data->event_file;

	destroy_hist_field(data->track_data.track_var, 0);

	if (data->action == ACTION_SNAPSHOT) {
		struct track_data *track_data;

		track_data = tracing_cond_snapshot_data(file->tr);
		if (track_data && track_data->hist_data == hist_data) {
			tracing_snapshot_cond_disable(file->tr);
			track_data_free(track_data);
		}
	}

	kfree(data->track_data.var_str);

	action_data_destroy(data);
}

static int action_create(struct hist_trigger_data *hist_data,
			 struct action_data *data);

static int track_data_create(struct hist_trigger_data *hist_data,
			     struct action_data *data)
{
	struct hist_field *var_field, *ref_field, *track_var = NULL;
	struct trace_event_file *file = hist_data->event_file;
	struct trace_array *tr = file->tr;
	char *track_data_var_str;
	int ret = 0;

	track_data_var_str = data->track_data.var_str;
	if (track_data_var_str[0] != '$') {
		hist_err(tr, HIST_ERR_ONX_NOT_VAR, errpos(track_data_var_str));
		return -EINVAL;
	}
	track_data_var_str++;

	var_field = find_target_event_var(hist_data, NULL, NULL, track_data_var_str);
	if (!var_field) {
		hist_err(tr, HIST_ERR_ONX_VAR_NOT_FOUND, errpos(track_data_var_str));
		return -EINVAL;
	}

	ref_field = create_var_ref(hist_data, var_field, NULL, NULL);
	if (!ref_field)
		return -ENOMEM;

	data->track_data.var_ref = ref_field;

	if (data->handler == HANDLER_ONMAX)
		track_var = create_var(hist_data, file, "__max", sizeof(u64), "u64");
	if (IS_ERR(track_var)) {
		hist_err(tr, HIST_ERR_ONX_VAR_CREATE_FAIL, 0);
		ret = PTR_ERR(track_var);
		goto out;
	}

	if (data->handler == HANDLER_ONCHANGE)
		track_var = create_var(hist_data, file, "__change", sizeof(u64), "u64");
	if (IS_ERR(track_var)) {
		hist_err(tr, HIST_ERR_ONX_VAR_CREATE_FAIL, 0);
		ret = PTR_ERR(track_var);
		goto out;
	}
	data->track_data.track_var = track_var;

	ret = action_create(hist_data, data);
 out:
	return ret;
}

static int parse_action_params(struct trace_array *tr, char *params,
			       struct action_data *data)
{
	char *param, *saved_param;
	bool first_param = true;
	int ret = 0;

	while (params) {
		if (data->n_params >= SYNTH_FIELDS_MAX) {
			hist_err(tr, HIST_ERR_TOO_MANY_PARAMS, 0);
			goto out;
		}

		param = strsep(&params, ",");
		if (!param) {
			hist_err(tr, HIST_ERR_PARAM_NOT_FOUND, 0);
			ret = -EINVAL;
			goto out;
		}

		param = strstrip(param);
		if (strlen(param) < 2) {
			hist_err(tr, HIST_ERR_INVALID_PARAM, errpos(param));
			ret = -EINVAL;
			goto out;
		}

		saved_param = kstrdup(param, GFP_KERNEL);
		if (!saved_param) {
			ret = -ENOMEM;
			goto out;
		}

		if (first_param && data->use_trace_keyword) {
			data->synth_event_name = saved_param;
			first_param = false;
			continue;
		}
		first_param = false;

		data->params[data->n_params++] = saved_param;
	}
 out:
	return ret;
}

static int action_parse(struct trace_array *tr, char *str, struct action_data *data,
			enum handler_id handler)
{
	char *action_name;
	int ret = 0;

	strsep(&str, ".");
	if (!str) {
		hist_err(tr, HIST_ERR_ACTION_NOT_FOUND, 0);
		ret = -EINVAL;
		goto out;
	}

	action_name = strsep(&str, "(");
	if (!action_name || !str) {
		hist_err(tr, HIST_ERR_ACTION_NOT_FOUND, 0);
		ret = -EINVAL;
		goto out;
	}

	if (str_has_prefix(action_name, "save")) {
		char *params = strsep(&str, ")");

		if (!params) {
			hist_err(tr, HIST_ERR_NO_SAVE_PARAMS, 0);
			ret = -EINVAL;
			goto out;
		}

		ret = parse_action_params(tr, params, data);
		if (ret)
			goto out;

		if (handler == HANDLER_ONMAX)
			data->track_data.check_val = check_track_val_max;
		else if (handler == HANDLER_ONCHANGE)
			data->track_data.check_val = check_track_val_changed;
		else {
			hist_err(tr, HIST_ERR_ACTION_MISMATCH, errpos(action_name));
			ret = -EINVAL;
			goto out;
		}

		data->track_data.save_data = save_track_data_vars;
		data->fn = ontrack_action;
		data->action = ACTION_SAVE;
	} else if (str_has_prefix(action_name, "snapshot")) {
		char *params = strsep(&str, ")");

		if (!str) {
			hist_err(tr, HIST_ERR_NO_CLOSING_PAREN, errpos(params));
			ret = -EINVAL;
			goto out;
		}

		if (handler == HANDLER_ONMAX)
			data->track_data.check_val = check_track_val_max;
		else if (handler == HANDLER_ONCHANGE)
			data->track_data.check_val = check_track_val_changed;
		else {
			hist_err(tr, HIST_ERR_ACTION_MISMATCH, errpos(action_name));
			ret = -EINVAL;
			goto out;
		}

		data->track_data.save_data = save_track_data_snapshot;
		data->fn = ontrack_action;
		data->action = ACTION_SNAPSHOT;
	} else {
		char *params = strsep(&str, ")");

		if (str_has_prefix(action_name, "trace"))
			data->use_trace_keyword = true;

		if (params) {
			ret = parse_action_params(tr, params, data);
			if (ret)
				goto out;
		}

		if (handler == HANDLER_ONMAX)
			data->track_data.check_val = check_track_val_max;
		else if (handler == HANDLER_ONCHANGE)
			data->track_data.check_val = check_track_val_changed;

		if (handler != HANDLER_ONMATCH) {
			data->track_data.save_data = action_trace;
			data->fn = ontrack_action;
		} else
			data->fn = action_trace;

		data->action = ACTION_TRACE;
	}

	data->action_name = kstrdup(action_name, GFP_KERNEL);
	if (!data->action_name) {
		ret = -ENOMEM;
		goto out;
	}

	data->handler = handler;
 out:
	return ret;
}

static struct action_data *track_data_parse(struct hist_trigger_data *hist_data,
					    char *str, enum handler_id handler)
{
	struct action_data *data;
	int ret = -EINVAL;
	char *var_str;

	data = kzalloc(sizeof(*data), GFP_KERNEL);
	if (!data)
		return ERR_PTR(-ENOMEM);

	var_str = strsep(&str, ")");
	if (!var_str || !str) {
		ret = -EINVAL;
		goto free;
	}

	data->track_data.var_str = kstrdup(var_str, GFP_KERNEL);
	if (!data->track_data.var_str) {
		ret = -ENOMEM;
		goto free;
	}

	ret = action_parse(hist_data->event_file->tr, str, data, handler);
	if (ret)
		goto free;
 out:
	return data;
 free:
	track_data_destroy(hist_data, data);
	data = ERR_PTR(ret);
	goto out;
}

static void onmatch_destroy(struct action_data *data)
{
	kfree(data->match_data.event);
	kfree(data->match_data.event_system);

	action_data_destroy(data);
}

static void destroy_field_var(struct field_var *field_var)
{
	if (!field_var)
		return;

	destroy_hist_field(field_var->var, 0);
	destroy_hist_field(field_var->val, 0);

	kfree(field_var);
}

static void destroy_field_vars(struct hist_trigger_data *hist_data)
{
	unsigned int i;

	for (i = 0; i < hist_data->n_field_vars; i++)
		destroy_field_var(hist_data->field_vars[i]);
}

static void save_field_var(struct hist_trigger_data *hist_data,
			   struct field_var *field_var)
{
	hist_data->field_vars[hist_data->n_field_vars++] = field_var;

	if (field_var->val->flags & HIST_FIELD_FL_STRING)
		hist_data->n_field_var_str++;
}


static int check_synth_field(struct synth_event *event,
			     struct hist_field *hist_field,
			     unsigned int field_pos)
{
	struct synth_field *field;

	if (field_pos >= event->n_fields)
		return -EINVAL;

	field = event->fields[field_pos];

	if (strcmp(field->type, hist_field->type) != 0) {
		if (field->size != hist_field->size ||
		    field->is_signed != hist_field->is_signed)
			return -EINVAL;
	}

	return 0;
}

static struct hist_field *
trace_action_find_var(struct hist_trigger_data *hist_data,
		      struct action_data *data,
		      char *system, char *event, char *var)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_field *hist_field;

	var++; /* skip '$' */

	hist_field = find_target_event_var(hist_data, system, event, var);
	if (!hist_field) {
		if (!system && data->handler == HANDLER_ONMATCH) {
			system = data->match_data.event_system;
			event = data->match_data.event;
		}

		hist_field = find_event_var(hist_data, system, event, var);
	}

	if (!hist_field)
		hist_err(tr, HIST_ERR_PARAM_NOT_FOUND, errpos(var));

	return hist_field;
}

static struct hist_field *
trace_action_create_field_var(struct hist_trigger_data *hist_data,
			      struct action_data *data, char *system,
			      char *event, char *var)
{
	struct hist_field *hist_field = NULL;
	struct field_var *field_var;

	/*
	 * First try to create a field var on the target event (the
	 * currently being defined).  This will create a variable for
	 * unqualified fields on the target event, or if qualified,
	 * target fields that have qualified names matching the target.
	 */
	field_var = create_target_field_var(hist_data, system, event, var);

	if (field_var && !IS_ERR(field_var)) {
		save_field_var(hist_data, field_var);
		hist_field = field_var->var;
	} else {
		field_var = NULL;
		/*
		 * If no explicit system.event is specfied, default to
		 * looking for fields on the onmatch(system.event.xxx)
		 * event.
		 */
		if (!system && data->handler == HANDLER_ONMATCH) {
			system = data->match_data.event_system;
			event = data->match_data.event;
		}

		/*
		 * At this point, we're looking at a field on another
		 * event.  Because we can't modify a hist trigger on
		 * another event to add a variable for a field, we need
		 * to create a new trigger on that event and create the
		 * variable at the same time.
		 */
		hist_field = create_field_var_hist(hist_data, system, event, var);
		if (IS_ERR(hist_field))
			goto free;
	}
 out:
	return hist_field;
 free:
	destroy_field_var(field_var);
	hist_field = NULL;
	goto out;
}

static int trace_action_create(struct hist_trigger_data *hist_data,
			       struct action_data *data)
{
	struct trace_array *tr = hist_data->event_file->tr;
	char *event_name, *param, *system = NULL;
	struct hist_field *hist_field, *var_ref;
	unsigned int i;
	unsigned int field_pos = 0;
	struct synth_event *event;
	char *synth_event_name;
	int var_ref_idx, ret = 0;

	lockdep_assert_held(&event_mutex);

	if (data->use_trace_keyword)
		synth_event_name = data->synth_event_name;
	else
		synth_event_name = data->action_name;

	event = find_synth_event(synth_event_name);
	if (!event) {
		hist_err(tr, HIST_ERR_SYNTH_EVENT_NOT_FOUND, errpos(synth_event_name));
		return -EINVAL;
	}

	event->ref++;

	for (i = 0; i < data->n_params; i++) {
		char *p;

		p = param = kstrdup(data->params[i], GFP_KERNEL);
		if (!param) {
			ret = -ENOMEM;
			goto err;
		}

		system = strsep(&param, ".");
		if (!param) {
			param = (char *)system;
			system = event_name = NULL;
		} else {
			event_name = strsep(&param, ".");
			if (!param) {
				kfree(p);
				ret = -EINVAL;
				goto err;
			}
		}

		if (param[0] == '$')
			hist_field = trace_action_find_var(hist_data, data,
							   system, event_name,
							   param);
		else
			hist_field = trace_action_create_field_var(hist_data,
								   data,
								   system,
								   event_name,
								   param);

		if (!hist_field) {
			kfree(p);
			ret = -EINVAL;
			goto err;
		}

		if (check_synth_field(event, hist_field, field_pos) == 0) {
			var_ref = create_var_ref(hist_data, hist_field,
						 system, event_name);
			if (!var_ref) {
				kfree(p);
				ret = -ENOMEM;
				goto err;
			}

			var_ref_idx = find_var_ref_idx(hist_data, var_ref);
			if (WARN_ON(var_ref_idx < 0)) {
				ret = var_ref_idx;
				goto err;
			}

			data->var_ref_idx[i] = var_ref_idx;

			field_pos++;
			kfree(p);
			continue;
		}

		hist_err(tr, HIST_ERR_SYNTH_TYPE_MISMATCH, errpos(param));
		kfree(p);
		ret = -EINVAL;
		goto err;
	}

	if (field_pos != event->n_fields) {
		hist_err(tr, HIST_ERR_SYNTH_COUNT_MISMATCH, errpos(event->name));
		ret = -EINVAL;
		goto err;
	}

	data->synth_event = event;
 out:
	return ret;
 err:
	event->ref--;

	goto out;
}

static int action_create(struct hist_trigger_data *hist_data,
			 struct action_data *data)
{
	struct trace_event_file *file = hist_data->event_file;
	struct trace_array *tr = file->tr;
	struct track_data *track_data;
	struct field_var *field_var;
	unsigned int i;
	char *param;
	int ret = 0;

	if (data->action == ACTION_TRACE)
		return trace_action_create(hist_data, data);

	if (data->action == ACTION_SNAPSHOT) {
		track_data = track_data_alloc(hist_data->key_size, data, hist_data);
		if (IS_ERR(track_data)) {
			ret = PTR_ERR(track_data);
			goto out;
		}

		ret = tracing_snapshot_cond_enable(file->tr, track_data,
						   cond_snapshot_update);
		if (ret)
			track_data_free(track_data);

		goto out;
	}

	if (data->action == ACTION_SAVE) {
		if (hist_data->n_save_vars) {
			ret = -EEXIST;
			hist_err(tr, HIST_ERR_TOO_MANY_SAVE_ACTIONS, 0);
			goto out;
		}

		for (i = 0; i < data->n_params; i++) {
			param = kstrdup(data->params[i], GFP_KERNEL);
			if (!param) {
				ret = -ENOMEM;
				goto out;
			}

			field_var = create_target_field_var(hist_data, NULL, NULL, param);
			if (IS_ERR(field_var)) {
				hist_err(tr, HIST_ERR_FIELD_VAR_CREATE_FAIL,
					 errpos(param));
				ret = PTR_ERR(field_var);
				kfree(param);
				goto out;
			}

			hist_data->save_vars[hist_data->n_save_vars++] = field_var;
			if (field_var->val->flags & HIST_FIELD_FL_STRING)
				hist_data->n_save_var_str++;
			kfree(param);
		}
	}
 out:
	return ret;
}

static int onmatch_create(struct hist_trigger_data *hist_data,
			  struct action_data *data)
{
	return action_create(hist_data, data);
}

static struct action_data *onmatch_parse(struct trace_array *tr, char *str)
{
	char *match_event, *match_event_system;
	struct action_data *data;
	int ret = -EINVAL;

	data = kzalloc(sizeof(*data), GFP_KERNEL);
	if (!data)
		return ERR_PTR(-ENOMEM);

	match_event = strsep(&str, ")");
	if (!match_event || !str) {
		hist_err(tr, HIST_ERR_NO_CLOSING_PAREN, errpos(match_event));
		goto free;
	}

	match_event_system = strsep(&match_event, ".");
	if (!match_event) {
		hist_err(tr, HIST_ERR_SUBSYS_NOT_FOUND, errpos(match_event_system));
		goto free;
	}

	if (IS_ERR(event_file(tr, match_event_system, match_event))) {
		hist_err(tr, HIST_ERR_INVALID_SUBSYS_EVENT, errpos(match_event));
		goto free;
	}

	data->match_data.event = kstrdup(match_event, GFP_KERNEL);
	if (!data->match_data.event) {
		ret = -ENOMEM;
		goto free;
	}

	data->match_data.event_system = kstrdup(match_event_system, GFP_KERNEL);
	if (!data->match_data.event_system) {
		ret = -ENOMEM;
		goto free;
	}

	ret = action_parse(tr, str, data, HANDLER_ONMATCH);
	if (ret)
		goto free;
 out:
	return data;
 free:
	onmatch_destroy(data);
	data = ERR_PTR(ret);
	goto out;
}

static int create_hitcount_val(struct hist_trigger_data *hist_data)
{
	hist_data->fields[HITCOUNT_IDX] =
		create_hist_field(hist_data, NULL, HIST_FIELD_FL_HITCOUNT, NULL);
	if (!hist_data->fields[HITCOUNT_IDX])
		return -ENOMEM;

	hist_data->n_vals++;
	hist_data->n_fields++;

	if (WARN_ON(hist_data->n_vals > TRACING_MAP_VALS_MAX))
		return -EINVAL;

	return 0;
}

static int __create_val_field(struct hist_trigger_data *hist_data,
			      unsigned int val_idx,
			      struct trace_event_file *file,
			      char *var_name, char *field_str,
			      unsigned long flags)
{
	struct hist_field *hist_field;
	int ret = 0;

	hist_field = parse_expr(hist_data, file, field_str, flags, var_name, 0);
	if (IS_ERR(hist_field)) {
		ret = PTR_ERR(hist_field);
		goto out;
	}

	hist_data->fields[val_idx] = hist_field;

	++hist_data->n_vals;
	++hist_data->n_fields;

	if (WARN_ON(hist_data->n_vals > TRACING_MAP_VALS_MAX + TRACING_MAP_VARS_MAX))
		ret = -EINVAL;
 out:
	return ret;
}

static int create_val_field(struct hist_trigger_data *hist_data,
			    unsigned int val_idx,
			    struct trace_event_file *file,
			    char *field_str)
{
	if (WARN_ON(val_idx >= TRACING_MAP_VALS_MAX))
		return -EINVAL;

	return __create_val_field(hist_data, val_idx, file, NULL, field_str, 0);
}

static int create_var_field(struct hist_trigger_data *hist_data,
			    unsigned int val_idx,
			    struct trace_event_file *file,
			    char *var_name, char *expr_str)
{
	struct trace_array *tr = hist_data->event_file->tr;
	unsigned long flags = 0;

	if (WARN_ON(val_idx >= TRACING_MAP_VALS_MAX + TRACING_MAP_VARS_MAX))
		return -EINVAL;

	if (find_var(hist_data, file, var_name) && !hist_data->remove) {
		hist_err(tr, HIST_ERR_DUPLICATE_VAR, errpos(var_name));
		return -EINVAL;
	}

	flags |= HIST_FIELD_FL_VAR;
	hist_data->n_vars++;
	if (WARN_ON(hist_data->n_vars > TRACING_MAP_VARS_MAX))
		return -EINVAL;

	return __create_val_field(hist_data, val_idx, file, var_name, expr_str, flags);
}

static int create_val_fields(struct hist_trigger_data *hist_data,
			     struct trace_event_file *file)
{
	char *fields_str, *field_str;
	unsigned int i, j = 1;
	int ret;

	ret = create_hitcount_val(hist_data);
	if (ret)
		goto out;

	fields_str = hist_data->attrs->vals_str;
	if (!fields_str)
		goto out;

	for (i = 0, j = 1; i < TRACING_MAP_VALS_MAX &&
		     j < TRACING_MAP_VALS_MAX; i++) {
		field_str = strsep(&fields_str, ",");
		if (!field_str)
			break;

		if (strcmp(field_str, "hitcount") == 0)
			continue;

		ret = create_val_field(hist_data, j++, file, field_str);
		if (ret)
			goto out;
	}

	if (fields_str && (strcmp(fields_str, "hitcount") != 0))
		ret = -EINVAL;
 out:
	return ret;
}

static int create_key_field(struct hist_trigger_data *hist_data,
			    unsigned int key_idx,
			    unsigned int key_offset,
			    struct trace_event_file *file,
			    char *field_str)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct hist_field *hist_field = NULL;
	unsigned long flags = 0;
	unsigned int key_size;
	int ret = 0;

	if (WARN_ON(key_idx >= HIST_FIELDS_MAX))
		return -EINVAL;

	flags |= HIST_FIELD_FL_KEY;

	if (strcmp(field_str, "stacktrace") == 0) {
		flags |= HIST_FIELD_FL_STACKTRACE;
		key_size = sizeof(unsigned long) * HIST_STACKTRACE_DEPTH;
		hist_field = create_hist_field(hist_data, NULL, flags, NULL);
	} else {
		hist_field = parse_expr(hist_data, file, field_str, flags,
					NULL, 0);
		if (IS_ERR(hist_field)) {
			ret = PTR_ERR(hist_field);
			goto out;
		}

		if (field_has_hist_vars(hist_field, 0))	{
			hist_err(tr, HIST_ERR_INVALID_REF_KEY, errpos(field_str));
			destroy_hist_field(hist_field, 0);
			ret = -EINVAL;
			goto out;
		}

		key_size = hist_field->size;
	}

	hist_data->fields[key_idx] = hist_field;

	key_size = ALIGN(key_size, sizeof(u64));
	hist_data->fields[key_idx]->size = key_size;
	hist_data->fields[key_idx]->offset = key_offset;

	hist_data->key_size += key_size;

	if (hist_data->key_size > HIST_KEY_SIZE_MAX) {
		ret = -EINVAL;
		goto out;
	}

	hist_data->n_keys++;
	hist_data->n_fields++;

	if (WARN_ON(hist_data->n_keys > TRACING_MAP_KEYS_MAX))
		return -EINVAL;

	ret = key_size;
 out:
	return ret;
}

static int create_key_fields(struct hist_trigger_data *hist_data,
			     struct trace_event_file *file)
{
	unsigned int i, key_offset = 0, n_vals = hist_data->n_vals;
	char *fields_str, *field_str;
	int ret = -EINVAL;

	fields_str = hist_data->attrs->keys_str;
	if (!fields_str)
		goto out;

	for (i = n_vals; i < n_vals + TRACING_MAP_KEYS_MAX; i++) {
		field_str = strsep(&fields_str, ",");
		if (!field_str)
			break;
		ret = create_key_field(hist_data, i, key_offset,
				       file, field_str);
		if (ret < 0)
			goto out;
		key_offset += ret;
	}
	if (fields_str) {
		ret = -EINVAL;
		goto out;
	}
	ret = 0;
 out:
	return ret;
}

static int create_var_fields(struct hist_trigger_data *hist_data,
			     struct trace_event_file *file)
{
	unsigned int i, j = hist_data->n_vals;
	int ret = 0;

	unsigned int n_vars = hist_data->attrs->var_defs.n_vars;

	for (i = 0; i < n_vars; i++) {
		char *var_name = hist_data->attrs->var_defs.name[i];
		char *expr = hist_data->attrs->var_defs.expr[i];

		ret = create_var_field(hist_data, j++, file, var_name, expr);
		if (ret)
			goto out;
	}
 out:
	return ret;
}

static void free_var_defs(struct hist_trigger_data *hist_data)
{
	unsigned int i;

	for (i = 0; i < hist_data->attrs->var_defs.n_vars; i++) {
		kfree(hist_data->attrs->var_defs.name[i]);
		kfree(hist_data->attrs->var_defs.expr[i]);
	}

	hist_data->attrs->var_defs.n_vars = 0;
}

static int parse_var_defs(struct hist_trigger_data *hist_data)
{
	struct trace_array *tr = hist_data->event_file->tr;
	char *s, *str, *var_name, *field_str;
	unsigned int i, j, n_vars = 0;
	int ret = 0;

	for (i = 0; i < hist_data->attrs->n_assignments; i++) {
		str = hist_data->attrs->assignment_str[i];
		for (j = 0; j < TRACING_MAP_VARS_MAX; j++) {
			field_str = strsep(&str, ",");
			if (!field_str)
				break;

			var_name = strsep(&field_str, "=");
			if (!var_name || !field_str) {
				hist_err(tr, HIST_ERR_MALFORMED_ASSIGNMENT,
					 errpos(var_name));
				ret = -EINVAL;
				goto free;
			}

			if (n_vars == TRACING_MAP_VARS_MAX) {
				hist_err(tr, HIST_ERR_TOO_MANY_VARS, errpos(var_name));
				ret = -EINVAL;
				goto free;
			}

			s = kstrdup(var_name, GFP_KERNEL);
			if (!s) {
				ret = -ENOMEM;
				goto free;
			}
			hist_data->attrs->var_defs.name[n_vars] = s;

			s = kstrdup(field_str, GFP_KERNEL);
			if (!s) {
				kfree(hist_data->attrs->var_defs.name[n_vars]);
				ret = -ENOMEM;
				goto free;
			}
			hist_data->attrs->var_defs.expr[n_vars++] = s;

			hist_data->attrs->var_defs.n_vars = n_vars;
		}
	}

	return ret;
 free:
	free_var_defs(hist_data);

	return ret;
}

static int create_hist_fields(struct hist_trigger_data *hist_data,
			      struct trace_event_file *file)
{
	int ret;

	ret = parse_var_defs(hist_data);
	if (ret)
		goto out;

	ret = create_val_fields(hist_data, file);
	if (ret)
		goto out;

	ret = create_var_fields(hist_data, file);
	if (ret)
		goto out;

	ret = create_key_fields(hist_data, file);
	if (ret)
		goto out;
 out:
	free_var_defs(hist_data);

	return ret;
}

static int is_descending(struct trace_array *tr, const char *str)
{
	if (!str)
		return 0;

	if (strcmp(str, "descending") == 0)
		return 1;

	if (strcmp(str, "ascending") == 0)
		return 0;

	hist_err(tr, HIST_ERR_INVALID_SORT_MODIFIER, errpos((char *)str));

	return -EINVAL;
}

static int create_sort_keys(struct hist_trigger_data *hist_data)
{
	struct trace_array *tr = hist_data->event_file->tr;
	char *fields_str = hist_data->attrs->sort_key_str;
	struct tracing_map_sort_key *sort_key;
	int descending, ret = 0;
	unsigned int i, j, k;

	hist_data->n_sort_keys = 1; /* we always have at least one, hitcount */

	if (!fields_str)
		goto out;

	for (i = 0; i < TRACING_MAP_SORT_KEYS_MAX; i++) {
		struct hist_field *hist_field;
		char *field_str, *field_name;
		const char *test_name;

		sort_key = &hist_data->sort_keys[i];

		field_str = strsep(&fields_str, ",");
		if (!field_str)
			break;

		if (!*field_str) {
			ret = -EINVAL;
			hist_err(tr, HIST_ERR_EMPTY_SORT_FIELD, errpos("sort="));
			break;
		}

		if ((i == TRACING_MAP_SORT_KEYS_MAX - 1) && fields_str) {
			hist_err(tr, HIST_ERR_TOO_MANY_SORT_FIELDS, errpos("sort="));
			ret = -EINVAL;
			break;
		}

		field_name = strsep(&field_str, ".");
		if (!field_name || !*field_name) {
			ret = -EINVAL;
			hist_err(tr, HIST_ERR_EMPTY_SORT_FIELD, errpos("sort="));
			break;
		}

		if (strcmp(field_name, "hitcount") == 0) {
			descending = is_descending(tr, field_str);
			if (descending < 0) {
				ret = descending;
				break;
			}
			sort_key->descending = descending;
			continue;
		}

		for (j = 1, k = 1; j < hist_data->n_fields; j++) {
			unsigned int idx;

			hist_field = hist_data->fields[j];
			if (hist_field->flags & HIST_FIELD_FL_VAR)
				continue;

			idx = k++;

			test_name = hist_field_name(hist_field, 0);

			if (strcmp(field_name, test_name) == 0) {
				sort_key->field_idx = idx;
				descending = is_descending(tr, field_str);
				if (descending < 0) {
					ret = descending;
					goto out;
				}
				sort_key->descending = descending;
				break;
			}
		}
		if (j == hist_data->n_fields) {
			ret = -EINVAL;
			hist_err(tr, HIST_ERR_INVALID_SORT_FIELD, errpos(field_name));
			break;
		}
	}

	hist_data->n_sort_keys = i;
 out:
	return ret;
}

static void destroy_actions(struct hist_trigger_data *hist_data)
{
	unsigned int i;

	for (i = 0; i < hist_data->n_actions; i++) {
		struct action_data *data = hist_data->actions[i];

		if (data->handler == HANDLER_ONMATCH)
			onmatch_destroy(data);
		else if (data->handler == HANDLER_ONMAX ||
			 data->handler == HANDLER_ONCHANGE)
			track_data_destroy(hist_data, data);
		else
			kfree(data);
	}
}

static int parse_actions(struct hist_trigger_data *hist_data)
{
	struct trace_array *tr = hist_data->event_file->tr;
	struct action_data *data;
	unsigned int i;
	int ret = 0;
	char *str;
	int len;

	for (i = 0; i < hist_data->attrs->n_actions; i++) {
		str = hist_data->attrs->action_str[i];

		if ((len = str_has_prefix(str, "onmatch("))) {
			char *action_str = str + len;

			data = onmatch_parse(tr, action_str);
			if (IS_ERR(data)) {
				ret = PTR_ERR(data);
				break;
			}
		} else if ((len = str_has_prefix(str, "onmax("))) {
			char *action_str = str + len;

			data = track_data_parse(hist_data, action_str,
						HANDLER_ONMAX);
			if (IS_ERR(data)) {
				ret = PTR_ERR(data);
				break;
			}
		} else if ((len = str_has_prefix(str, "onchange("))) {
			char *action_str = str + len;

			data = track_data_parse(hist_data, action_str,
						HANDLER_ONCHANGE);
			if (IS_ERR(data)) {
				ret = PTR_ERR(data);
				break;
			}
		} else {
			ret = -EINVAL;
			break;
		}

		hist_data->actions[hist_data->n_actions++] = data;
	}

	return ret;
}

static int create_actions(struct hist_trigger_data *hist_data)
{
	struct action_data *data;
	unsigned int i;
	int ret = 0;

	for (i = 0; i < hist_data->attrs->n_actions; i++) {
		data = hist_data->actions[i];

		if (data->handler == HANDLER_ONMATCH) {
			ret = onmatch_create(hist_data, data);
			if (ret)
				break;
		} else if (data->handler == HANDLER_ONMAX ||
			   data->handler == HANDLER_ONCHANGE) {
			ret = track_data_create(hist_data, data);
			if (ret)
				break;
		} else {
			ret = -EINVAL;
			break;
		}
	}

	return ret;
}

static void print_actions(struct seq_file *m,
			  struct hist_trigger_data *hist_data,
			  struct tracing_map_elt *elt)
{
	unsigned int i;

	for (i = 0; i < hist_data->n_actions; i++) {
		struct action_data *data = hist_data->actions[i];

		if (data->action == ACTION_SNAPSHOT)
			continue;

		if (data->handler == HANDLER_ONMAX ||
		    data->handler == HANDLER_ONCHANGE)
			track_data_print(m, hist_data, elt, data);
	}
}

static void print_action_spec(struct seq_file *m,
			      struct hist_trigger_data *hist_data,
			      struct action_data *data)
{
	unsigned int i;

	if (data->action == ACTION_SAVE) {
		for (i = 0; i < hist_data->n_save_vars; i++) {
			seq_printf(m, "%s", hist_data->save_vars[i]->var->var.name);
			if (i < hist_data->n_save_vars - 1)
				seq_puts(m, ",");
		}
	} else if (data->action == ACTION_TRACE) {
		if (data->use_trace_keyword)
			seq_printf(m, "%s", data->synth_event_name);
		for (i = 0; i < data->n_params; i++) {
			if (i || data->use_trace_keyword)
				seq_puts(m, ",");
			seq_printf(m, "%s", data->params[i]);
		}
	}
}

static void print_track_data_spec(struct seq_file *m,
				  struct hist_trigger_data *hist_data,
				  struct action_data *data)
{
	if (data->handler == HANDLER_ONMAX)
		seq_puts(m, ":onmax(");
	else if (data->handler == HANDLER_ONCHANGE)
		seq_puts(m, ":onchange(");
	seq_printf(m, "%s", data->track_data.var_str);
	seq_printf(m, ").%s(", data->action_name);

	print_action_spec(m, hist_data, data);

	seq_puts(m, ")");
}

static void print_onmatch_spec(struct seq_file *m,
			       struct hist_trigger_data *hist_data,
			       struct action_data *data)
{
	seq_printf(m, ":onmatch(%s.%s).", data->match_data.event_system,
		   data->match_data.event);

	seq_printf(m, "%s(", data->action_name);

	print_action_spec(m, hist_data, data);

	seq_puts(m, ")");
}

static bool actions_match(struct hist_trigger_data *hist_data,
			  struct hist_trigger_data *hist_data_test)
{
	unsigned int i, j;

	if (hist_data->n_actions != hist_data_test->n_actions)
		return false;

	for (i = 0; i < hist_data->n_actions; i++) {
		struct action_data *data = hist_data->actions[i];
		struct action_data *data_test = hist_data_test->actions[i];
		char *action_name, *action_name_test;

		if (data->handler != data_test->handler)
			return false;
		if (data->action != data_test->action)
			return false;

		if (data->n_params != data_test->n_params)
			return false;

		for (j = 0; j < data->n_params; j++) {
			if (strcmp(data->params[j], data_test->params[j]) != 0)
				return false;
		}

		if (data->use_trace_keyword)
			action_name = data->synth_event_name;
		else
			action_name = data->action_name;

		if (data_test->use_trace_keyword)
			action_name_test = data_test->synth_event_name;
		else
			action_name_test = data_test->action_name;

		if (strcmp(action_name, action_name_test) != 0)
			return false;

		if (data->handler == HANDLER_ONMATCH) {
			if (strcmp(data->match_data.event_system,
				   data_test->match_data.event_system) != 0)
				return false;
			if (strcmp(data->match_data.event,
				   data_test->match_data.event) != 0)
				return false;
		} else if (data->handler == HANDLER_ONMAX ||
			   data->handler == HANDLER_ONCHANGE) {
			if (strcmp(data->track_data.var_str,
				   data_test->track_data.var_str) != 0)
				return false;
		}
	}

	return true;
}


static void print_actions_spec(struct seq_file *m,
			       struct hist_trigger_data *hist_data)
{
	unsigned int i;

	for (i = 0; i < hist_data->n_actions; i++) {
		struct action_data *data = hist_data->actions[i];

		if (data->handler == HANDLER_ONMATCH)
			print_onmatch_spec(m, hist_data, data);
		else if (data->handler == HANDLER_ONMAX ||
			 data->handler == HANDLER_ONCHANGE)
			print_track_data_spec(m, hist_data, data);
	}
}

static void destroy_field_var_hists(struct hist_trigger_data *hist_data)
{
	unsigned int i;

	for (i = 0; i < hist_data->n_field_var_hists; i++) {
		kfree(hist_data->field_var_hists[i]->cmd);
		kfree(hist_data->field_var_hists[i]);
	}
}

static void destroy_hist_data(struct hist_trigger_data *hist_data)
{
	if (!hist_data)
		return;

	destroy_hist_trigger_attrs(hist_data->attrs);
	destroy_hist_fields(hist_data);
	tracing_map_destroy(hist_data->map);

	destroy_actions(hist_data);
	destroy_field_vars(hist_data);
	destroy_field_var_hists(hist_data);

	kfree(hist_data);
}

static int create_tracing_map_fields(struct hist_trigger_data *hist_data)
{
	struct tracing_map *map = hist_data->map;
	struct ftrace_event_field *field;
	struct hist_field *hist_field;
	int i, idx = 0;

	for_each_hist_field(i, hist_data) {
		hist_field = hist_data->fields[i];
		if (hist_field->flags & HIST_FIELD_FL_KEY) {
			tracing_map_cmp_fn_t cmp_fn;

			field = hist_field->field;

			if (hist_field->flags & HIST_FIELD_FL_STACKTRACE)
				cmp_fn = tracing_map_cmp_none;
			else if (!field)
				cmp_fn = tracing_map_cmp_num(hist_field->size,
							     hist_field->is_signed);
			else if (is_string_field(field))
				cmp_fn = tracing_map_cmp_string;
			else
				cmp_fn = tracing_map_cmp_num(field->size,
							     field->is_signed);
			idx = tracing_map_add_key_field(map,
							hist_field->offset,
							cmp_fn);
		} else if (!(hist_field->flags & HIST_FIELD_FL_VAR))
			idx = tracing_map_add_sum_field(map);

		if (idx < 0)
			return idx;

		if (hist_field->flags & HIST_FIELD_FL_VAR) {
			idx = tracing_map_add_var(map);
			if (idx < 0)
				return idx;
			hist_field->var.idx = idx;
			hist_field->var.hist_data = hist_data;
		}
	}

	return 0;
}

static struct hist_trigger_data *
create_hist_data(unsigned int map_bits,
		 struct hist_trigger_attrs *attrs,
		 struct trace_event_file *file,
		 bool remove)
{
	const struct tracing_map_ops *map_ops = NULL;
	struct hist_trigger_data *hist_data;
	int ret = 0;

	hist_data = kzalloc(sizeof(*hist_data), GFP_KERNEL);
	if (!hist_data)
		return ERR_PTR(-ENOMEM);

	hist_data->attrs = attrs;
	hist_data->remove = remove;
	hist_data->event_file = file;

	ret = parse_actions(hist_data);
	if (ret)
		goto free;

	ret = create_hist_fields(hist_data, file);
	if (ret)
		goto free;

	ret = create_sort_keys(hist_data);
	if (ret)
		goto free;

	map_ops = &hist_trigger_elt_data_ops;

	hist_data->map = tracing_map_create(map_bits, hist_data->key_size,
					    map_ops, hist_data);
	if (IS_ERR(hist_data->map)) {
		ret = PTR_ERR(hist_data->map);
		hist_data->map = NULL;
		goto free;
	}

	ret = create_tracing_map_fields(hist_data);
	if (ret)
		goto free;
 out:
	return hist_data;
 free:
	hist_data->attrs = NULL;

	destroy_hist_data(hist_data);

	hist_data = ERR_PTR(ret);

	goto out;
}

static void hist_trigger_elt_update(struct hist_trigger_data *hist_data,
				    struct tracing_map_elt *elt, void *rec,
				    struct ring_buffer_event *rbe,
				    u64 *var_ref_vals)
{
	struct hist_elt_data *elt_data;
	struct hist_field *hist_field;
	unsigned int i, var_idx;
	u64 hist_val;

	elt_data = elt->private_data;
	elt_data->var_ref_vals = var_ref_vals;

	for_each_hist_val_field(i, hist_data) {
		hist_field = hist_data->fields[i];
		hist_val = hist_field->fn(hist_field, elt, rbe, rec);
		if (hist_field->flags & HIST_FIELD_FL_VAR) {
			var_idx = hist_field->var.idx;
			tracing_map_set_var(elt, var_idx, hist_val);
			continue;
		}
		tracing_map_update_sum(elt, i, hist_val);
	}

	for_each_hist_key_field(i, hist_data) {
		hist_field = hist_data->fields[i];
		if (hist_field->flags & HIST_FIELD_FL_VAR) {
			hist_val = hist_field->fn(hist_field, elt, rbe, rec);
			var_idx = hist_field->var.idx;
			tracing_map_set_var(elt, var_idx, hist_val);
		}
	}

	update_field_vars(hist_data, elt, rbe, rec);
}

static inline void add_to_key(char *compound_key, void *key,
			      struct hist_field *key_field, void *rec)
{
	size_t size = key_field->size;

	if (key_field->flags & HIST_FIELD_FL_STRING) {
		struct ftrace_event_field *field;

		field = key_field->field;
		if (field->filter_type == FILTER_DYN_STRING)
			size = *(u32 *)(rec + field->offset) >> 16;
		else if (field->filter_type == FILTER_PTR_STRING)
			size = strlen(key);
		else if (field->filter_type == FILTER_STATIC_STRING)
			size = field->size;

		/* ensure NULL-termination */
		if (size > key_field->size - 1)
			size = key_field->size - 1;

		strncpy(compound_key + key_field->offset, (char *)key, size);
	} else
		memcpy(compound_key + key_field->offset, key, size);
}

static void
hist_trigger_actions(struct hist_trigger_data *hist_data,
		     struct tracing_map_elt *elt, void *rec,
		     struct ring_buffer_event *rbe, void *key,
		     u64 *var_ref_vals)
{
	struct action_data *data;
	unsigned int i;

	for (i = 0; i < hist_data->n_actions; i++) {
		data = hist_data->actions[i];
		data->fn(hist_data, elt, rec, rbe, key, data, var_ref_vals);
	}
}

static void event_hist_trigger(struct event_trigger_data *data, void *rec,
			       struct ring_buffer_event *rbe)
{
	struct hist_trigger_data *hist_data = data->private_data;
	bool use_compound_key = (hist_data->n_keys > 1);
	unsigned long entries[HIST_STACKTRACE_DEPTH];
	u64 var_ref_vals[TRACING_MAP_VARS_MAX];
	char compound_key[HIST_KEY_SIZE_MAX];
	struct tracing_map_elt *elt = NULL;
	struct hist_field *key_field;
	u64 field_contents;
	void *key = NULL;
	unsigned int i;

	memset(compound_key, 0, hist_data->key_size);

	for_each_hist_key_field(i, hist_data) {
		key_field = hist_data->fields[i];

		if (key_field->flags & HIST_FIELD_FL_STACKTRACE) {
			memset(entries, 0, HIST_STACKTRACE_SIZE);
			stack_trace_save(entries, HIST_STACKTRACE_DEPTH,
					 HIST_STACKTRACE_SKIP);
			key = entries;
		} else {
			field_contents = key_field->fn(key_field, elt, rbe, rec);
			if (key_field->flags & HIST_FIELD_FL_STRING) {
				key = (void *)(unsigned long)field_contents;
				use_compound_key = true;
			} else
				key = (void *)&field_contents;
		}

		if (use_compound_key)
			add_to_key(compound_key, key, key_field, rec);
	}

	if (use_compound_key)
		key = compound_key;

	if (hist_data->n_var_refs &&
	    !resolve_var_refs(hist_data, key, var_ref_vals, false))
		return;

	elt = tracing_map_insert(hist_data->map, key);
	if (!elt)
		return;

	hist_trigger_elt_update(hist_data, elt, rec, rbe, var_ref_vals);

	if (resolve_var_refs(hist_data, key, var_ref_vals, true))
		hist_trigger_actions(hist_data, elt, rec, rbe, key, var_ref_vals);
}

static void hist_trigger_stacktrace_print(struct seq_file *m,
					  unsigned long *stacktrace_entries,
					  unsigned int max_entries)
{
	char str[KSYM_SYMBOL_LEN];
	unsigned int spaces = 8;
	unsigned int i;

	for (i = 0; i < max_entries; i++) {
		if (!stacktrace_entries[i])
			return;

		seq_printf(m, "%*c", 1 + spaces, ' ');
		sprint_symbol(str, stacktrace_entries[i]);
		seq_printf(m, "%s\n", str);
	}
}

static void hist_trigger_print_key(struct seq_file *m,
				   struct hist_trigger_data *hist_data,
				   void *key,
				   struct tracing_map_elt *elt)
{
	struct hist_field *key_field;
	char str[KSYM_SYMBOL_LEN];
	bool multiline = false;
	const char *field_name;
	unsigned int i;
	u64 uval;

	seq_puts(m, "{ ");

	for_each_hist_key_field(i, hist_data) {
		key_field = hist_data->fields[i];

		if (i > hist_data->n_vals)
			seq_puts(m, ", ");

		field_name = hist_field_name(key_field, 0);

		if (key_field->flags & HIST_FIELD_FL_HEX) {
			uval = *(u64 *)(key + key_field->offset);
			seq_printf(m, "%s: %llx", field_name, uval);
		} else if (key_field->flags & HIST_FIELD_FL_SYM) {
			uval = *(u64 *)(key + key_field->offset);
			sprint_symbol_no_offset(str, uval);
			seq_printf(m, "%s: [%llx] %-45s", field_name,
				   uval, str);
		} else if (key_field->flags & HIST_FIELD_FL_SYM_OFFSET) {
			uval = *(u64 *)(key + key_field->offset);
			sprint_symbol(str, uval);
			seq_printf(m, "%s: [%llx] %-55s", field_name,
				   uval, str);
		} else if (key_field->flags & HIST_FIELD_FL_EXECNAME) {
			struct hist_elt_data *elt_data = elt->private_data;
			char *comm;

			if (WARN_ON_ONCE(!elt_data))
				return;

			comm = elt_data->comm;

			uval = *(u64 *)(key + key_field->offset);
			seq_printf(m, "%s: %-16s[%10llu]", field_name,
				   comm, uval);
		} else if (key_field->flags & HIST_FIELD_FL_SYSCALL) {
			const char *syscall_name;

			uval = *(u64 *)(key + key_field->offset);
			syscall_name = get_syscall_name(uval);
			if (!syscall_name)
				syscall_name = "unknown_syscall";

			seq_printf(m, "%s: %-30s[%3llu]", field_name,
				   syscall_name, uval);
		} else if (key_field->flags & HIST_FIELD_FL_STACKTRACE) {
			seq_puts(m, "stacktrace:\n");
			hist_trigger_stacktrace_print(m,
						      key + key_field->offset,
						      HIST_STACKTRACE_DEPTH);
			multiline = true;
		} else if (key_field->flags & HIST_FIELD_FL_LOG2) {
			seq_printf(m, "%s: ~ 2^%-2llu", field_name,
				   *(u64 *)(key + key_field->offset));
		} else if (key_field->flags & HIST_FIELD_FL_STRING) {
			seq_printf(m, "%s: %-50s", field_name,
				   (char *)(key + key_field->offset));
		} else {
			uval = *(u64 *)(key + key_field->offset);
			seq_printf(m, "%s: %10llu", field_name, uval);
		}
	}

	if (!multiline)
		seq_puts(m, " ");

	seq_puts(m, "}");
}

static void hist_trigger_entry_print(struct seq_file *m,
				     struct hist_trigger_data *hist_data,
				     void *key,
				     struct tracing_map_elt *elt)
{
	const char *field_name;
	unsigned int i;

	hist_trigger_print_key(m, hist_data, key, elt);

	seq_printf(m, " hitcount: %10llu",
		   tracing_map_read_sum(elt, HITCOUNT_IDX));

	for (i = 1; i < hist_data->n_vals; i++) {
		field_name = hist_field_name(hist_data->fields[i], 0);

		if (hist_data->fields[i]->flags & HIST_FIELD_FL_VAR ||
		    hist_data->fields[i]->flags & HIST_FIELD_FL_EXPR)
			continue;

		if (hist_data->fields[i]->flags & HIST_FIELD_FL_HEX) {
			seq_printf(m, "  %s: %10llx", field_name,
				   tracing_map_read_sum(elt, i));
		} else {
			seq_printf(m, "  %s: %10llu", field_name,
				   tracing_map_read_sum(elt, i));
		}
	}

	print_actions(m, hist_data, elt);

	seq_puts(m, "\n");
}

static int print_entries(struct seq_file *m,
			 struct hist_trigger_data *hist_data)
{
	struct tracing_map_sort_entry **sort_entries = NULL;
	struct tracing_map *map = hist_data->map;
	int i, n_entries;

	n_entries = tracing_map_sort_entries(map, hist_data->sort_keys,
					     hist_data->n_sort_keys,
					     &sort_entries);
	if (n_entries < 0)
		return n_entries;

	for (i = 0; i < n_entries; i++)
		hist_trigger_entry_print(m, hist_data,
					 sort_entries[i]->key,
					 sort_entries[i]->elt);

	tracing_map_destroy_sort_entries(sort_entries, n_entries);

	return n_entries;
}

static void hist_trigger_show(struct seq_file *m,
			      struct event_trigger_data *data, int n)
{
	struct hist_trigger_data *hist_data;
	int n_entries;

	if (n > 0)
		seq_puts(m, "\n\n");

	seq_puts(m, "# event histogram\n#\n# trigger info: ");
	data->ops->print(m, data->ops, data);
	seq_puts(m, "#\n\n");

	hist_data = data->private_data;
	n_entries = print_entries(m, hist_data);
	if (n_entries < 0)
		n_entries = 0;

	track_data_snapshot_print(m, hist_data);

	seq_printf(m, "\nTotals:\n    Hits: %llu\n    Entries: %u\n    Dropped: %llu\n",
		   (u64)atomic64_read(&hist_data->map->hits),
		   n_entries, (u64)atomic64_read(&hist_data->map->drops));
}

static int hist_show(struct seq_file *m, void *v)
{
	struct event_trigger_data *data;
	struct trace_event_file *event_file;
	int n = 0, ret = 0;

	mutex_lock(&event_mutex);

	event_file = event_file_data(m->private);
	if (unlikely(!event_file)) {
		ret = -ENODEV;
		goto out_unlock;
	}

	list_for_each_entry(data, &event_file->triggers, list) {
		if (data->cmd_ops->trigger_type == ETT_EVENT_HIST)
			hist_trigger_show(m, data, n++);
	}

 out_unlock:
	mutex_unlock(&event_mutex);

	return ret;
}

static int event_hist_open(struct inode *inode, struct file *file)
{
	int ret;

	ret = security_locked_down(LOCKDOWN_TRACEFS);
	if (ret)
		return ret;

	return single_open(file, hist_show, file);
}

const struct file_operations event_hist_fops = {
	.open = event_hist_open,
	.read = seq_read,
	.llseek = seq_lseek,
	.release = single_release,
};

static void hist_field_print(struct seq_file *m, struct hist_field *hist_field)
{
	const char *field_name = hist_field_name(hist_field, 0);

	if (hist_field->var.name)
		seq_printf(m, "%s=", hist_field->var.name);

	if (hist_field->flags & HIST_FIELD_FL_CPU)
		seq_puts(m, "cpu");
	else if (field_name) {
		if (hist_field->flags & HIST_FIELD_FL_VAR_REF ||
		    hist_field->flags & HIST_FIELD_FL_ALIAS)
			seq_putc(m, '$');
		seq_printf(m, "%s", field_name);
	} else if (hist_field->flags & HIST_FIELD_FL_TIMESTAMP)
		seq_puts(m, "common_timestamp");

	if (hist_field->flags) {
		if (!(hist_field->flags & HIST_FIELD_FL_VAR_REF) &&
		    !(hist_field->flags & HIST_FIELD_FL_EXPR)) {
			const char *flags = get_hist_field_flags(hist_field);

			if (flags)
				seq_printf(m, ".%s", flags);
		}
	}
}

static int event_hist_trigger_print(struct seq_file *m,
				    struct event_trigger_ops *ops,
				    struct event_trigger_data *data)
{
	struct hist_trigger_data *hist_data = data->private_data;
	struct hist_field *field;
	bool have_var = false;
	unsigned int i;

	seq_puts(m, "hist:");

	if (data->name)
		seq_printf(m, "%s:", data->name);

	seq_puts(m, "keys=");

	for_each_hist_key_field(i, hist_data) {
		field = hist_data->fields[i];

		if (i > hist_data->n_vals)
			seq_puts(m, ",");

		if (field->flags & HIST_FIELD_FL_STACKTRACE)
			seq_puts(m, "stacktrace");
		else
			hist_field_print(m, field);
	}

	seq_puts(m, ":vals=");

	for_each_hist_val_field(i, hist_data) {
		field = hist_data->fields[i];
		if (field->flags & HIST_FIELD_FL_VAR) {
			have_var = true;
			continue;
		}

		if (i == HITCOUNT_IDX)
			seq_puts(m, "hitcount");
		else {
			seq_puts(m, ",");
			hist_field_print(m, field);
		}
	}

	if (have_var) {
		unsigned int n = 0;

		seq_puts(m, ":");

		for_each_hist_val_field(i, hist_data) {
			field = hist_data->fields[i];

			if (field->flags & HIST_FIELD_FL_VAR) {
				if (n++)
					seq_puts(m, ",");
				hist_field_print(m, field);
			}
		}
	}

	seq_puts(m, ":sort=");

	for (i = 0; i < hist_data->n_sort_keys; i++) {
		struct tracing_map_sort_key *sort_key;
		unsigned int idx, first_key_idx;

		/* skip VAR vals */
		first_key_idx = hist_data->n_vals - hist_data->n_vars;

		sort_key = &hist_data->sort_keys[i];
		idx = sort_key->field_idx;

		if (WARN_ON(idx >= HIST_FIELDS_MAX))
			return -EINVAL;

		if (i > 0)
			seq_puts(m, ",");

		if (idx == HITCOUNT_IDX)
			seq_puts(m, "hitcount");
		else {
			if (idx >= first_key_idx)
				idx += hist_data->n_vars;
			hist_field_print(m, hist_data->fields[idx]);
		}

		if (sort_key->descending)
			seq_puts(m, ".descending");
	}
	seq_printf(m, ":size=%u", (1 << hist_data->map->map_bits));
	if (hist_data->enable_timestamps)
		seq_printf(m, ":clock=%s", hist_data->attrs->clock);

	print_actions_spec(m, hist_data);

	if (data->filter_str)
		seq_printf(m, " if %s", data->filter_str);

	if (data->paused)
		seq_puts(m, " [paused]");
	else
		seq_puts(m, " [active]");

	seq_putc(m, '\n');

	return 0;
}

static int event_hist_trigger_init(struct event_trigger_ops *ops,
				   struct event_trigger_data *data)
{
	struct hist_trigger_data *hist_data = data->private_data;

	if (!data->ref && hist_data->attrs->name)
		save_named_trigger(hist_data->attrs->name, data);

	data->ref++;

	return 0;
}

static void unregister_field_var_hists(struct hist_trigger_data *hist_data)
{
	struct trace_event_file *file;
	unsigned int i;
	char *cmd;
	int ret;

	for (i = 0; i < hist_data->n_field_var_hists; i++) {
		file = hist_data->field_var_hists[i]->hist_data->event_file;
		cmd = hist_data->field_var_hists[i]->cmd;
		ret = event_hist_trigger_func(&trigger_hist_cmd, file,
					      "!hist", "hist", cmd);
	}
}

static void event_hist_trigger_free(struct event_trigger_ops *ops,
				    struct event_trigger_data *data)
{
	struct hist_trigger_data *hist_data = data->private_data;

	if (WARN_ON_ONCE(data->ref <= 0))
		return;

	data->ref--;
	if (!data->ref) {
		if (data->name)
			del_named_trigger(data);

		trigger_data_free(data);

		remove_hist_vars(hist_data);

		unregister_field_var_hists(hist_data);

		destroy_hist_data(hist_data);
	}
}

static struct event_trigger_ops event_hist_trigger_ops = {
	.func			= event_hist_trigger,
	.print			= event_hist_trigger_print,
	.init			= event_hist_trigger_init,
	.free			= event_hist_trigger_free,
};

static int event_hist_trigger_named_init(struct event_trigger_ops *ops,
					 struct event_trigger_data *data)
{
	data->ref++;

	save_named_trigger(data->named_data->name, data);

	event_hist_trigger_init(ops, data->named_data);

	return 0;
}

static void event_hist_trigger_named_free(struct event_trigger_ops *ops,
					  struct event_trigger_data *data)
{
	if (WARN_ON_ONCE(data->ref <= 0))
		return;

	event_hist_trigger_free(ops, data->named_data);

	data->ref--;
	if (!data->ref) {
		del_named_trigger(data);
		trigger_data_free(data);
	}
}

static struct event_trigger_ops event_hist_trigger_named_ops = {
	.func			= event_hist_trigger,
	.print			= event_hist_trigger_print,
	.init			= event_hist_trigger_named_init,
	.free			= event_hist_trigger_named_free,
};

static struct event_trigger_ops *event_hist_get_trigger_ops(char *cmd,
							    char *param)
{
	return &event_hist_trigger_ops;
}

static void hist_clear(struct event_trigger_data *data)
{
	struct hist_trigger_data *hist_data = data->private_data;

	if (data->name)
		pause_named_trigger(data);

	tracepoint_synchronize_unregister();

	tracing_map_clear(hist_data->map);

	if (data->name)
		unpause_named_trigger(data);
}

static bool compatible_field(struct ftrace_event_field *field,
			     struct ftrace_event_field *test_field)
{
	if (field == test_field)
		return true;
	if (field == NULL || test_field == NULL)
		return false;
	if (strcmp(field->name, test_field->name) != 0)
		return false;
	if (strcmp(field->type, test_field->type) != 0)
		return false;
	if (field->size != test_field->size)
		return false;
	if (field->is_signed != test_field->is_signed)
		return false;

	return true;
}

static bool hist_trigger_match(struct event_trigger_data *data,
			       struct event_trigger_data *data_test,
			       struct event_trigger_data *named_data,
			       bool ignore_filter)
{
	struct tracing_map_sort_key *sort_key, *sort_key_test;
	struct hist_trigger_data *hist_data, *hist_data_test;
	struct hist_field *key_field, *key_field_test;
	unsigned int i;

	if (named_data && (named_data != data_test) &&
	    (named_data != data_test->named_data))
		return false;

	if (!named_data && is_named_trigger(data_test))
		return false;

	hist_data = data->private_data;
	hist_data_test = data_test->private_data;

	if (hist_data->n_vals != hist_data_test->n_vals ||
	    hist_data->n_fields != hist_data_test->n_fields ||
	    hist_data->n_sort_keys != hist_data_test->n_sort_keys)
		return false;

	if (!ignore_filter) {
		if ((data->filter_str && !data_test->filter_str) ||
		   (!data->filter_str && data_test->filter_str))
			return false;
	}

	for_each_hist_field(i, hist_data) {
		key_field = hist_data->fields[i];
		key_field_test = hist_data_test->fields[i];

		if (key_field->flags != key_field_test->flags)
			return false;
		if (!compatible_field(key_field->field, key_field_test->field))
			return false;
		if (key_field->offset != key_field_test->offset)
			return false;
		if (key_field->size != key_field_test->size)
			return false;
		if (key_field->is_signed != key_field_test->is_signed)
			return false;
		if (!!key_field->var.name != !!key_field_test->var.name)
			return false;
		if (key_field->var.name &&
		    strcmp(key_field->var.name, key_field_test->var.name) != 0)
			return false;
	}

	for (i = 0; i < hist_data->n_sort_keys; i++) {
		sort_key = &hist_data->sort_keys[i];
		sort_key_test = &hist_data_test->sort_keys[i];

		if (sort_key->field_idx != sort_key_test->field_idx ||
		    sort_key->descending != sort_key_test->descending)
			return false;
	}

	if (!ignore_filter && data->filter_str &&
	    (strcmp(data->filter_str, data_test->filter_str) != 0))
		return false;

	if (!actions_match(hist_data, hist_data_test))
		return false;

	return true;
}

static int hist_register_trigger(char *glob, struct event_trigger_ops *ops,
				 struct event_trigger_data *data,
				 struct trace_event_file *file)
{
	struct hist_trigger_data *hist_data = data->private_data;
	struct event_trigger_data *test, *named_data = NULL;
	struct trace_array *tr = file->tr;
	int ret = 0;

	if (hist_data->attrs->name) {
		named_data = find_named_trigger(hist_data->attrs->name);
		if (named_data) {
			if (!hist_trigger_match(data, named_data, named_data,
						true)) {
				hist_err(tr, HIST_ERR_NAMED_MISMATCH, errpos(hist_data->attrs->name));
				ret = -EINVAL;
				goto out;
			}
		}
	}

	if (hist_data->attrs->name && !named_data)
		goto new;

	lockdep_assert_held(&event_mutex);

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			if (!hist_trigger_match(data, test, named_data, false))
				continue;
			if (hist_data->attrs->pause)
				test->paused = true;
			else if (hist_data->attrs->cont)
				test->paused = false;
			else if (hist_data->attrs->clear)
				hist_clear(test);
			else {
				hist_err(tr, HIST_ERR_TRIGGER_EEXIST, 0);
				ret = -EEXIST;
			}
			goto out;
		}
	}
 new:
	if (hist_data->attrs->cont || hist_data->attrs->clear) {
		hist_err(tr, HIST_ERR_TRIGGER_ENOENT_CLEAR, 0);
		ret = -ENOENT;
		goto out;
	}

	if (hist_data->attrs->pause)
		data->paused = true;

	if (named_data) {
		data->private_data = named_data->private_data;
		set_named_trigger_data(data, named_data);
		data->ops = &event_hist_trigger_named_ops;
	}

	if (data->ops->init) {
		ret = data->ops->init(data->ops, data);
		if (ret < 0)
			goto out;
	}

	if (hist_data->enable_timestamps) {
		char *clock = hist_data->attrs->clock;

		ret = tracing_set_clock(file->tr, hist_data->attrs->clock);
		if (ret) {
			hist_err(tr, HIST_ERR_SET_CLOCK_FAIL, errpos(clock));
			goto out;
		}

		tracing_set_time_stamp_abs(file->tr, true);
	}

	if (named_data)
		destroy_hist_data(hist_data);

	ret++;
 out:
	return ret;
}

static int hist_trigger_enable(struct event_trigger_data *data,
			       struct trace_event_file *file)
{
	int ret = 0;

	list_add_tail_rcu(&data->list, &file->triggers);

	update_cond_flag(file);

	if (trace_event_trigger_enable_disable(file, 1) < 0) {
		list_del_rcu(&data->list);
		update_cond_flag(file);
		ret--;
	}

	return ret;
}

static bool have_hist_trigger_match(struct event_trigger_data *data,
				    struct trace_event_file *file)
{
	struct hist_trigger_data *hist_data = data->private_data;
	struct event_trigger_data *test, *named_data = NULL;
	bool match = false;

	lockdep_assert_held(&event_mutex);

	if (hist_data->attrs->name)
		named_data = find_named_trigger(hist_data->attrs->name);

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			if (hist_trigger_match(data, test, named_data, false)) {
				match = true;
				break;
			}
		}
	}

	return match;
}

static bool hist_trigger_check_refs(struct event_trigger_data *data,
				    struct trace_event_file *file)
{
	struct hist_trigger_data *hist_data = data->private_data;
	struct event_trigger_data *test, *named_data = NULL;

	lockdep_assert_held(&event_mutex);

	if (hist_data->attrs->name)
		named_data = find_named_trigger(hist_data->attrs->name);

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			if (!hist_trigger_match(data, test, named_data, false))
				continue;
			hist_data = test->private_data;
			if (check_var_refs(hist_data))
				return true;
			break;
		}
	}

	return false;
}

static void hist_unregister_trigger(char *glob, struct event_trigger_ops *ops,
				    struct event_trigger_data *data,
				    struct trace_event_file *file)
{
	struct hist_trigger_data *hist_data = data->private_data;
	struct event_trigger_data *test, *named_data = NULL;
	bool unregistered = false;

	lockdep_assert_held(&event_mutex);

	if (hist_data->attrs->name)
		named_data = find_named_trigger(hist_data->attrs->name);

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			if (!hist_trigger_match(data, test, named_data, false))
				continue;
			unregistered = true;
			list_del_rcu(&test->list);
			trace_event_trigger_enable_disable(file, 0);
			update_cond_flag(file);
			break;
		}
	}

	if (unregistered && test->ops->free)
		test->ops->free(test->ops, test);

	if (hist_data->enable_timestamps) {
		if (!hist_data->remove || unregistered)
			tracing_set_time_stamp_abs(file->tr, false);
	}
}

static bool hist_file_check_refs(struct trace_event_file *file)
{
	struct hist_trigger_data *hist_data;
	struct event_trigger_data *test;

	lockdep_assert_held(&event_mutex);

	list_for_each_entry(test, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			hist_data = test->private_data;
			if (check_var_refs(hist_data))
				return true;
		}
	}

	return false;
}

static void hist_unreg_all(struct trace_event_file *file)
{
	struct event_trigger_data *test, *n;
	struct hist_trigger_data *hist_data;
	struct synth_event *se;
	const char *se_name;

	lockdep_assert_held(&event_mutex);

	if (hist_file_check_refs(file))
		return;

	list_for_each_entry_safe(test, n, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			hist_data = test->private_data;
			list_del_rcu(&test->list);
			trace_event_trigger_enable_disable(file, 0);

			se_name = trace_event_name(file->event_call);
			se = find_synth_event(se_name);
			if (se)
				se->ref--;

			update_cond_flag(file);
			if (hist_data->enable_timestamps)
				tracing_set_time_stamp_abs(file->tr, false);
			if (test->ops->free)
				test->ops->free(test->ops, test);
		}
	}
}

static int event_hist_trigger_func(struct event_command *cmd_ops,
				   struct trace_event_file *file,
				   char *glob, char *cmd, char *param)
{
	unsigned int hist_trigger_bits = TRACING_MAP_BITS_DEFAULT;
	struct event_trigger_data *trigger_data;
	struct hist_trigger_attrs *attrs;
	struct event_trigger_ops *trigger_ops;
	struct hist_trigger_data *hist_data;
	struct synth_event *se;
	const char *se_name;
	bool remove = false;
	char *trigger, *p;
	int ret = 0;

	lockdep_assert_held(&event_mutex);

	if (glob && strlen(glob)) {
		hist_err_clear();
		last_cmd_set(file, param);
	}

	if (!param)
		return -EINVAL;

	if (glob[0] == '!')
		remove = true;

	/*
	 * separate the trigger from the filter (k:v [if filter])
	 * allowing for whitespace in the trigger
	 */
	p = trigger = param;
	do {
		p = strstr(p, "if");
		if (!p)
			break;
		if (p == param)
			return -EINVAL;
		if (*(p - 1) != ' ' && *(p - 1) != '\t') {
			p++;
			continue;
		}
		if (p >= param + strlen(param) - (sizeof("if") - 1) - 1)
			return -EINVAL;
		if (*(p + sizeof("if") - 1) != ' ' && *(p + sizeof("if") - 1) != '\t') {
			p++;
			continue;
		}
		break;
	} while (p);

	if (!p)
		param = NULL;
	else {
		*(p - 1) = '\0';
		param = strstrip(p);
		trigger = strstrip(trigger);
	}

	attrs = parse_hist_trigger_attrs(file->tr, trigger);
	if (IS_ERR(attrs))
		return PTR_ERR(attrs);

	if (attrs->map_bits)
		hist_trigger_bits = attrs->map_bits;

	hist_data = create_hist_data(hist_trigger_bits, attrs, file, remove);
	if (IS_ERR(hist_data)) {
		destroy_hist_trigger_attrs(attrs);
		return PTR_ERR(hist_data);
	}

	trigger_ops = cmd_ops->get_trigger_ops(cmd, trigger);

	trigger_data = kzalloc(sizeof(*trigger_data), GFP_KERNEL);
	if (!trigger_data) {
		ret = -ENOMEM;
		goto out_free;
	}

	trigger_data->count = -1;
	trigger_data->ops = trigger_ops;
	trigger_data->cmd_ops = cmd_ops;

	INIT_LIST_HEAD(&trigger_data->list);
	RCU_INIT_POINTER(trigger_data->filter, NULL);

	trigger_data->private_data = hist_data;

	/* if param is non-empty, it's supposed to be a filter */
	if (param && cmd_ops->set_filter) {
		ret = cmd_ops->set_filter(param, trigger_data, file);
		if (ret < 0)
			goto out_free;
	}

	if (remove) {
		if (!have_hist_trigger_match(trigger_data, file))
			goto out_free;

		if (hist_trigger_check_refs(trigger_data, file)) {
			ret = -EBUSY;
			goto out_free;
		}

		cmd_ops->unreg(glob+1, trigger_ops, trigger_data, file);
		se_name = trace_event_name(file->event_call);
		se = find_synth_event(se_name);
		if (se)
			se->ref--;
		ret = 0;
		goto out_free;
	}

	ret = cmd_ops->reg(glob, trigger_ops, trigger_data, file);
	/*
	 * The above returns on success the # of triggers registered,
	 * but if it didn't register any it returns zero.  Consider no
	 * triggers registered a failure too.
	 */
	if (!ret) {
		if (!(attrs->pause || attrs->cont || attrs->clear))
			ret = -ENOENT;
		goto out_free;
	} else if (ret < 0)
		goto out_free;

	if (get_named_trigger_data(trigger_data))
		goto enable;

	if (has_hist_vars(hist_data))
		save_hist_vars(hist_data);

	ret = create_actions(hist_data);
	if (ret)
		goto out_unreg;

	ret = tracing_map_init(hist_data->map);
	if (ret)
		goto out_unreg;
enable:
	ret = hist_trigger_enable(trigger_data, file);
	if (ret)
		goto out_unreg;

	se_name = trace_event_name(file->event_call);
	se = find_synth_event(se_name);
	if (se)
		se->ref++;
	/* Just return zero, not the number of registered triggers */
	ret = 0;
 out:
	if (ret == 0)
		hist_err_clear();

	return ret;
 out_unreg:
	cmd_ops->unreg(glob+1, trigger_ops, trigger_data, file);
 out_free:
	if (cmd_ops->set_filter)
		cmd_ops->set_filter(NULL, trigger_data, NULL);

	remove_hist_vars(hist_data);

	kfree(trigger_data);

	destroy_hist_data(hist_data);
	goto out;
}

static struct event_command trigger_hist_cmd = {
	.name			= "hist",
	.trigger_type		= ETT_EVENT_HIST,
	.flags			= EVENT_CMD_FL_NEEDS_REC,
	.func			= event_hist_trigger_func,
	.reg			= hist_register_trigger,
	.unreg			= hist_unregister_trigger,
	.unreg_all		= hist_unreg_all,
	.get_trigger_ops	= event_hist_get_trigger_ops,
	.set_filter		= set_trigger_filter,
};

__init int register_trigger_hist_cmd(void)
{
	int ret;

	ret = register_event_command(&trigger_hist_cmd);
	WARN_ON(ret < 0);

	return ret;
}

static void
hist_enable_trigger(struct event_trigger_data *data, void *rec,
		    struct ring_buffer_event *event)
{
	struct enable_trigger_data *enable_data = data->private_data;
	struct event_trigger_data *test;

	list_for_each_entry_rcu(test, &enable_data->file->triggers, list,
				lockdep_is_held(&event_mutex)) {
		if (test->cmd_ops->trigger_type == ETT_EVENT_HIST) {
			if (enable_data->enable)
				test->paused = false;
			else
				test->paused = true;
		}
	}
}

static void
hist_enable_count_trigger(struct event_trigger_data *data, void *rec,
			  struct ring_buffer_event *event)
{
	if (!data->count)
		return;

	if (data->count != -1)
		(data->count)--;

	hist_enable_trigger(data, rec, event);
}

static struct event_trigger_ops hist_enable_trigger_ops = {
	.func			= hist_enable_trigger,
	.print			= event_enable_trigger_print,
	.init			= event_trigger_init,
	.free			= event_enable_trigger_free,
};

static struct event_trigger_ops hist_enable_count_trigger_ops = {
	.func			= hist_enable_count_trigger,
	.print			= event_enable_trigger_print,
	.init			= event_trigger_init,
	.free			= event_enable_trigger_free,
};

static struct event_trigger_ops hist_disable_trigger_ops = {
	.func			= hist_enable_trigger,
	.print			= event_enable_trigger_print,
	.init			= event_trigger_init,
	.free			= event_enable_trigger_free,
};

static struct event_trigger_ops hist_disable_count_trigger_ops = {
	.func			= hist_enable_count_trigger,
	.print			= event_enable_trigger_print,
	.init			= event_trigger_init,
	.free			= event_enable_trigger_free,
};

static struct event_trigger_ops *
hist_enable_get_trigger_ops(char *cmd, char *param)
{
	struct event_trigger_ops *ops;
	bool enable;

	enable = (strcmp(cmd, ENABLE_HIST_STR) == 0);

	if (enable)
		ops = param ? &hist_enable_count_trigger_ops :
			&hist_enable_trigger_ops;
	else
		ops = param ? &hist_disable_count_trigger_ops :
			&hist_disable_trigger_ops;

	return ops;
}

static void hist_enable_unreg_all(struct trace_event_file *file)
{
	struct event_trigger_data *test, *n;

	list_for_each_entry_safe(test, n, &file->triggers, list) {
		if (test->cmd_ops->trigger_type == ETT_HIST_ENABLE) {
			list_del_rcu(&test->list);
			update_cond_flag(file);
			trace_event_trigger_enable_disable(file, 0);
			if (test->ops->free)
				test->ops->free(test->ops, test);
		}
	}
}

static struct event_command trigger_hist_enable_cmd = {
	.name			= ENABLE_HIST_STR,
	.trigger_type		= ETT_HIST_ENABLE,
	.func			= event_enable_trigger_func,
	.reg			= event_enable_register_trigger,
	.unreg			= event_enable_unregister_trigger,
	.unreg_all		= hist_enable_unreg_all,
	.get_trigger_ops	= hist_enable_get_trigger_ops,
	.set_filter		= set_trigger_filter,
};

static struct event_command trigger_hist_disable_cmd = {
	.name			= DISABLE_HIST_STR,
	.trigger_type		= ETT_HIST_ENABLE,
	.func			= event_enable_trigger_func,
	.reg			= event_enable_register_trigger,
	.unreg			= event_enable_unregister_trigger,
	.unreg_all		= hist_enable_unreg_all,
	.get_trigger_ops	= hist_enable_get_trigger_ops,
	.set_filter		= set_trigger_filter,
};

static __init void unregister_trigger_hist_enable_disable_cmds(void)
{
	unregister_event_command(&trigger_hist_enable_cmd);
	unregister_event_command(&trigger_hist_disable_cmd);
}

__init int register_trigger_hist_enable_disable_cmds(void)
{
	int ret;

	ret = register_event_command(&trigger_hist_enable_cmd);
	if (WARN_ON(ret < 0))
		return ret;
	ret = register_event_command(&trigger_hist_disable_cmd);
	if (WARN_ON(ret < 0))
		unregister_trigger_hist_enable_disable_cmds();

	return ret;
}

static __init int trace_events_hist_init(void)
{
	struct dentry *entry = NULL;
	struct dentry *d_tracer;
	int err = 0;

	err = dyn_event_register(&synth_event_ops);
	if (err) {
		pr_warn("Could not register synth_event_ops\n");
		return err;
	}

	d_tracer = tracing_init_dentry();
	if (IS_ERR(d_tracer)) {
		err = PTR_ERR(d_tracer);
		goto err;
	}

	entry = tracefs_create_file("synthetic_events", 0644, d_tracer,
				    NULL, &synth_events_fops);
	if (!entry) {
		err = -ENODEV;
		goto err;
	}

	return err;
 err:
	pr_warn("Could not create tracefs 'synthetic_events' entry\n");

	return err;
}

fs_initcall(trace_events_hist_init);
