Commit 0b22cd27 authored by Ingo Molnar's avatar Ingo Molnar
Browse files

Merge tag 'perf-core-for-mingo-20160414' of...

Merge tag 'perf-core-for-mingo-20160414' of git://git.kernel.org/pub/scm/linux/kernel/git/acme/linux

 into perf/core

Pull perf/core improvements from Arnaldo Carvalho de Melo:

User visible changes:

- Introduce 'perf record --timestamp-filename', to add a timestamp
  at the end of the 'perf data' file. Will get added value when
  the patch to make 'perf.data' file snapshots gets merged (Wang Nan)

- Fix display of variables present in both --config and --user in
  'perf list' (Taeung Song)

Build fixes:

- Add seccomp and getradom beautifier related defines to fix
  the build in older systems where those definitions are not
  available (Arnaldo Carvalho de Melo)

Signed-off-by: default avatarArnaldo Carvalho de Melo <acme@redhat.com>
Signed-off-by: default avatarIngo Molnar <mingo@kernel.org>
parents c5ab6ad7 860b8d4b
Loading
Loading
Loading
Loading
+32 −7
Original line number Diff line number Diff line
@@ -12,6 +12,7 @@
#include <subcmd/parse-options.h>
#include "util/util.h"
#include "util/debug.h"
#include "util/config.h"

static bool use_system_config, use_user_config;

@@ -32,13 +33,28 @@ static struct option config_options[] = {
	OPT_END()
};

static int show_config(const char *key, const char *value,
		       void *cb __maybe_unused)
static int show_config(struct perf_config_set *set)
{
	struct perf_config_section *section;
	struct perf_config_item *item;
	struct list_head *sections;

	if (set == NULL)
		return -1;

	sections = &set->sections;
	if (list_empty(sections))
		return -1;

	list_for_each_entry(section, sections, node) {
		list_for_each_entry(item, &section->items, node) {
			char *value = item->value;

			if (value)
		printf("%s=%s\n", key, value);
	else
		printf("%s\n", key);
				printf("%s.%s=%s\n", section->name,
				       item->name, value);
		}
	}

	return 0;
}
@@ -46,6 +62,7 @@ static int show_config(const char *key, const char *value,
int cmd_config(int argc, const char **argv, const char *prefix __maybe_unused)
{
	int ret = 0;
	struct perf_config_set *set;
	char *user_config = mkpath("%s/.perfconfig", getenv("HOME"));

	argc = parse_options(argc, argv, config_options, config_usage,
@@ -63,13 +80,19 @@ int cmd_config(int argc, const char **argv, const char *prefix __maybe_unused)
	else if (use_user_config)
		config_exclusive_filename = user_config;

	set = perf_config_set__new();
	if (!set) {
		ret = -1;
		goto out_err;
	}

	switch (actions) {
	case ACTION_LIST:
		if (argc) {
			pr_err("Error: takes no arguments\n");
			parse_options_usage(config_usage, config_options, "l", 1);
		} else {
			ret = perf_config(show_config, NULL);
			ret = show_config(set);
			if (ret < 0) {
				const char * config_filename = config_exclusive_filename;
				if (!config_exclusive_filename)
@@ -83,5 +106,7 @@ int cmd_config(int argc, const char **argv, const char *prefix __maybe_unused)
		usage_with_options(config_usage, config_options);
	}

	perf_config_set__delete(set);
out_err:
	return ret;
}
+98 −14
Original line number Diff line number Diff line
@@ -56,6 +56,7 @@ struct record {
	bool			no_buildid_cache;
	bool			no_buildid_cache_set;
	bool			buildid_all;
	bool			timestamp_filename;
	unsigned long long	samples;
};

@@ -125,7 +126,43 @@ out:
static volatile int done;
static volatile int signr = -1;
static volatile int child_finished;
static volatile int auxtrace_snapshot_enabled;

static volatile enum {
	AUXTRACE_SNAPSHOT_OFF = -1,
	AUXTRACE_SNAPSHOT_DISABLED = 0,
	AUXTRACE_SNAPSHOT_ENABLED = 1,
} auxtrace_snapshot_state = AUXTRACE_SNAPSHOT_OFF;

static inline void
auxtrace_snapshot_on(void)
{
	auxtrace_snapshot_state = AUXTRACE_SNAPSHOT_DISABLED;
}

static inline void
auxtrace_snapshot_enable(void)
{
	if (auxtrace_snapshot_state == AUXTRACE_SNAPSHOT_OFF)
		return;
	auxtrace_snapshot_state = AUXTRACE_SNAPSHOT_ENABLED;
}

static inline void
auxtrace_snapshot_disable(void)
{
	if (auxtrace_snapshot_state == AUXTRACE_SNAPSHOT_OFF)
		return;
	auxtrace_snapshot_state = AUXTRACE_SNAPSHOT_DISABLED;
}

static inline bool
auxtrace_snapshot_is_enabled(void)
{
	if (auxtrace_snapshot_state == AUXTRACE_SNAPSHOT_OFF)
		return false;
	return auxtrace_snapshot_state == AUXTRACE_SNAPSHOT_ENABLED;
}

static volatile int auxtrace_snapshot_err;
static volatile int auxtrace_record__snapshot_started;

@@ -249,7 +286,7 @@ static void record__read_auxtrace_snapshot(struct record *rec)
	} else {
		auxtrace_snapshot_err = auxtrace_record__snapshot_finish(rec->itr);
		if (!auxtrace_snapshot_err)
			auxtrace_snapshot_enabled = 1;
			auxtrace_snapshot_enable();
	}
}

@@ -495,6 +532,37 @@ record__finish_output(struct record *rec)
	return;
}

static int
record__switch_output(struct record *rec, bool at_exit)
{
	struct perf_data_file *file = &rec->file;
	int fd, err;

	/* Same Size:      "2015122520103046"*/
	char timestamp[] = "InvalidTimestamp";

	rec->samples = 0;
	record__finish_output(rec);
	err = fetch_current_timestamp(timestamp, sizeof(timestamp));
	if (err) {
		pr_err("Failed to get current timestamp\n");
		return -EINVAL;
	}

	fd = perf_data_file__switch(file, timestamp,
				    rec->session->header.data_offset,
				    at_exit);
	if (fd >= 0 && !at_exit) {
		rec->bytes_written = 0;
		rec->session->header.data_size = 0;
	}

	if (!quiet)
		fprintf(stderr, "[ perf record: Dump %s.%s ]\n",
			file->path, timestamp);
	return fd;
}

static volatile int workload_exec_errno;

/*
@@ -615,10 +683,13 @@ static int __cmd_record(struct record *rec, int argc, const char **argv)
	signal(SIGCHLD, sig_handler);
	signal(SIGINT, sig_handler);
	signal(SIGTERM, sig_handler);
	if (rec->opts.auxtrace_snapshot_mode)

	if (rec->opts.auxtrace_snapshot_mode) {
		signal(SIGUSR2, snapshot_sig_handler);
	else
		auxtrace_snapshot_on();
	} else {
		signal(SIGUSR2, SIG_IGN);
	}

	session = perf_session__new(file, false, tool);
	if (session == NULL) {
@@ -744,12 +815,12 @@ static int __cmd_record(struct record *rec, int argc, const char **argv)
		perf_evlist__enable(rec->evlist);
	}

	auxtrace_snapshot_enabled = 1;
	auxtrace_snapshot_enable();
	for (;;) {
		unsigned long long hits = rec->samples;

		if (record__mmap_read_all(rec) < 0) {
			auxtrace_snapshot_enabled = 0;
			auxtrace_snapshot_disable();
			err = -1;
			goto out_child;
		}
@@ -787,12 +858,12 @@ static int __cmd_record(struct record *rec, int argc, const char **argv)
		 * disable events in this case.
		 */
		if (done && !disabled && !target__none(&opts->target)) {
			auxtrace_snapshot_enabled = 0;
			auxtrace_snapshot_disable();
			perf_evlist__disable(rec->evlist);
			disabled = true;
		}
	}
	auxtrace_snapshot_enabled = 0;
	auxtrace_snapshot_disable();

	if (forks && workload_exec_errno) {
		char msg[STRERR_BUFSIZE];
@@ -826,11 +897,22 @@ out_child:
	/* this will be recalculated during process_buildids() */
	rec->samples = 0;

	if (!err)
	if (!err) {
		if (!rec->timestamp_filename) {
			record__finish_output(rec);
		} else {
			fd = record__switch_output(rec, true);
			if (fd < 0) {
				status = fd;
				goto out_delete_session;
			}
		}
	}

	if (!err && !quiet) {
		char samples[128];
		const char *postfix = rec->timestamp_filename ?
					".<timestamp>" : "";

		if (rec->samples && !rec->opts.full_auxtrace)
			scnprintf(samples, sizeof(samples),
@@ -838,9 +920,9 @@ out_child:
		else
			samples[0] = '\0';

		fprintf(stderr,	"[ perf record: Captured and wrote %.3f MB %s%s ]\n",
		fprintf(stderr,	"[ perf record: Captured and wrote %.3f MB %s%s%s ]\n",
			perf_data_file__size(file) / 1024.0 / 1024.0,
			file->path, samples);
			file->path, postfix, samples);
	}

out_delete_session:
@@ -1210,6 +1292,8 @@ struct option __record_options[] = {
		   "file", "vmlinux pathname"),
	OPT_BOOLEAN(0, "buildid-all", &record.buildid_all,
		    "Record build-id of all DSOs regardless of hits"),
	OPT_BOOLEAN(0, "timestamp-filename", &record.timestamp_filename,
		    "append timestamp to output filename"),
	OPT_END()
};

@@ -1358,9 +1442,9 @@ out_symbol_exit:

static void snapshot_sig_handler(int sig __maybe_unused)
{
	if (!auxtrace_snapshot_enabled)
	if (!auxtrace_snapshot_is_enabled())
		return;
	auxtrace_snapshot_enabled = 0;
	auxtrace_snapshot_disable();
	auxtrace_snapshot_err = auxtrace_record__snapshot_start(record.itr);
	auxtrace_record__snapshot_started = 1;
}
+20 −198
Original line number Diff line number Diff line
@@ -39,7 +39,6 @@

#include <libaudit.h> /* FIXME: Still needed for audit_errno_to_name */
#include <stdlib.h>
#include <sys/mman.h>
#include <linux/futex.h>
#include <linux/err.h>
#include <linux/seccomp.h>
@@ -48,36 +47,6 @@
#include <sys/ptrace.h>
#include <linux/random.h>

/* For older distros: */
#ifndef MAP_STACK
# define MAP_STACK		0x20000
#endif

#ifndef MADV_HWPOISON
# define MADV_HWPOISON		100

#endif

#ifndef MADV_MERGEABLE
# define MADV_MERGEABLE		12
#endif

#ifndef MADV_UNMERGEABLE
# define MADV_UNMERGEABLE	13
#endif

#ifndef EFD_SEMAPHORE
# define EFD_SEMAPHORE		1
#endif

#ifndef EFD_NONBLOCK
# define EFD_NONBLOCK		00004000
#endif

#ifndef EFD_CLOEXEC
# define EFD_CLOEXEC		02000000
#endif

#ifndef O_CLOEXEC
# define O_CLOEXEC		02000000
#endif
@@ -429,147 +398,6 @@ static size_t syscall_arg__scnprintf_int(char *bf, size_t size,

#define SCA_INT syscall_arg__scnprintf_int

static size_t syscall_arg__scnprintf_mmap_prot(char *bf, size_t size,
					       struct syscall_arg *arg)
{
	int printed = 0, prot = arg->val;

	if (prot == PROT_NONE)
		return scnprintf(bf, size, "NONE");
#define	P_MMAP_PROT(n) \
	if (prot & PROT_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		prot &= ~PROT_##n; \
	}

	P_MMAP_PROT(EXEC);
	P_MMAP_PROT(READ);
	P_MMAP_PROT(WRITE);
#ifdef PROT_SEM
	P_MMAP_PROT(SEM);
#endif
	P_MMAP_PROT(GROWSDOWN);
	P_MMAP_PROT(GROWSUP);
#undef P_MMAP_PROT

	if (prot)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", prot);

	return printed;
}

#define SCA_MMAP_PROT syscall_arg__scnprintf_mmap_prot

static size_t syscall_arg__scnprintf_mmap_flags(char *bf, size_t size,
						struct syscall_arg *arg)
{
	int printed = 0, flags = arg->val;

#define	P_MMAP_FLAG(n) \
	if (flags & MAP_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		flags &= ~MAP_##n; \
	}

	P_MMAP_FLAG(SHARED);
	P_MMAP_FLAG(PRIVATE);
#ifdef MAP_32BIT
	P_MMAP_FLAG(32BIT);
#endif
	P_MMAP_FLAG(ANONYMOUS);
	P_MMAP_FLAG(DENYWRITE);
	P_MMAP_FLAG(EXECUTABLE);
	P_MMAP_FLAG(FILE);
	P_MMAP_FLAG(FIXED);
	P_MMAP_FLAG(GROWSDOWN);
#ifdef MAP_HUGETLB
	P_MMAP_FLAG(HUGETLB);
#endif
	P_MMAP_FLAG(LOCKED);
	P_MMAP_FLAG(NONBLOCK);
	P_MMAP_FLAG(NORESERVE);
	P_MMAP_FLAG(POPULATE);
	P_MMAP_FLAG(STACK);
#ifdef MAP_UNINITIALIZED
	P_MMAP_FLAG(UNINITIALIZED);
#endif
#undef P_MMAP_FLAG

	if (flags)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", flags);

	return printed;
}

#define SCA_MMAP_FLAGS syscall_arg__scnprintf_mmap_flags

static size_t syscall_arg__scnprintf_mremap_flags(char *bf, size_t size,
						  struct syscall_arg *arg)
{
	int printed = 0, flags = arg->val;

#define P_MREMAP_FLAG(n) \
	if (flags & MREMAP_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		flags &= ~MREMAP_##n; \
	}

	P_MREMAP_FLAG(MAYMOVE);
#ifdef MREMAP_FIXED
	P_MREMAP_FLAG(FIXED);
#endif
#undef P_MREMAP_FLAG

	if (flags)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", flags);

	return printed;
}

#define SCA_MREMAP_FLAGS syscall_arg__scnprintf_mremap_flags

static size_t syscall_arg__scnprintf_madvise_behavior(char *bf, size_t size,
						      struct syscall_arg *arg)
{
	int behavior = arg->val;

	switch (behavior) {
#define	P_MADV_BHV(n) case MADV_##n: return scnprintf(bf, size, #n)
	P_MADV_BHV(NORMAL);
	P_MADV_BHV(RANDOM);
	P_MADV_BHV(SEQUENTIAL);
	P_MADV_BHV(WILLNEED);
	P_MADV_BHV(DONTNEED);
	P_MADV_BHV(REMOVE);
	P_MADV_BHV(DONTFORK);
	P_MADV_BHV(DOFORK);
	P_MADV_BHV(HWPOISON);
#ifdef MADV_SOFT_OFFLINE
	P_MADV_BHV(SOFT_OFFLINE);
#endif
	P_MADV_BHV(MERGEABLE);
	P_MADV_BHV(UNMERGEABLE);
#ifdef MADV_HUGEPAGE
	P_MADV_BHV(HUGEPAGE);
#endif
#ifdef MADV_NOHUGEPAGE
	P_MADV_BHV(NOHUGEPAGE);
#endif
#ifdef MADV_DONTDUMP
	P_MADV_BHV(DONTDUMP);
#endif
#ifdef MADV_DODUMP
	P_MADV_BHV(DODUMP);
#endif
#undef P_MADV_PHV
	default: break;
	}

	return scnprintf(bf, size, "%#x", behavior);
}

#define SCA_MADV_BHV syscall_arg__scnprintf_madvise_behavior

static size_t syscall_arg__scnprintf_flock(char *bf, size_t size,
					   struct syscall_arg *arg)
{
@@ -930,32 +758,6 @@ static size_t syscall_arg__scnprintf_perf_flags(char *bf, size_t size,

#define SCA_PERF_FLAGS syscall_arg__scnprintf_perf_flags

static size_t syscall_arg__scnprintf_eventfd_flags(char *bf, size_t size,
						   struct syscall_arg *arg)
{
	int printed = 0, flags = arg->val;

	if (flags == 0)
		return scnprintf(bf, size, "NONE");
#define	P_FLAG(n) \
	if (flags & EFD_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		flags &= ~EFD_##n; \
	}

	P_FLAG(SEMAPHORE);
	P_FLAG(CLOEXEC);
	P_FLAG(NONBLOCK);
#undef P_FLAG

	if (flags)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", flags);

	return printed;
}

#define SCA_EFD_FLAGS syscall_arg__scnprintf_eventfd_flags

static size_t syscall_arg__scnprintf_pipe_flags(char *bf, size_t size,
						struct syscall_arg *arg)
{
@@ -1059,6 +861,13 @@ static const char *tioctls[] = {
static DEFINE_STRARRAY_OFFSET(tioctls, 0x5401);
#endif /* defined(__i386__) || defined(__x86_64__) */

#ifndef SECCOMP_SET_MODE_STRICT
#define SECCOMP_SET_MODE_STRICT 0
#endif
#ifndef SECCOMP_SET_MODE_FILTER
#define SECCOMP_SET_MODE_FILTER 1
#endif

static size_t syscall_arg__scnprintf_seccomp_op(char *bf, size_t size, struct syscall_arg *arg)
{
	int op = arg->val;
@@ -1077,6 +886,10 @@ static size_t syscall_arg__scnprintf_seccomp_op(char *bf, size_t size, struct sy

#define SCA_SECCOMP_OP  syscall_arg__scnprintf_seccomp_op

#ifndef SECCOMP_FILTER_FLAG_TSYNC
#define SECCOMP_FILTER_FLAG_TSYNC 1
#endif

static size_t syscall_arg__scnprintf_seccomp_flags(char *bf, size_t size,
						   struct syscall_arg *arg)
{
@@ -1099,6 +912,13 @@ static size_t syscall_arg__scnprintf_seccomp_flags(char *bf, size_t size,

#define SCA_SECCOMP_FLAGS syscall_arg__scnprintf_seccomp_flags

#ifndef GRND_NONBLOCK
#define GRND_NONBLOCK	0x0001
#endif
#ifndef GRND_RANDOM
#define GRND_RANDOM	0x0002
#endif

static size_t syscall_arg__scnprintf_getrandom_flags(char *bf, size_t size,
						   struct syscall_arg *arg)
{
@@ -1126,7 +946,9 @@ static size_t syscall_arg__scnprintf_getrandom_flags(char *bf, size_t size,
	  .arg_scnprintf = { [arg] = SCA_STRARRAY, }, \
	  .arg_parm	 = { [arg] = &strarray__##array, }

#include "trace/beauty/eventfd.c"
#include "trace/beauty/pid.c"
#include "trace/beauty/mmap.c"
#include "trace/beauty/mode_t.c"
#include "trace/beauty/sched_policy.c"
#include "trace/beauty/waitid_options.c"
+38 −0
Original line number Diff line number Diff line
#include <sys/eventfd.h>

#ifndef EFD_SEMAPHORE
#define EFD_SEMAPHORE		1
#endif

#ifndef EFD_NONBLOCK
#define EFD_NONBLOCK		00004000
#endif

#ifndef EFD_CLOEXEC
#define EFD_CLOEXEC		02000000
#endif

static size_t syscall_arg__scnprintf_eventfd_flags(char *bf, size_t size, struct syscall_arg *arg)
{
	int printed = 0, flags = arg->val;

	if (flags == 0)
		return scnprintf(bf, size, "NONE");
#define	P_FLAG(n) \
	if (flags & EFD_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		flags &= ~EFD_##n; \
	}

	P_FLAG(SEMAPHORE);
	P_FLAG(CLOEXEC);
	P_FLAG(NONBLOCK);
#undef P_FLAG

	if (flags)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", flags);

	return printed;
}

#define SCA_EFD_FLAGS syscall_arg__scnprintf_eventfd_flags
+158 −0
Original line number Diff line number Diff line
#include <sys/mman.h>

static size_t syscall_arg__scnprintf_mmap_prot(char *bf, size_t size,
					       struct syscall_arg *arg)
{
	int printed = 0, prot = arg->val;

	if (prot == PROT_NONE)
		return scnprintf(bf, size, "NONE");
#define	P_MMAP_PROT(n) \
	if (prot & PROT_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		prot &= ~PROT_##n; \
	}

	P_MMAP_PROT(EXEC);
	P_MMAP_PROT(READ);
	P_MMAP_PROT(WRITE);
#ifdef PROT_SEM
	P_MMAP_PROT(SEM);
#endif
	P_MMAP_PROT(GROWSDOWN);
	P_MMAP_PROT(GROWSUP);
#undef P_MMAP_PROT

	if (prot)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", prot);

	return printed;
}

#define SCA_MMAP_PROT syscall_arg__scnprintf_mmap_prot

#ifndef MAP_STACK
# define MAP_STACK		0x20000
#endif

static size_t syscall_arg__scnprintf_mmap_flags(char *bf, size_t size,
						struct syscall_arg *arg)
{
	int printed = 0, flags = arg->val;

#define	P_MMAP_FLAG(n) \
	if (flags & MAP_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		flags &= ~MAP_##n; \
	}

	P_MMAP_FLAG(SHARED);
	P_MMAP_FLAG(PRIVATE);
#ifdef MAP_32BIT
	P_MMAP_FLAG(32BIT);
#endif
	P_MMAP_FLAG(ANONYMOUS);
	P_MMAP_FLAG(DENYWRITE);
	P_MMAP_FLAG(EXECUTABLE);
	P_MMAP_FLAG(FILE);
	P_MMAP_FLAG(FIXED);
	P_MMAP_FLAG(GROWSDOWN);
#ifdef MAP_HUGETLB
	P_MMAP_FLAG(HUGETLB);
#endif
	P_MMAP_FLAG(LOCKED);
	P_MMAP_FLAG(NONBLOCK);
	P_MMAP_FLAG(NORESERVE);
	P_MMAP_FLAG(POPULATE);
	P_MMAP_FLAG(STACK);
#ifdef MAP_UNINITIALIZED
	P_MMAP_FLAG(UNINITIALIZED);
#endif
#undef P_MMAP_FLAG

	if (flags)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", flags);

	return printed;
}

#define SCA_MMAP_FLAGS syscall_arg__scnprintf_mmap_flags

static size_t syscall_arg__scnprintf_mremap_flags(char *bf, size_t size,
						  struct syscall_arg *arg)
{
	int printed = 0, flags = arg->val;

#define P_MREMAP_FLAG(n) \
	if (flags & MREMAP_##n) { \
		printed += scnprintf(bf + printed, size - printed, "%s%s", printed ? "|" : "", #n); \
		flags &= ~MREMAP_##n; \
	}

	P_MREMAP_FLAG(MAYMOVE);
#ifdef MREMAP_FIXED
	P_MREMAP_FLAG(FIXED);
#endif
#undef P_MREMAP_FLAG

	if (flags)
		printed += scnprintf(bf + printed, size - printed, "%s%#x", printed ? "|" : "", flags);

	return printed;
}

#define SCA_MREMAP_FLAGS syscall_arg__scnprintf_mremap_flags

#ifndef MADV_HWPOISON
#define MADV_HWPOISON		100
#endif

#ifndef MADV_MERGEABLE
#define MADV_MERGEABLE		 12
#endif

#ifndef MADV_UNMERGEABLE
#define MADV_UNMERGEABLE	 13
#endif

static size_t syscall_arg__scnprintf_madvise_behavior(char *bf, size_t size,
						      struct syscall_arg *arg)
{
	int behavior = arg->val;

	switch (behavior) {
#define	P_MADV_BHV(n) case MADV_##n: return scnprintf(bf, size, #n)
	P_MADV_BHV(NORMAL);
	P_MADV_BHV(RANDOM);
	P_MADV_BHV(SEQUENTIAL);
	P_MADV_BHV(WILLNEED);
	P_MADV_BHV(DONTNEED);
	P_MADV_BHV(REMOVE);
	P_MADV_BHV(DONTFORK);
	P_MADV_BHV(DOFORK);
	P_MADV_BHV(HWPOISON);
#ifdef MADV_SOFT_OFFLINE
	P_MADV_BHV(SOFT_OFFLINE);
#endif
	P_MADV_BHV(MERGEABLE);
	P_MADV_BHV(UNMERGEABLE);
#ifdef MADV_HUGEPAGE
	P_MADV_BHV(HUGEPAGE);
#endif
#ifdef MADV_NOHUGEPAGE
	P_MADV_BHV(NOHUGEPAGE);
#endif
#ifdef MADV_DONTDUMP
	P_MADV_BHV(DONTDUMP);
#endif
#ifdef MADV_DODUMP
	P_MADV_BHV(DODUMP);
#endif
#undef P_MADV_PHV
	default: break;
	}

	return scnprintf(bf, size, "%#x", behavior);
}

#define SCA_MADV_BHV syscall_arg__scnprintf_madvise_behavior
Loading