linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH 0/6] tools/bootconfig: Add boot-time tracing script
@ 2020-08-10  8:34 Masami Hiramatsu
  2020-08-10  8:34 ` [PATCH 1/6] tools/bootconfig: Show bootconfig compact tree from bootconfig file Masami Hiramatsu
                   ` (5 more replies)
  0 siblings, 6 replies; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-10  8:34 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar, Masami Hiramatsu

Hi,

This is a series of patches to introduce scripts for the boot-time tracing.

- bconf2ftrace.sh generates a shell script from a bootconfig file which
  setup ftrace via tracefs. This is useful for checking whether your
  boot-time tracing bootconfig is working as you expected.

- ftrace2bconf.sh generates a bootconfig file from current ftrace setting.
  You can set up the ftrace manually and run a test on it before dump it
  to a bootconfig file.
  Note that some function-tracer/fgraph-tracer options are not supported
  by ftrace2bconf.sh, because the original wildcard expression has been
  lost during setup ftrace.

Also, this series improve the bootconfig command to increase usability.

- The bootconfig can format the bootconfig file without initrd. You don't
  need a dummy initrd anymore :)
- The bootconfig command supports -l (format as a list) option which
  outputs the bootconfig as a key-value list, as same as /proc/bootconfig.


Thank you,

---

Masami Hiramatsu (6):
      tools/bootconfig: Show bootconfig compact tree from bootconfig file
      tools/bootconfig: Add list option
      tools/bootconfig: Make all functions static
      tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig
      tools/bootconfig: Add a script to generates bootconfig from ftrace
      tools/bootconfig: Add --init option for bconf2ftrace.sh


 tools/bootconfig/main.c                  |  147 +++++++++++++-----
 tools/bootconfig/scripts/bconf2ftrace.sh |  199 ++++++++++++++++++++++++
 tools/bootconfig/scripts/ftrace.sh       |  109 +++++++++++++
 tools/bootconfig/scripts/ftrace2bconf.sh |  244 ++++++++++++++++++++++++++++++
 tools/bootconfig/scripts/xbc.sh          |   56 +++++++
 5 files changed, 713 insertions(+), 42 deletions(-)
 create mode 100755 tools/bootconfig/scripts/bconf2ftrace.sh
 create mode 100644 tools/bootconfig/scripts/ftrace.sh
 create mode 100755 tools/bootconfig/scripts/ftrace2bconf.sh
 create mode 100644 tools/bootconfig/scripts/xbc.sh

--
Masami Hiramatsu (Linaro) <mhiramat@kernel.org>

^ permalink raw reply	[flat|nested] 9+ messages in thread

* [PATCH 1/6] tools/bootconfig: Show bootconfig compact tree from bootconfig file
  2020-08-10  8:34 [PATCH 0/6] tools/bootconfig: Add boot-time tracing script Masami Hiramatsu
@ 2020-08-10  8:34 ` Masami Hiramatsu
  2020-08-10  8:34 ` [PATCH 2/6] tools/bootconfig: Add list option Masami Hiramatsu
                   ` (4 subsequent siblings)
  5 siblings, 0 replies; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-10  8:34 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar, Masami Hiramatsu

Show the bootconfig compact tree from the bootconfig file
instead of an initrd if the given file has no magic number
and is smaller than 32KB.

User can use this for checking the syntax error or output
checking before applying the bootconfig to initrd.

Signed-off-by: Masami Hiramatsu <mhiramat@kernel.org>
---
 tools/bootconfig/main.c |   81 ++++++++++++++++++++++++++++++++++-------------
 1 file changed, 58 insertions(+), 23 deletions(-)

diff --git a/tools/bootconfig/main.c b/tools/bootconfig/main.c
index e0878f5f74b1..d165e63b5d5a 100644
--- a/tools/bootconfig/main.c
+++ b/tools/bootconfig/main.c
@@ -195,10 +195,55 @@ int load_xbc_from_initrd(int fd, char **buf)
 	return size;
 }
 
+static void show_xbc_error(const char *data, const char *msg, int pos)
+{
+	int lin = 1, col, i;
+
+	if (pos < 0) {
+		pr_err("Error: %s.\n", msg);
+		return;
+	}
+
+	/* Note that pos starts from 0 but lin and col should start from 1. */
+	col = pos + 1;
+	for (i = 0; i < pos; i++) {
+		if (data[i] == '\n') {
+			lin++;
+			col = pos - i;
+		}
+	}
+	pr_err("Parse Error: %s at %d:%d\n", msg, lin, col);
+
+}
+
+static int init_xbc_with_error(char *buf, int len)
+{
+	char *copy = strdup(buf);
+	const char *msg;
+	int ret, pos;
+
+	if (!copy)
+		return -ENOMEM;
+
+	ret = xbc_init(buf, &msg, &pos);
+	if (ret < 0)
+		show_xbc_error(copy, msg, pos);
+	free(copy);
+
+	return ret;
+}
+
 int show_xbc(const char *path)
 {
 	int ret, fd;
 	char *buf = NULL;
+	struct stat st;
+
+	ret = stat(path, &st);
+	if (ret < 0) {
+		pr_err("Failed to stat %s: %d\n", path, -errno);
+		return -errno;
+	}
 
 	fd = open(path, O_RDONLY);
 	if (fd < 0) {
@@ -207,14 +252,24 @@ int show_xbc(const char *path)
 	}
 
 	ret = load_xbc_from_initrd(fd, &buf);
+	close(fd);
 	if (ret < 0) {
 		pr_err("Failed to load a boot config from initrd: %d\n", ret);
 		goto out;
 	}
+	/* Assume a bootconfig file if it is enough small */
+	if (ret == 0 && st.st_size <= XBC_DATA_MAX) {
+		ret = load_xbc_file(path, &buf);
+		if (ret < 0) {
+			pr_err("Failed to load a boot config: %d\n", ret);
+			goto out;
+		}
+		if (init_xbc_with_error(buf, ret) < 0)
+			goto out;
+	}
 	xbc_show_compact_tree();
 	ret = 0;
 out:
-	close(fd);
 	free(buf);
 
 	return ret;
@@ -251,27 +306,6 @@ int delete_xbc(const char *path)
 	return ret;
 }
 
-static void show_xbc_error(const char *data, const char *msg, int pos)
-{
-	int lin = 1, col, i;
-
-	if (pos < 0) {
-		pr_err("Error: %s.\n", msg);
-		return;
-	}
-
-	/* Note that pos starts from 0 but lin and col should start from 1. */
-	col = pos + 1;
-	for (i = 0; i < pos; i++) {
-		if (data[i] == '\n') {
-			lin++;
-			col = pos - i;
-		}
-	}
-	pr_err("Parse Error: %s at %d:%d\n", msg, lin, col);
-
-}
-
 int apply_xbc(const char *path, const char *xbc_path)
 {
 	u32 size, csum;
@@ -352,11 +386,12 @@ int apply_xbc(const char *path, const char *xbc_path)
 int usage(void)
 {
 	printf("Usage: bootconfig [OPTIONS] <INITRD>\n"
+		"Or     bootconfig <CONFIG>\n"
 		" Apply, delete or show boot config to initrd.\n"
 		" Options:\n"
 		"		-a <config>: Apply boot config to initrd\n"
 		"		-d : Delete boot config file from initrd\n\n"
-		" If no option is given, show current applied boot config.\n");
+		" If no option is given, show the bootconfig in the given file.\n");
 	return -1;
 }
 


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 2/6] tools/bootconfig: Add list option
  2020-08-10  8:34 [PATCH 0/6] tools/bootconfig: Add boot-time tracing script Masami Hiramatsu
  2020-08-10  8:34 ` [PATCH 1/6] tools/bootconfig: Show bootconfig compact tree from bootconfig file Masami Hiramatsu
@ 2020-08-10  8:34 ` Masami Hiramatsu
  2020-08-10  8:35 ` [PATCH 3/6] tools/bootconfig: Make all functions static Masami Hiramatsu
                   ` (3 subsequent siblings)
  5 siblings, 0 replies; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-10  8:34 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar, Masami Hiramatsu

Add list option (-l) to show the bootconfig in the list style.
This is same output of /proc/bootconfig. So users can check
how their bootconfig will be shown in procfs. This will help
them to write a user-space script to parse the /proc/bootconfig.

Signed-off-by: Masami Hiramatsu <mhiramat@kernel.org>
---
 tools/bootconfig/main.c |   52 ++++++++++++++++++++++++++++++++++++-----------
 1 file changed, 40 insertions(+), 12 deletions(-)

diff --git a/tools/bootconfig/main.c b/tools/bootconfig/main.c
index d165e63b5d5a..78025267df20 100644
--- a/tools/bootconfig/main.c
+++ b/tools/bootconfig/main.c
@@ -14,18 +14,19 @@
 #include <linux/kernel.h>
 #include <linux/bootconfig.h>
 
-static int xbc_show_value(struct xbc_node *node)
+static int xbc_show_value(struct xbc_node *node, bool semicolon)
 {
-	const char *val;
+	const char *val, *eol;
 	char q;
 	int i = 0;
 
+	eol = semicolon ? ";\n" : "\n";
 	xbc_array_for_each_value(node, val) {
 		if (strchr(val, '"'))
 			q = '\'';
 		else
 			q = '"';
-		printf("%c%s%c%s", q, val, q, node->next ? ", " : ";\n");
+		printf("%c%s%c%s", q, val, q, node->next ? ", " : eol);
 		i++;
 	}
 	return i;
@@ -53,7 +54,7 @@ static void xbc_show_compact_tree(void)
 			continue;
 		} else if (cnode && xbc_node_is_value(cnode)) {
 			printf("%s = ", xbc_node_get_data(node));
-			xbc_show_value(cnode);
+			xbc_show_value(cnode, true);
 		} else {
 			printf("%s;\n", xbc_node_get_data(node));
 		}
@@ -77,6 +78,26 @@ static void xbc_show_compact_tree(void)
 	}
 }
 
+static void xbc_show_list(void)
+{
+	char key[XBC_KEYLEN_MAX];
+	struct xbc_node *leaf;
+	const char *val;
+	int ret = 0;
+
+	xbc_for_each_key_value(leaf, val) {
+		ret = xbc_node_compose_key(leaf, key, XBC_KEYLEN_MAX);
+		if (ret < 0)
+			break;
+		printf("%s = ", key);
+		if (!val || val[0] == '\0') {
+			printf("\"\"\n");
+			continue;
+		}
+		xbc_show_value(xbc_node_get_child(leaf), false);
+	}
+}
+
 /* Simple real checksum */
 int checksum(unsigned char *buf, int len)
 {
@@ -233,7 +254,7 @@ static int init_xbc_with_error(char *buf, int len)
 	return ret;
 }
 
-int show_xbc(const char *path)
+int show_xbc(const char *path, bool list)
 {
 	int ret, fd;
 	char *buf = NULL;
@@ -267,7 +288,10 @@ int show_xbc(const char *path)
 		if (init_xbc_with_error(buf, ret) < 0)
 			goto out;
 	}
-	xbc_show_compact_tree();
+	if (list)
+		xbc_show_list();
+	else
+		xbc_show_compact_tree();
 	ret = 0;
 out:
 	free(buf);
@@ -390,7 +414,8 @@ int usage(void)
 		" Apply, delete or show boot config to initrd.\n"
 		" Options:\n"
 		"		-a <config>: Apply boot config to initrd\n"
-		"		-d : Delete boot config file from initrd\n\n"
+		"		-d : Delete boot config file from initrd\n"
+		"		-l : list boot config in initrd or file\n\n"
 		" If no option is given, show the bootconfig in the given file.\n");
 	return -1;
 }
@@ -399,10 +424,10 @@ int main(int argc, char **argv)
 {
 	char *path = NULL;
 	char *apply = NULL;
-	bool delete = false;
+	bool delete = false, list = false;
 	int opt;
 
-	while ((opt = getopt(argc, argv, "hda:")) != -1) {
+	while ((opt = getopt(argc, argv, "hda:l")) != -1) {
 		switch (opt) {
 		case 'd':
 			delete = true;
@@ -410,14 +435,17 @@ int main(int argc, char **argv)
 		case 'a':
 			apply = optarg;
 			break;
+		case 'l':
+			list = true;
+			break;
 		case 'h':
 		default:
 			return usage();
 		}
 	}
 
-	if (apply && delete) {
-		pr_err("Error: You can not specify both -a and -d at once.\n");
+	if ((apply && delete) || (delete && list) || (apply && list)) {
+		pr_err("Error: You can give one of -a, -d or -l at once.\n");
 		return usage();
 	}
 
@@ -433,5 +461,5 @@ int main(int argc, char **argv)
 	else if (delete)
 		return delete_xbc(path);
 
-	return show_xbc(path);
+	return show_xbc(path, list);
 }


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 3/6] tools/bootconfig: Make all functions static
  2020-08-10  8:34 [PATCH 0/6] tools/bootconfig: Add boot-time tracing script Masami Hiramatsu
  2020-08-10  8:34 ` [PATCH 1/6] tools/bootconfig: Show bootconfig compact tree from bootconfig file Masami Hiramatsu
  2020-08-10  8:34 ` [PATCH 2/6] tools/bootconfig: Add list option Masami Hiramatsu
@ 2020-08-10  8:35 ` Masami Hiramatsu
  2020-08-10  8:35 ` [PATCH 4/6] tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig Masami Hiramatsu
                   ` (2 subsequent siblings)
  5 siblings, 0 replies; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-10  8:35 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar, Masami Hiramatsu

Make all functions static except for main(). This is just a cleanup.

Signed-off-by: Masami Hiramatsu <mhiramat@kernel.org>
---
 tools/bootconfig/main.c |   16 ++++++++--------
 1 file changed, 8 insertions(+), 8 deletions(-)

diff --git a/tools/bootconfig/main.c b/tools/bootconfig/main.c
index 78025267df20..eb92027817a7 100644
--- a/tools/bootconfig/main.c
+++ b/tools/bootconfig/main.c
@@ -99,7 +99,7 @@ static void xbc_show_list(void)
 }
 
 /* Simple real checksum */
-int checksum(unsigned char *buf, int len)
+static int checksum(unsigned char *buf, int len)
 {
 	int i, sum = 0;
 
@@ -111,7 +111,7 @@ int checksum(unsigned char *buf, int len)
 
 #define PAGE_SIZE	4096
 
-int load_xbc_fd(int fd, char **buf, int size)
+static int load_xbc_fd(int fd, char **buf, int size)
 {
 	int ret;
 
@@ -128,7 +128,7 @@ int load_xbc_fd(int fd, char **buf, int size)
 }
 
 /* Return the read size or -errno */
-int load_xbc_file(const char *path, char **buf)
+static int load_xbc_file(const char *path, char **buf)
 {
 	struct stat stat;
 	int fd, ret;
@@ -147,7 +147,7 @@ int load_xbc_file(const char *path, char **buf)
 	return ret;
 }
 
-int load_xbc_from_initrd(int fd, char **buf)
+static int load_xbc_from_initrd(int fd, char **buf)
 {
 	struct stat stat;
 	int ret;
@@ -254,7 +254,7 @@ static int init_xbc_with_error(char *buf, int len)
 	return ret;
 }
 
-int show_xbc(const char *path, bool list)
+static int show_xbc(const char *path, bool list)
 {
 	int ret, fd;
 	char *buf = NULL;
@@ -299,7 +299,7 @@ int show_xbc(const char *path, bool list)
 	return ret;
 }
 
-int delete_xbc(const char *path)
+static int delete_xbc(const char *path)
 {
 	struct stat stat;
 	int ret = 0, fd, size;
@@ -330,7 +330,7 @@ int delete_xbc(const char *path)
 	return ret;
 }
 
-int apply_xbc(const char *path, const char *xbc_path)
+static int apply_xbc(const char *path, const char *xbc_path)
 {
 	u32 size, csum;
 	char *buf, *data;
@@ -407,7 +407,7 @@ int apply_xbc(const char *path, const char *xbc_path)
 	return ret;
 }
 
-int usage(void)
+static int usage(void)
 {
 	printf("Usage: bootconfig [OPTIONS] <INITRD>\n"
 		"Or     bootconfig <CONFIG>\n"


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 4/6] tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig
  2020-08-10  8:34 [PATCH 0/6] tools/bootconfig: Add boot-time tracing script Masami Hiramatsu
                   ` (2 preceding siblings ...)
  2020-08-10  8:35 ` [PATCH 3/6] tools/bootconfig: Make all functions static Masami Hiramatsu
@ 2020-08-10  8:35 ` Masami Hiramatsu
  2020-08-14  1:01   ` Steven Rostedt
  2020-08-10  8:35 ` [PATCH 5/6] tools/bootconfig: Add a script to generates bootconfig from ftrace Masami Hiramatsu
  2020-08-10  8:35 ` [PATCH 6/6] tools/bootconfig: Add --init option for bconf2ftrace.sh Masami Hiramatsu
  5 siblings, 1 reply; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-10  8:35 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar, Masami Hiramatsu

Add a bconf2ftrace.sh under tools/bootconfig/scripts which generates
a shell script to setup boot-time trace from bootconfig file for testing
the bootconfig.

bconf2ftrace.sh will take a bootconfig file (includes boot-time tracing)
and convert it into a shell-script which is almost same as the boot-time
tracer does.
If --apply option is given, it also tries to apply those command to the
running kernel, which requires the root privilege (or sudo).

For example, if you just want to confirm the shell commands, save
the output as below.

 # bconf2ftrace.sh ftrace.bconf > ftrace.sh

Or, you can apply it directly.

 # bconf2ftrace.sh --apply ftrace.bconf

Note that some boot-time tracing parameters under kernel.* are not able
to set via tracefs nor procfs (e.g. tp_printk, traceoff_on_warning.),
so those are ignored.

Signed-off-by: Masami Hiramatsu <mhiramat@kernel.org>
---
 tools/bootconfig/scripts/bconf2ftrace.sh |  189 ++++++++++++++++++++++++++++++
 tools/bootconfig/scripts/xbc.sh          |   56 +++++++++
 2 files changed, 245 insertions(+)
 create mode 100755 tools/bootconfig/scripts/bconf2ftrace.sh
 create mode 100644 tools/bootconfig/scripts/xbc.sh

diff --git a/MAINTAINERS b/MAINTAINERS
index 496fd4eafb68..fbe066d58eef 100644
--- a/MAINTAINERS
+++ b/MAINTAINERS
@@ -6506,6 +6506,7 @@ F:	fs/proc/bootconfig.c
 F:	include/linux/bootconfig.h
 F:	lib/bootconfig.c
 F:	tools/bootconfig/*
+F:	tools/bootconfig/scripts/*
 
 EXYNOS DP DRIVER
 M:	Jingoo Han <jingoohan1@gmail.com>
diff --git a/tools/bootconfig/scripts/bconf2ftrace.sh b/tools/bootconfig/scripts/bconf2ftrace.sh
new file mode 100755
index 000000000000..a46e984fb2ff
--- /dev/null
+++ b/tools/bootconfig/scripts/bconf2ftrace.sh
@@ -0,0 +1,189 @@
+#!/bin/sh
+# SPDX-License-Identifier: GPL-2.0-only
+
+usage() {
+	echo "Ftrace boottime trace test tool"
+	echo "Usage: $0 [--apply] [--debug] BOOTCONFIG-FILE"
+	echo "    --apply: Test actual apply to tracefs (need sudo)"
+	exit 1
+}
+
+[ $# -eq 0 ] && usage
+
+BCONF=
+DEBUG=
+APPLY=
+while [ x"$1" != x ]; do
+	case "$1" in
+	"--debug")
+		DEBUG=$1;;
+	"--apply")
+		APPLY=$1;;
+	*)
+		[ ! -f $1 ] && usage
+		BCONF=$1;;
+	esac
+	shift 1
+done
+
+if [ x"$APPLY" != x ]; then
+	if [ `id -u` -ne 0 ]; then
+		echo "This must be run by root user. Try sudo." 1>&2
+		exec sudo $0 $DEBUG $APPLY $BCONF
+	fi
+fi
+
+run_cmd() { # command
+	echo "$*"
+	if [ x"$APPLY" != x ]; then # apply command
+		eval $*
+	fi
+}
+
+if [ x"$DEBUG" != x ]; then
+	set -x
+fi
+
+TRACEFS=`grep -m 1 -w tracefs /proc/mounts | cut -f 2 -d " "`
+if [ -z "$TRACEFS" ]; then
+	if ! grep -wq debugfs /proc/mounts; then
+		echo "Error: No tracefs/debugfs was mounted." 1>&2
+		exit 1
+	fi
+	TRACEFS=`grep -m 1 -w debugfs /proc/mounts | cut -f 2 -d " "`/tracing
+	if [ ! -d $TRACEFS ]; then
+		echo "Error: ftrace is not enabled on this kernel." 1>&2
+		exit 1
+	fi
+fi
+
+. `dirname $0`/xbc.sh
+
+######## main #########
+set -e
+
+xbc_init $BCONF
+
+set_value_of() { # key file
+	if xbc_has_key $1; then
+		val=`xbc_get_val $1 1`
+		run_cmd "echo '$val' >> $2"
+	fi
+}
+
+set_array_of() { # key file
+	if xbc_has_key $1; then
+		xbc_get_val $1 | while read line; do
+			run_cmd "echo '$line' >> $2"
+		done
+	fi
+}
+
+compose_synth() { # event_name branch
+	echo -n "$1 "
+	xbc_get_val $2 | while read field; do echo -n "$field; "; done
+}
+
+setup_event() { # prefix group event [instance]
+	branch=$1.$2.$3
+	if [ "$4" ]; then
+		eventdir="$TRACEFS/instances/$4/events/$2/$3"
+	else
+		eventdir="$TRACEFS/events/$2/$3"
+	fi
+	case $2 in
+	kprobes)
+		xbc_get_val ${branch}.probes | while read line; do
+			run_cmd "echo 'p:kprobes/$3 $line' >> $TRACEFS/kprobe_events"
+		done
+		;;
+	synthetic)
+		run_cmd "echo '`compose_synth $3 ${branch}.fields`' >> $TRACEFS/synthetic_events"
+		;;
+	esac
+
+	set_value_of ${branch}.filter ${eventdir}/filter
+	set_array_of ${branch}.actions ${eventdir}/trigger
+
+	if xbc_has_key ${branch}.enable; then
+		run_cmd "echo 1 > ${eventdir}/enable"
+	fi
+}
+
+setup_events() { # prefix("ftrace" or "ftrace.instance.INSTANCE") [instance]
+	prefix="${1}.event"
+	if xbc_has_branch ${1}.event; then
+		for grpev in `xbc_subkeys ${1}.event 2`; do
+			setup_event $prefix ${grpev%.*} ${grpev#*.} $2
+		done
+	fi
+}
+
+size2kb() { # size[KB|MB]
+	case $1 in
+	*KB)
+		echo ${1%KB};;
+	*MB)
+		expr ${1%MB} \* 1024;;
+	*)
+		expr $1 / 1024 ;;
+	esac
+}
+
+setup_instance() { # [instance]
+	if [ "$1" ]; then
+		instance="ftrace.instance.${1}"
+		instancedir=$TRACEFS/instances/$1
+	else
+		instance="ftrace"
+		instancedir=$TRACEFS
+	fi
+
+	set_array_of ${instance}.options ${instancedir}/trace_options
+	set_value_of ${instance}.trace_clock ${instancedir}/trace_clock
+	set_value_of ${instance}.cpumask ${instancedir}/tracing_cpumask
+	set_value_of ${instance}.tracer ${instancedir}/current_tracer
+	set_array_of ${instance}.ftrace.filters \
+		${instancedir}/set_ftrace_filter
+	set_array_of ${instance}.ftrace.notrace \
+		${instancedir}/set_ftrace_notrace
+
+	if xbc_has_key ${instance}.alloc_snapshot; then
+		run_cmd "echo 1 > ${instancedir}/snapshot"
+	fi
+
+	if xbc_has_key ${instance}.buffer_size; then
+		size=`xbc_get_val ${instance}.buffer_size 1`
+		size=`eval size2kb $size`
+		run_cmd "echo $size >> ${instancedir}/buffer_size_kb"
+	fi
+
+	setup_events ${instance} $1
+	set_array_of ${instance}.events ${instancedir}/set_event
+}
+
+# ftrace global configs (kernel.*)
+if xbc_has_key "kernel.dump_on_oops"; then
+	dump_mode=`xbc_get_val "kernel.dump_on_oops" 1`
+	[ "$dump_mode" ] && dump_mode=`eval echo $dump_mode` || dump_mode=1
+	run_cmd "echo \"$dump_mode\" > /proc/sys/kernel/ftrace_dump_on_oops"
+fi
+
+set_value_of kernel.fgraph_max_depth $TRACEFS/max_graph_depth
+set_array_of kernel.fgraph_filters $TRACEFS/set_graph_function
+set_array_of kernel.fgraph_notraces $TRACEFS/set_graph_notrace
+
+# Per-instance/per-event configs
+if ! xbc_has_branch "ftrace" ; then
+	exit 0
+fi
+
+setup_instance # root instance
+
+if xbc_has_branch "ftrace.instance"; then
+	for i in `xbc_subkeys "ftrace.instance" 1`; do
+		run_cmd "mkdir -p $TRACEFS/instances/$i"
+		setup_instance $i
+	done
+fi
+
diff --git a/tools/bootconfig/scripts/xbc.sh b/tools/bootconfig/scripts/xbc.sh
new file mode 100644
index 000000000000..b8c84e654556
--- /dev/null
+++ b/tools/bootconfig/scripts/xbc.sh
@@ -0,0 +1,56 @@
+#!/bin/sh
+# SPDX-License-Identifier: GPL-2.0-only
+
+# bootconfig utility functions
+
+XBC_TMPFILE=
+XBC_BASEDIR=`dirname $0`
+BOOTCONFIG=${BOOTCONFIG:=$XBC_BASEDIR/../bootconfig}
+if [ ! -x "$BOOTCONFIG" ]; then
+	BOOTCONFIG=`which bootconfig`
+	if [ -z "$BOOTCONFIG" ]; then
+		echo "Erorr: bootconfig command is not found" 1>&2
+		exit 1
+	fi
+fi
+
+xbc_cleanup() {
+	if [ "$XBC_TMPFILE" ]; then
+		rm -f "$XBC_TMPFILE"
+	fi
+}
+
+xbc_init() { # bootconfig-file
+	xbc_cleanup
+	XBC_TMPFILE=`mktemp bconf-XXXX`
+	trap xbc_cleanup EXIT TERM
+
+	$BOOTCONFIG -l $1 > $XBC_TMPFILE || exit 1
+}
+
+nr_args() { # args
+	echo $#
+}
+
+xbc_get_val() { # key [maxnum]
+	if [ "$2" ]; then
+		MAXOPT="-L $2"
+	fi
+	grep "^$1 =" $XBC_TMPFILE | cut -d= -f2- | \
+		sed -e 's/", /" /g' -e "s/',/' /g" | \
+		xargs $MAXOPT -n 1 echo
+}
+
+xbc_has_key() { # key
+	grep -q "^$1 =" $XBC_TMPFILE
+}
+
+xbc_has_branch() { # prefix-key
+	grep -q "^$1" $XBC_TMPFILE
+}
+
+xbc_subkeys() { # prefix-key depth
+	__keys=`echo $1 | sed "s/\./ /g"`
+	__s=`nr_args $__keys`
+	grep "^$1" $XBC_TMPFILE | cut -d= -f1| cut -d. -f$((__s + 1))-$((__s + $2)) | uniq
+}


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 5/6] tools/bootconfig: Add a script to generates bootconfig from ftrace
  2020-08-10  8:34 [PATCH 0/6] tools/bootconfig: Add boot-time tracing script Masami Hiramatsu
                   ` (3 preceding siblings ...)
  2020-08-10  8:35 ` [PATCH 4/6] tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig Masami Hiramatsu
@ 2020-08-10  8:35 ` Masami Hiramatsu
  2020-08-10  8:35 ` [PATCH 6/6] tools/bootconfig: Add --init option for bconf2ftrace.sh Masami Hiramatsu
  5 siblings, 0 replies; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-10  8:35 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar, Masami Hiramatsu

Add a ftrace2bconf.sh under tools/bootconfig/scripts which generates
a bootconfig file from the current ftrace settings.

To read the ftrace settings, ftrace2bconf.sh requires the root
privilege (or sudo). The ftrace2bconf.sh will output the bootconfig
to stdout and error messages to stderr, so usually you'll run it as

 # ftrace2bconf.sh > ftrace.bconf

Note that some ftrace configurations are not supported. For example,
function-call/callgraph trace/notrace settings are not supported because
the wildcard has been expanded and lost in the ftrace anymore.

Signed-off-by: Masami Hiramatsu <mhiramat@kernel.org>
---
 tools/bootconfig/scripts/ftrace2bconf.sh |  244 ++++++++++++++++++++++++++++++
 1 file changed, 244 insertions(+)
 create mode 100755 tools/bootconfig/scripts/ftrace2bconf.sh

diff --git a/tools/bootconfig/scripts/ftrace2bconf.sh b/tools/bootconfig/scripts/ftrace2bconf.sh
new file mode 100755
index 000000000000..6c0d4b61e0c2
--- /dev/null
+++ b/tools/bootconfig/scripts/ftrace2bconf.sh
@@ -0,0 +1,244 @@
+#!/bin/sh
+# SPDX-License-Identifier: GPL-2.0-only
+
+usage() {
+	echo "Dump boot-time tracing bootconfig from ftrace"
+	echo "Usage: $0 [--debug] [ > BOOTCONFIG-FILE]"
+	exit 1
+}
+
+DEBUG=
+while [ x"$1" != x ]; do
+	case "$1" in
+	"--debug")
+		DEBUG=$1;;
+	-*)
+		usage
+		;;
+	esac
+	shift 1
+done
+
+if [ x"$DEBUG" != x ]; then
+	set -x
+fi
+
+TRACEFS=`grep -m 1 -w tracefs /proc/mounts | cut -f 2 -d " "`
+if [ -z "$TRACEFS" ]; then
+	if ! grep -wq debugfs /proc/mounts; then
+		echo "Error: No tracefs/debugfs was mounted."
+		exit 1
+	fi
+	TRACEFS=`grep -m 1 -w debugfs /proc/mounts | cut -f 2 -d " "`/tracing
+	if [ ! -d $TRACEFS ]; then
+		echo "Error: ftrace is not enabled on this kernel." 1>&2
+		exit 1
+	fi
+fi
+
+######## main #########
+
+set -e
+
+emit_kv() { # key =|+= value
+	echo "$@"
+}
+
+global_options() {
+	val=`cat $TRACEFS/max_graph_depth`
+	[ $val != 0 ] && emit_kv kernel.fgraph_max_depth = $val
+	if grep -qv "^#" $TRACEFS/set_graph_function $TRACEFS/set_graph_notrace ; then
+		cat 1>&2 << EOF
+# WARN: kernel.fgraph_filters and kernel.fgraph_notrace are not supported, since the wild card expression was expanded and lost from memory.
+EOF
+	fi
+}
+
+kprobe_event_options() {
+	cat $TRACEFS/kprobe_events | while read p args; do
+		case $p in
+		r*)
+		cat 1>&2 << EOF
+# WARN: A return probe found but it is not supported by bootconfig. Skip it.
+EOF
+		continue;;
+		esac
+		p=${p#*:}
+		event=${p#*/}
+		group=${p%/*}
+		if [ $group != "kprobes" ]; then
+			cat 1>&2 << EOF
+# WARN: kprobes group name $group is changed to "kprobes" for bootconfig.
+EOF
+		fi
+		emit_kv $PREFIX.event.kprobes.$event.probes += $args
+	done
+}
+
+synth_event_options() {
+	cat $TRACEFS/synthetic_events | while read event fields; do
+		emit_kv $PREFIX.event.synthetic.$event.fields = `echo $fields | sed "s/;/,/g"`
+	done
+}
+
+# Variables resolver
+DEFINED_VARS=
+UNRESOLVED_EVENTS=
+
+defined_vars() { # event-dir
+	grep "^hist" $1/trigger | grep -o ':[a-zA-Z0-9]*='
+}
+referred_vars() {
+	grep "^hist" $1/trigger | grep -o '$[a-zA-Z0-9]*'
+}
+
+per_event_options() { # event-dir
+	evdir=$1
+	# Check the special event which has no filter and no trigger
+	[ ! -f $evdir/filter ] && return
+
+	if grep -q "^hist:" $evdir/trigger; then
+		# hist action can refer the undefined variables
+		__vars=`defined_vars $evdir`
+		for v in `referred_vars $evdir`; do
+			if echo $DEFINED_VARS $__vars | grep -vqw ${v#$}; then
+				# $v is not defined yet, defer it
+				UNRESOLVED_EVENTS="$UNRESOLVED_EVENTS $evdir"
+				return;
+			fi
+		done
+		DEFINED_VARS="$DEFINED_VARS "`defined_vars $evdir`
+	fi
+	grep -v "^#" $evdir/trigger | while read action active; do
+		emit_kv $PREFIX.event.$group.$event.actions += \'$action\'
+	done
+
+	# enable is not checked; this is done by set_event in the instance.
+	val=`cat $evdir/filter`
+	if [ "$val" != "none" ]; then
+		emit_kv $PREFIX.event.$group.$event.filter = "$val"
+	fi
+}
+
+retry_unresolved() {
+	unresolved=$UNRESOLVED_EVENTS
+	UNRESOLVED_EVENTS=
+	for evdir in $unresolved; do
+		event=${evdir##*/}
+		group=${evdir%/*}; group=${group##*/}
+		per_event_options $evdir
+	done
+}
+
+event_options() {
+	# PREFIX and INSTANCE must be set
+	if [ $PREFIX = "ftrace" ]; then
+		# define the dynamic events
+		kprobe_event_options
+		synth_event_options
+	fi
+	for group in `ls $INSTANCE/events/` ; do
+		[ ! -d $INSTANCE/events/$group ] && continue
+		for event in `ls $INSTANCE/events/$group/` ;do
+			[ ! -d $INSTANCE/events/$group/$event ] && continue
+			per_event_options $INSTANCE/events/$group/$event
+		done
+	done
+	retry=0
+	while [ $retry -lt 3 ]; do
+		retry_unresolved
+		retry=$((retry + 1))
+	done
+	if [ "$UNRESOLVED_EVENTS" ]; then
+		cat 1>&2 << EOF
+! ERROR: hist triggers in $UNRESOLVED_EVENTS use some undefined variables.
+EOF
+	fi
+}
+
+is_default_trace_option() { # option
+grep -qw $1 << EOF
+print-parent
+nosym-offset
+nosym-addr
+noverbose
+noraw
+nohex
+nobin
+noblock
+trace_printk
+annotate
+nouserstacktrace
+nosym-userobj
+noprintk-msg-only
+context-info
+nolatency-format
+record-cmd
+norecord-tgid
+overwrite
+nodisable_on_free
+irq-info
+markers
+noevent-fork
+nopause-on-trace
+function-trace
+nofunction-fork
+nodisplay-graph
+nostacktrace
+notest_nop_accept
+notest_nop_refuse
+EOF
+}
+
+instance_options() { # [instance-name]
+	if [ $# -eq 0 ]; then
+		PREFIX="ftrace"
+		INSTANCE=$TRACEFS
+	else
+		PREFIX="ftrace.instance.$1"
+		INSTANCE=$TRACEFS/instances/$1
+	fi
+	val=
+	for i in `cat $INSTANCE/trace_options`; do
+		is_default_trace_option $i && continue
+		val="$val, $i"
+	done
+	[ "$val" ] && emit_kv $PREFIX.options = "${val#,}"
+	val="local"
+	for i in `cat $INSTANCE/trace_clock` ; do
+		[ "${i#*]}" ] && continue
+		i=${i%]}; val=${i#[}
+	done
+	[ $val != "local" ] && emit_kv $PREFIX.trace_clock = $val
+	val=`cat $INSTANCE/buffer_size_kb`
+	if echo $val | grep -vq "expanded" ; then
+		emit_kv $PREFIX.buffer_size = $val"KB"
+	fi
+	if grep -q "is allocated" $INSTANCE/snapshot ; then
+		emit_kv $PREFIX.alloc_snapshot
+	fi
+	val=`cat $INSTANCE/tracing_cpumask`
+	if [ `echo $val | sed -e s/f//g`x != x ]; then
+		emit_kv $PREFIX.cpumask = $val
+	fi
+
+	val=
+	for i in `cat $INSTANCE/set_event`; do
+		val="$val, $i"
+	done
+	[ "$val" ] && emit_kv $PREFIX.events = "${val#,}"
+	val=`cat $INSTANCE/current_tracer`
+	[ $val != nop ] && emit_kv $PREFIX.tracer = $val
+	if grep -qv "^#" $INSTANCE/set_ftrace_filter $INSTANCE/set_ftrace_notrace; then
+		cat 1>&2 << EOF
+# WARN: kernel.ftrace.filters and kernel.ftrace.notrace are not supported, since the wild card expression was expanded and lost from memory.
+EOF
+	fi
+	event_options
+}
+
+global_options
+instance_options
+for i in `ls $TRACEFS/instances` ; do
+	instance_options $i
+done


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* [PATCH 6/6] tools/bootconfig: Add --init option for bconf2ftrace.sh
  2020-08-10  8:34 [PATCH 0/6] tools/bootconfig: Add boot-time tracing script Masami Hiramatsu
                   ` (4 preceding siblings ...)
  2020-08-10  8:35 ` [PATCH 5/6] tools/bootconfig: Add a script to generates bootconfig from ftrace Masami Hiramatsu
@ 2020-08-10  8:35 ` Masami Hiramatsu
  5 siblings, 0 replies; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-10  8:35 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar, Masami Hiramatsu

Since the ftrace current setting may conflict with the new setting
from bootconfig, add the --init option to initialize ftrace before
setting for bconf2ftrace.sh.

E.g.
 $ bconf2ftrace.sh --init boottrace.bconf

This initialization method copied from selftests/ftrace.

Signed-off-by: Masami Hiramatsu <mhiramat@kernel.org>
---
 tools/bootconfig/scripts/bconf2ftrace.sh |   12 +++
 tools/bootconfig/scripts/ftrace.sh       |  109 ++++++++++++++++++++++++++++++
 2 files changed, 120 insertions(+), 1 deletion(-)
 create mode 100644 tools/bootconfig/scripts/ftrace.sh

diff --git a/tools/bootconfig/scripts/bconf2ftrace.sh b/tools/bootconfig/scripts/bconf2ftrace.sh
index a46e984fb2ff..595e164dc352 100755
--- a/tools/bootconfig/scripts/bconf2ftrace.sh
+++ b/tools/bootconfig/scripts/bconf2ftrace.sh
@@ -3,8 +3,9 @@
 
 usage() {
 	echo "Ftrace boottime trace test tool"
-	echo "Usage: $0 [--apply] [--debug] BOOTCONFIG-FILE"
+	echo "Usage: $0 [--apply|--init] [--debug] BOOTCONFIG-FILE"
 	echo "    --apply: Test actual apply to tracefs (need sudo)"
+	echo "    --init:  Initialize ftrace before applying (imply --apply)"
 	exit 1
 }
 
@@ -13,12 +14,16 @@ usage() {
 BCONF=
 DEBUG=
 APPLY=
+INIT=
 while [ x"$1" != x ]; do
 	case "$1" in
 	"--debug")
 		DEBUG=$1;;
 	"--apply")
 		APPLY=$1;;
+	"--init")
+		APPLY=$1
+		INIT=$1;;
 	*)
 		[ ! -f $1 ] && usage
 		BCONF=$1;;
@@ -57,6 +62,11 @@ if [ -z "$TRACEFS" ]; then
 	fi
 fi
 
+if [ x"$INIT" != x ]; then
+	. `dirname $0`/ftrace.sh
+	(cd $TRACEFS; initialize_ftrace)
+fi
+
 . `dirname $0`/xbc.sh
 
 ######## main #########
diff --git a/tools/bootconfig/scripts/ftrace.sh b/tools/bootconfig/scripts/ftrace.sh
new file mode 100644
index 000000000000..186eed923041
--- /dev/null
+++ b/tools/bootconfig/scripts/ftrace.sh
@@ -0,0 +1,109 @@
+# SPDX-License-Identifier: GPL-2.0-only
+
+clear_trace() { # reset trace output
+    echo > trace
+}
+
+disable_tracing() { # stop trace recording
+    echo 0 > tracing_on
+}
+
+enable_tracing() { # start trace recording
+    echo 1 > tracing_on
+}
+
+reset_tracer() { # reset the current tracer
+    echo nop > current_tracer
+}
+
+reset_trigger_file() {
+    # remove action triggers first
+    grep -H ':on[^:]*(' $@ |
+    while read line; do
+        cmd=`echo $line | cut -f2- -d: | cut -f1 -d"["`
+	file=`echo $line | cut -f1 -d:`
+	echo "!$cmd" >> $file
+    done
+    grep -Hv ^# $@ |
+    while read line; do
+        cmd=`echo $line | cut -f2- -d: | cut -f1 -d"["`
+	file=`echo $line | cut -f1 -d:`
+	echo "!$cmd" > $file
+    done
+}
+
+reset_trigger() { # reset all current setting triggers
+    if [ -d events/synthetic ]; then
+        reset_trigger_file events/synthetic/*/trigger
+    fi
+    reset_trigger_file events/*/*/trigger
+}
+
+reset_events_filter() { # reset all current setting filters
+    grep -v ^none events/*/*/filter |
+    while read line; do
+	echo 0 > `echo $line | cut -f1 -d:`
+    done
+}
+
+reset_ftrace_filter() { # reset all triggers in set_ftrace_filter
+    if [ ! -f set_ftrace_filter ]; then
+      return 0
+    fi
+    echo > set_ftrace_filter
+    grep -v '^#' set_ftrace_filter | while read t; do
+	tr=`echo $t | cut -d: -f2`
+	if [ "$tr" = "" ]; then
+	    continue
+	fi
+	if ! grep -q "$t" set_ftrace_filter; then
+		continue;
+	fi
+	name=`echo $t | cut -d: -f1 | cut -d' ' -f1`
+	if [ $tr = "enable_event" -o $tr = "disable_event" ]; then
+	    tr=`echo $t | cut -d: -f2-4`
+	    limit=`echo $t | cut -d: -f5`
+	else
+	    tr=`echo $t | cut -d: -f2`
+	    limit=`echo $t | cut -d: -f3`
+	fi
+	if [ "$limit" != "unlimited" ]; then
+	    tr="$tr:$limit"
+	fi
+	echo "!$name:$tr" > set_ftrace_filter
+    done
+}
+
+disable_events() {
+    echo 0 > events/enable
+}
+
+clear_synthetic_events() { # reset all current synthetic events
+    grep -v ^# synthetic_events |
+    while read line; do
+        echo "!$line" >> synthetic_events
+    done
+}
+
+initialize_ftrace() { # Reset ftrace to initial-state
+# As the initial state, ftrace will be set to nop tracer,
+# no events, no triggers, no filters, no function filters,
+# no probes, and tracing on.
+    disable_tracing
+    reset_tracer
+    reset_trigger
+    reset_events_filter
+    reset_ftrace_filter
+    disable_events
+    [ -f set_event_pid ] && echo > set_event_pid
+    [ -f set_ftrace_pid ] && echo > set_ftrace_pid
+    [ -f set_ftrace_notrace ] && echo > set_ftrace_notrace
+    [ -f set_graph_function ] && echo | tee set_graph_*
+    [ -f stack_trace_filter ] && echo > stack_trace_filter
+    [ -f kprobe_events ] && echo > kprobe_events
+    [ -f uprobe_events ] && echo > uprobe_events
+    [ -f synthetic_events ] && echo > synthetic_events
+    [ -f snapshot ] && echo 0 > snapshot
+    clear_trace
+    enable_tracing
+}


^ permalink raw reply related	[flat|nested] 9+ messages in thread

* Re: [PATCH 4/6] tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig
  2020-08-10  8:35 ` [PATCH 4/6] tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig Masami Hiramatsu
@ 2020-08-14  1:01   ` Steven Rostedt
  2020-08-15 10:57     ` Masami Hiramatsu
  0 siblings, 1 reply; 9+ messages in thread
From: Steven Rostedt @ 2020-08-14  1:01 UTC (permalink / raw)
  To: Masami Hiramatsu; +Cc: LKML, Ingo Molnar

On Mon, 10 Aug 2020 17:35:11 +0900
Masami Hiramatsu <mhiramat@kernel.org> wrote:


> --- /dev/null
> +++ b/tools/bootconfig/scripts/xbc.sh
> @@ -0,0 +1,56 @@
> +#!/bin/sh
> +# SPDX-License-Identifier: GPL-2.0-only
> +
> +# bootconfig utility functions
> +
> +XBC_TMPFILE=
> +XBC_BASEDIR=`dirname $0`
> +BOOTCONFIG=${BOOTCONFIG:=$XBC_BASEDIR/../bootconfig}
> +if [ ! -x "$BOOTCONFIG" ]; then
> +	BOOTCONFIG=`which bootconfig`
> +	if [ -z "$BOOTCONFIG" ]; then
> +		echo "Erorr: bootconfig command is not found" 1>&2
> +		exit 1
> +	fi
> +fi
> +
> +xbc_cleanup() {
> +	if [ "$XBC_TMPFILE" ]; then

Should the above be:

	if [ -f "$XBC_TMPFILE" ]; then
?


-- Steve

> +		rm -f "$XBC_TMPFILE"
> +	fi
> +}
> +
> +xbc_init() { # bootconfig-file
> +	xbc_cleanup
> +	XBC_TMPFILE=`mktemp bconf-XXXX`
> +	trap xbc_cleanup EXIT TERM
> +
> +	$BOOTCONFIG -l $1 > $XBC_TMPFILE || exit 1
> +}
> +
> +nr_args() { # args
> +	echo $#
> +}
> +
> +xbc_get_val() { # key [maxnum]
> +	if [ "$2" ]; then
> +		MAXOPT="-L $2"
> +	fi
> +	grep "^$1 =" $XBC_TMPFILE | cut -d= -f2- | \
> +		sed -e 's/", /" /g' -e "s/',/' /g" | \
> +		xargs $MAXOPT -n 1 echo
> +}
> +
> +xbc_has_key() { # key
> +	grep -q "^$1 =" $XBC_TMPFILE
> +}
> +
> +xbc_has_branch() { # prefix-key
> +	grep -q "^$1" $XBC_TMPFILE
> +}
> +
> +xbc_subkeys() { # prefix-key depth
> +	__keys=`echo $1 | sed "s/\./ /g"`
> +	__s=`nr_args $__keys`
> +	grep "^$1" $XBC_TMPFILE | cut -d= -f1| cut -d. -f$((__s + 1))-$((__s + $2)) | uniq
> +}


^ permalink raw reply	[flat|nested] 9+ messages in thread

* Re: [PATCH 4/6] tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig
  2020-08-14  1:01   ` Steven Rostedt
@ 2020-08-15 10:57     ` Masami Hiramatsu
  0 siblings, 0 replies; 9+ messages in thread
From: Masami Hiramatsu @ 2020-08-15 10:57 UTC (permalink / raw)
  To: Steven Rostedt; +Cc: LKML, Ingo Molnar

On Thu, 13 Aug 2020 21:01:00 -0400
Steven Rostedt <rostedt@goodmis.org> wrote:

> On Mon, 10 Aug 2020 17:35:11 +0900
> Masami Hiramatsu <mhiramat@kernel.org> wrote:
> 
> 
> > --- /dev/null
> > +++ b/tools/bootconfig/scripts/xbc.sh
> > @@ -0,0 +1,56 @@
> > +#!/bin/sh
> > +# SPDX-License-Identifier: GPL-2.0-only
> > +
> > +# bootconfig utility functions
> > +
> > +XBC_TMPFILE=
> > +XBC_BASEDIR=`dirname $0`
> > +BOOTCONFIG=${BOOTCONFIG:=$XBC_BASEDIR/../bootconfig}
> > +if [ ! -x "$BOOTCONFIG" ]; then
> > +	BOOTCONFIG=`which bootconfig`
> > +	if [ -z "$BOOTCONFIG" ]; then
> > +		echo "Erorr: bootconfig command is not found" 1>&2
> > +		exit 1
> > +	fi
> > +fi
> > +
> > +xbc_cleanup() {
> > +	if [ "$XBC_TMPFILE" ]; then
> 
> Should the above be:
> 
> 	if [ -f "$XBC_TMPFILE" ]; then
> ?

Ah, good catch!
I didn't call xbc_cleanup except for the trap in bconf2ftrace,
but for user who call xbc_cleanup explicitly, we need -f.

Thank you!

> 
> 
> -- Steve
> 
> > +		rm -f "$XBC_TMPFILE"
> > +	fi
> > +}
> > +
> > +xbc_init() { # bootconfig-file
> > +	xbc_cleanup
> > +	XBC_TMPFILE=`mktemp bconf-XXXX`
> > +	trap xbc_cleanup EXIT TERM
> > +
> > +	$BOOTCONFIG -l $1 > $XBC_TMPFILE || exit 1
> > +}
> > +
> > +nr_args() { # args
> > +	echo $#
> > +}
> > +
> > +xbc_get_val() { # key [maxnum]
> > +	if [ "$2" ]; then
> > +		MAXOPT="-L $2"
> > +	fi
> > +	grep "^$1 =" $XBC_TMPFILE | cut -d= -f2- | \
> > +		sed -e 's/", /" /g' -e "s/',/' /g" | \
> > +		xargs $MAXOPT -n 1 echo
> > +}
> > +
> > +xbc_has_key() { # key
> > +	grep -q "^$1 =" $XBC_TMPFILE
> > +}
> > +
> > +xbc_has_branch() { # prefix-key
> > +	grep -q "^$1" $XBC_TMPFILE
> > +}
> > +
> > +xbc_subkeys() { # prefix-key depth
> > +	__keys=`echo $1 | sed "s/\./ /g"`
> > +	__s=`nr_args $__keys`
> > +	grep "^$1" $XBC_TMPFILE | cut -d= -f1| cut -d. -f$((__s + 1))-$((__s + $2)) | uniq
> > +}
> 


-- 
Masami Hiramatsu <mhiramat@kernel.org>

^ permalink raw reply	[flat|nested] 9+ messages in thread

end of thread, other threads:[~2020-08-15 22:12 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2020-08-10  8:34 [PATCH 0/6] tools/bootconfig: Add boot-time tracing script Masami Hiramatsu
2020-08-10  8:34 ` [PATCH 1/6] tools/bootconfig: Show bootconfig compact tree from bootconfig file Masami Hiramatsu
2020-08-10  8:34 ` [PATCH 2/6] tools/bootconfig: Add list option Masami Hiramatsu
2020-08-10  8:35 ` [PATCH 3/6] tools/bootconfig: Make all functions static Masami Hiramatsu
2020-08-10  8:35 ` [PATCH 4/6] tools/bootconfig: Add a script to generate ftrace shell-command from bootconfig Masami Hiramatsu
2020-08-14  1:01   ` Steven Rostedt
2020-08-15 10:57     ` Masami Hiramatsu
2020-08-10  8:35 ` [PATCH 5/6] tools/bootconfig: Add a script to generates bootconfig from ftrace Masami Hiramatsu
2020-08-10  8:35 ` [PATCH 6/6] tools/bootconfig: Add --init option for bconf2ftrace.sh Masami Hiramatsu

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).