summaryrefslogtreecommitdiff
path: root/tools/perf/util/probe-file.c
diff options
context:
space:
mode:
authorRavi Bangoria <ravi.bangoria@linux.vnet.ibm.com>2017-03-28 15:17:53 +0530
committerArnaldo Carvalho de Melo <acme@redhat.com>2017-03-28 12:25:30 -0300
commitd451a205da29c5485ca634367154e83997571aa0 (patch)
tree93c2a2519650d6d98b30b196f4fbb839c2add505 /tools/perf/util/probe-file.c
parent2d01ecc580405169ecd6e3880617bc61cf482fdd (diff)
perf/sdt/x86: Move OP parser to tools/perf/arch/x86/
SDT marker argument is in N@OP format. N is the size of argument and OP is the actual assembly operand. OP is arch dependent component and hence it's parsing logic also should be placed under tools/perf/arch/. Signed-off-by: Ravi Bangoria <ravi.bangoria@linux.vnet.ibm.com> Acked-by: Masami Hiramatsu <mhiramat@kernel.org> Cc: Alexander Shishkin <alexander.shishkin@linux.intel.com> Cc: Alexis Berlemont <alexis.berlemont@gmail.com> Cc: Hemant Kumar <hemant@linux.vnet.ibm.com> Cc: Michael Ellerman <mpe@ellerman.id.au> Cc: Naveen N. Rao <naveen.n.rao@linux.vnet.ibm.com> Cc: Peter Zijlstra <peterz@infradead.org> Link: http://lkml.kernel.org/r/20170328094754.3156-3-ravi.bangoria@linux.vnet.ibm.com Signed-off-by: Arnaldo Carvalho de Melo <acme@redhat.com>
Diffstat (limited to 'tools/perf/util/probe-file.c')
-rw-r--r--tools/perf/util/probe-file.c132
1 files changed, 38 insertions, 94 deletions
diff --git a/tools/perf/util/probe-file.c b/tools/perf/util/probe-file.c
index d741634cbfc0..88714dec8912 100644
--- a/tools/perf/util/probe-file.c
+++ b/tools/perf/util/probe-file.c
@@ -694,10 +694,29 @@ static const char * const type_to_suffix[] = {
"", ":u8", ":u16", "", ":u32", "", "", "", ":u64"
};
+/*
+ * Isolate the string number and convert it into a decimal value;
+ * this will be an index to get suffix of the uprobe name (defining
+ * the type)
+ */
+static int sdt_arg_parse_size(char *n_ptr, const char **suffix)
+{
+ long type_idx;
+
+ type_idx = strtol(n_ptr, NULL, 10);
+ if (type_idx < -8 || type_idx > 8) {
+ pr_debug4("Failed to get a valid sdt type\n");
+ return -1;
+ }
+
+ *suffix = type_to_suffix[type_idx + 8];
+ return 0;
+}
+
static int synthesize_sdt_probe_arg(struct strbuf *buf, int i, const char *arg)
{
- char *tmp, *desc = strdup(arg);
- const char *prefix = "", *suffix = "";
+ char *op, *desc = strdup(arg), *new_op = NULL;
+ const char *suffix = "";
int ret = -1;
if (desc == NULL) {
@@ -705,112 +724,37 @@ static int synthesize_sdt_probe_arg(struct strbuf *buf, int i, const char *arg)
return ret;
}
- tmp = strchr(desc, '@');
- if (tmp) {
- long type_idx;
- /*
- * Isolate the string number and convert it into a
- * binary value; this will be an index to get suffix
- * of the uprobe name (defining the type)
- */
- tmp[0] = '\0';
- type_idx = strtol(desc, NULL, 10);
- /* Check that the conversion went OK */
- if (type_idx == LONG_MIN || type_idx == LONG_MAX) {
- pr_debug4("Failed to parse sdt type\n");
- goto error;
- }
- /* Check that the converted value is OK */
- if (type_idx < -8 || type_idx > 8) {
- pr_debug4("Failed to get a valid sdt type\n");
- goto error;
- }
- suffix = type_to_suffix[type_idx + 8];
- /* Get rid of the sdt prefix which is now useless */
- tmp++;
- memmove(desc, tmp, strlen(tmp) + 1);
- }
-
/*
- * The uprobe tracer format does not support all the
- * addressing modes (notably: in x86 the scaled mode); so, we
- * detect ',' characters, if there is just one, there is no
- * use converting the sdt arg into a uprobe one.
+ * Argument is in N@OP format. N is size of the argument and OP is
+ * the actual assembly operand. N can be omitted; in that case
+ * argument is just OP(without @).
*/
- if (strchr(desc, ',')) {
- pr_debug4("Skipping unsupported SDT argument; %s\n", desc);
- goto out;
- }
+ op = strchr(desc, '@');
+ if (op) {
+ op[0] = '\0';
+ op++;
- /*
- * If the argument addressing mode is indirect, we must check
- * a few things...
- */
- tmp = strchr(desc, '(');
- if (tmp) {
- int j;
-
- /*
- * ...if the addressing mode is indirect with a
- * positive offset (ex.: "1608(%ax)"), we need to add
- * a '+' prefix so as to be compliant with uprobe
- * format.
- */
- if (desc[0] != '+' && desc[0] != '-')
- prefix = "+";
-
- /*
- * ...or if the addressing mode is indirect with a symbol
- * as offset, the argument will not be supported by
- * the uprobe tracer format; so, let's skip this one.
- */
- for (j = 0; j < tmp - desc; j++) {
- if (desc[j] != '+' && desc[j] != '-' &&
- !isdigit(desc[j])) {
- pr_debug4("Skipping unsupported SDT argument; "
- "%s\n", desc);
- goto out;
- }
- }
+ if (sdt_arg_parse_size(desc, &suffix))
+ goto error;
+ } else {
+ op = desc;
}
- /*
- * The uprobe tracer format does not support constants; if we
- * find one in the current argument, let's skip the argument.
- */
- if (strchr(desc, '$')) {
- pr_debug4("Skipping unsupported SDT argument; %s\n", desc);
- goto out;
- }
+ ret = arch_sdt_arg_parse_op(op, &new_op);
- /*
- * The uprobe parser does not support all gas register names;
- * so, we have to replace them (ex. for x86_64: %rax -> %ax);
- * the loop below looks for the register names (starting with
- * a '%' and tries to perform the needed renamings.
- */
- tmp = strchr(desc, '%');
- while (tmp) {
- size_t offset = tmp - desc;
+ if (ret < 0)
+ goto error;
- ret = sdt_rename_register(&desc, desc + offset);
+ if (ret == SDT_ARG_VALID) {
+ ret = strbuf_addf(buf, " arg%d=%s%s", i + 1, new_op, suffix);
if (ret < 0)
goto error;
-
- /*
- * The desc pointer might have changed; so, let's not
- * try to reuse tmp for next lookup
- */
- tmp = strchr(desc + offset + 1, '%');
}
- if (strbuf_addf(buf, " arg%d=%s%s%s", i + 1, prefix, desc, suffix) < 0)
- goto error;
-
-out:
ret = 0;
error:
free(desc);
+ free(new_op);
return ret;
}