|
|
d956f8 |
commit 0caa975190e4d2b19e7b65a0b23a7700522aa5d7
|
|
|
d956f8 |
Author: Frank Ch. Eigler <fche@redhat.com>
|
|
|
d956f8 |
Date: Mon Aug 31 11:17:33 2015 -0400
|
|
|
d956f8 |
|
|
|
d956f8 |
PR18889 part: improve module-notification related debug tracing
|
|
|
d956f8 |
|
|
|
d956f8 |
-DDEBUG_KPROBES -DDEBUG_SYMBOLS -DDEBUG_STP_ON_THE_FLY recommended.
|
|
|
d956f8 |
|
|
|
d956f8 |
diff --git a/runtime/linux/kprobes.c b/runtime/linux/kprobes.c
|
|
|
d956f8 |
index 47eb29a..54c224e 100644
|
|
|
d956f8 |
--- a/runtime/linux/kprobes.c
|
|
|
d956f8 |
+++ b/runtime/linux/kprobes.c
|
|
|
d956f8 |
@@ -567,6 +567,8 @@ stapkp_refresh(const char *modname,
|
|
|
d956f8 |
{
|
|
|
d956f8 |
size_t i;
|
|
|
d956f8 |
|
|
|
d956f8 |
+ dbug_stapkp("refresh %lu probes with module %s\n", nprobes, modname ?: "?");
|
|
|
d956f8 |
+
|
|
|
d956f8 |
for (i = 0; i < nprobes; i++) {
|
|
|
d956f8 |
|
|
|
d956f8 |
struct stap_dwarf_probe *sdp = &probes[i];
|
|
|
d956f8 |
diff --git a/runtime/transport/symbols.c b/runtime/transport/symbols.c
|
|
|
d956f8 |
index fe576c1..9ea2b5b 100644
|
|
|
d956f8 |
--- a/runtime/transport/symbols.c
|
|
|
d956f8 |
+++ b/runtime/transport/symbols.c
|
|
|
d956f8 |
@@ -1,7 +1,7 @@
|
|
|
d956f8 |
-/* -*- linux-c -*-
|
|
|
d956f8 |
+/* -*- linux-c -*-
|
|
|
d956f8 |
* symbols.c - stp symbol and module functions
|
|
|
d956f8 |
*
|
|
|
d956f8 |
- * Copyright (C) Red Hat Inc, 2006-2012
|
|
|
d956f8 |
+ * Copyright (C) Red Hat Inc, 2006-2015
|
|
|
d956f8 |
*
|
|
|
d956f8 |
* This file is part of systemtap, and is free software. You can
|
|
|
d956f8 |
* redistribute it and/or modify it under the terms of the GNU General
|
|
|
d956f8 |
@@ -121,10 +121,26 @@ static unsigned _stp_module_nsections (struct module_sect_attrs *attrs)
|
|
|
d956f8 |
static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
unsigned long val, void *data)
|
|
|
d956f8 |
{
|
|
|
d956f8 |
+ struct module *mod = data;
|
|
|
d956f8 |
+ struct module_sect_attrs *attrs;
|
|
|
d956f8 |
+ unsigned i, nsections;
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+ (void) attrs;
|
|
|
d956f8 |
+ (void) i;
|
|
|
d956f8 |
+ (void) nsections;
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+ if (!mod) { // so as to avoid null pointer checks later
|
|
|
d956f8 |
+ WARN_ON (!mod);
|
|
|
d956f8 |
+ return NOTIFY_DONE;
|
|
|
d956f8 |
+ }
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+ dbug_sym(1, "module notify %lu %s attrs %p\n",
|
|
|
d956f8 |
+ val, mod->name, mod->sect_attrs);
|
|
|
d956f8 |
+
|
|
|
d956f8 |
/* Prior to 2.6.11, struct module contained a module_sections
|
|
|
d956f8 |
attribute vector rather than module_sect_attrs. Prior to
|
|
|
d956f8 |
2.6.19, module_sect_attrs lacked a number-of-sections
|
|
|
d956f8 |
- field. Past 3.8, MODULE_STATE_COMING is sent too early to
|
|
|
d956f8 |
+ field. Past 3.8, MODULE_STATE_COMING is sent too early to
|
|
|
d956f8 |
let us probe module init functions.
|
|
|
d956f8 |
|
|
|
d956f8 |
Without CONFIG_KALLSYMS, we don't get any of the
|
|
|
d956f8 |
@@ -132,11 +148,6 @@ static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
that directly? */
|
|
|
d956f8 |
|
|
|
d956f8 |
#if defined(CONFIG_KALLSYMS) && LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,11)
|
|
|
d956f8 |
- struct module *mod = data;
|
|
|
d956f8 |
- struct module_sect_attrs *attrs;
|
|
|
d956f8 |
- unsigned i, nsections;
|
|
|
d956f8 |
- WARN_ON (!mod);
|
|
|
d956f8 |
-
|
|
|
d956f8 |
if (val == MODULE_STATE_COMING ||
|
|
|
d956f8 |
val == MODULE_STATE_LIVE) {
|
|
|
d956f8 |
/* A module is arriving or has arrived. Register all
|
|
|
d956f8 |
@@ -145,6 +156,7 @@ static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
did the fishie go? */
|
|
|
d956f8 |
|
|
|
d956f8 |
attrs = mod->sect_attrs;
|
|
|
d956f8 |
+ dbug_sym(1, "module_sect_attrs: %p\n", attrs);
|
|
|
d956f8 |
if (attrs == NULL) // until add_sect_attrs(), may be zero
|
|
|
d956f8 |
return NOTIFY_DONE; // remain ignorant
|
|
|
d956f8 |
|
|
|
d956f8 |
@@ -153,7 +165,7 @@ static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
int init_p = (strstr(attrs->attrs[i].name, "init.") != NULL);
|
|
|
d956f8 |
int init_gone_p = (val == MODULE_STATE_LIVE); // likely already unloaded
|
|
|
d956f8 |
|
|
|
d956f8 |
- _stp_kmodule_update_address(mod->name,
|
|
|
d956f8 |
+ _stp_kmodule_update_address(mod->name,
|
|
|
d956f8 |
attrs->attrs[i].name,
|
|
|
d956f8 |
((init_p && init_gone_p) ? 0 : attrs->attrs[i].address));
|
|
|
d956f8 |
}
|
|
|
d956f8 |
@@ -161,7 +173,7 @@ static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
/* Verify build-id. */
|
|
|
d956f8 |
if (_stp_kmodule_check (mod->name))
|
|
|
d956f8 |
_stp_kmodule_update_address(mod->name, NULL, 0); /* Pretend it was never here. */
|
|
|
d956f8 |
- }
|
|
|
d956f8 |
+ }
|
|
|
d956f8 |
else if (val == MODULE_STATE_GOING) {
|
|
|
d956f8 |
/* Unregister all sections. */
|
|
|
d956f8 |
_stp_kmodule_update_address(mod->name, NULL, 0);
|
|
|
d956f8 |
|
|
|
d956f8 |
commit 2278079efc01124dd509241f6c6eadbd6e19cb2a
|
|
|
d956f8 |
Author: Frank Ch. Eigler <fche@redhat.com>
|
|
|
d956f8 |
Date: Mon Aug 31 17:46:43 2015 -0400
|
|
|
d956f8 |
|
|
|
d956f8 |
PR18889 part: module-init notification via module_{load,free} tracepoints
|
|
|
d956f8 |
|
|
|
d956f8 |
Investigating RHBZ1257399 et al., we found that module_notifier is
|
|
|
d956f8 |
being called too early after kernel commit #4982223e51. This
|
|
|
d956f8 |
precludes normal module section-address computation and thus kprobe
|
|
|
d956f8 |
emplacement. This patch adds hooking into the module_{load,free}
|
|
|
d956f8 |
tracepoints in parallel, because on some kernels (RHEL7.1.Z+) they
|
|
|
d956f8 |
occur at just the right time.
|
|
|
d956f8 |
|
|
|
d956f8 |
On the downside, on recent LKML kernels, attaching to those
|
|
|
d956f8 |
tracepoints requires EXPORT_TRACEPOINT_SYMBOL_GPL's, so until that is
|
|
|
d956f8 |
done (or another workaround made), LKML kernels will still miss out on
|
|
|
d956f8 |
module-init probing.
|
|
|
d956f8 |
|
|
|
d956f8 |
diff --git a/buildrun.cxx b/buildrun.cxx
|
|
|
d956f8 |
index d7a431d..6d66b5a 100644
|
|
|
d956f8 |
--- a/buildrun.cxx
|
|
|
d956f8 |
+++ b/buildrun.cxx
|
|
|
d956f8 |
@@ -1,5 +1,5 @@
|
|
|
d956f8 |
// build/run probes
|
|
|
d956f8 |
-// Copyright (C) 2005-2014 Red Hat Inc.
|
|
|
d956f8 |
+// Copyright (C) 2005-2015 Red Hat Inc.
|
|
|
d956f8 |
//
|
|
|
d956f8 |
// This file is part of systemtap, and is free software. You can
|
|
|
d956f8 |
// redistribute it and/or modify it under the terms of the GNU General
|
|
|
d956f8 |
@@ -377,8 +377,10 @@ compile_pass (systemtap_session& s)
|
|
|
d956f8 |
output_exportconf(s, o, "proc_create_data", "STAPCONF_PROC_CREATE_DATA");
|
|
|
d956f8 |
output_exportconf(s, o, "PDE_DATA", "STAPCONF_PDE_DATA");
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-module-sect-attrs.c", "STAPCONF_MODULE_SECT_ATTRS", NULL);
|
|
|
d956f8 |
-
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-utrace-via-tracepoints.c", "STAPCONF_UTRACE_VIA_TRACEPOINTS", NULL);
|
|
|
d956f8 |
+ output_autoconf(s, o, "autoconf-module-tracepoints.c", "STAPCONF_MODULE_TRACEPOINT", NULL);
|
|
|
d956f8 |
+ output_exportconf(s, o, "__tracepoint_module_load", "STAPCONF_MODULE_TRACEPOINT_EXPORT_LOAD");
|
|
|
d956f8 |
+ output_exportconf(s, o, "__tracepoint_module_free", "STAPCONF_MODULE_TRACEPOINT_EXPORT_FREE");
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-task_work-struct.c", "STAPCONF_TASK_WORK_STRUCT", NULL);
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-vm-area-pte.c", "STAPCONF_VM_AREA_PTE", NULL);
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-relay-umode_t.c", "STAPCONF_RELAY_UMODE_T", NULL);
|
|
|
d956f8 |
diff --git a/runtime/linux/autoconf-module-tracepoints.c b/runtime/linux/autoconf-module-tracepoints.c
|
|
|
d956f8 |
new file mode 100644
|
|
|
d956f8 |
index 0000000..77b938e
|
|
|
d956f8 |
--- /dev/null
|
|
|
d956f8 |
+++ b/runtime/linux/autoconf-module-tracepoints.c
|
|
|
d956f8 |
@@ -0,0 +1,31 @@
|
|
|
d956f8 |
+#include <linux/module.h>
|
|
|
d956f8 |
+#include <trace/events/module.h>
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+// NB: in kernels which do have the requisite pieces, just unconfigured, then
|
|
|
d956f8 |
+// everything below will compile just fine, only returning ENOSYS at runtime.
|
|
|
d956f8 |
+// To get the compile-time error that autoconf needs, check it directly:
|
|
|
d956f8 |
+#ifndef CONFIG_TRACEPOINTS
|
|
|
d956f8 |
+#error "CONFIG_TRACEPOINTS is not enabled"
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+// presuming void *data-parametrized tracepoint callback api
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+void __module_load(void *cb_data, struct module* mod)
|
|
|
d956f8 |
+{
|
|
|
d956f8 |
+ (void) cb_data;
|
|
|
d956f8 |
+ (void) mod;
|
|
|
d956f8 |
+ return;
|
|
|
d956f8 |
+}
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+void __module_free(void *cb_data, struct module* mod)
|
|
|
d956f8 |
+{
|
|
|
d956f8 |
+ (void) cb_data;
|
|
|
d956f8 |
+ (void) mod;
|
|
|
d956f8 |
+ return;
|
|
|
d956f8 |
+}
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+void __autoconf_func(void)
|
|
|
d956f8 |
+{
|
|
|
d956f8 |
+ (void) register_trace_module_load(__module_load, NULL);
|
|
|
d956f8 |
+ (void) register_trace_module_free(__module_free, NULL);
|
|
|
d956f8 |
+}
|
|
|
d956f8 |
diff --git a/runtime/transport/symbols.c b/runtime/transport/symbols.c
|
|
|
d956f8 |
index 9ea2b5b..4266e5d 100644
|
|
|
d956f8 |
--- a/runtime/transport/symbols.c
|
|
|
d956f8 |
+++ b/runtime/transport/symbols.c
|
|
|
d956f8 |
@@ -125,6 +125,7 @@ static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
struct module_sect_attrs *attrs;
|
|
|
d956f8 |
unsigned i, nsections;
|
|
|
d956f8 |
|
|
|
d956f8 |
+ (void) nb;
|
|
|
d956f8 |
(void) attrs;
|
|
|
d956f8 |
(void) i;
|
|
|
d956f8 |
(void) nsections;
|
|
|
d956f8 |
@@ -191,6 +192,21 @@ static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
return NOTIFY_DONE;
|
|
|
d956f8 |
}
|
|
|
d956f8 |
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+#ifdef STAPCONF_MODULE_TRACEPOINT
|
|
|
d956f8 |
+/* We just delegate to the canonical notifier function */
|
|
|
d956f8 |
+static void _stp_module_load_tp(void *data, struct module* mod)
|
|
|
d956f8 |
+{
|
|
|
d956f8 |
+ (void) _stp_module_notifier (NULL, MODULE_STATE_COMING, mod);
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+}
|
|
|
d956f8 |
+static void _stp_module_free_tp(void *data, struct module* mod)
|
|
|
d956f8 |
+{
|
|
|
d956f8 |
+ (void) _stp_module_notifier (NULL, MODULE_STATE_GOING, mod);
|
|
|
d956f8 |
+}
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+
|
|
|
d956f8 |
static int _stp_module_update_self (void)
|
|
|
d956f8 |
{
|
|
|
d956f8 |
/* Only bother if we need unwinding and have module_sect_attrs. */
|
|
|
d956f8 |
diff --git a/runtime/transport/transport.c b/runtime/transport/transport.c
|
|
|
d956f8 |
index 54e9b41..e069a3d 100644
|
|
|
d956f8 |
--- a/runtime/transport/transport.c
|
|
|
d956f8 |
+++ b/runtime/transport/transport.c
|
|
|
d956f8 |
@@ -21,6 +21,23 @@
|
|
|
d956f8 |
#include <linux/delay.h>
|
|
|
d956f8 |
#include <linux/mutex.h>
|
|
|
d956f8 |
#include "../uidgid_compatibility.h"
|
|
|
d956f8 |
+#ifdef STAPCONF_MODULE_TRACEPOINT
|
|
|
d956f8 |
+#include <trace/events/module.h>
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+/* PR18889: After 3.17, commit #de7b2973903c6, tracepoints are
|
|
|
d956f8 |
+ attached by symbol-address rather than by name string. That means
|
|
|
d956f8 |
+ they must be EXPORT_TRACEPOINT_SYMBOL_GPL'd for a tracepoint
|
|
|
d956f8 |
+ [un]register operation. On RHEL7 kernels with out that commit
|
|
|
d956f8 |
+ backported, we can do a tracepoint attach even without the exports. */
|
|
|
d956f8 |
+#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,17,0)
|
|
|
d956f8 |
+#if defined(STAPCONF_MODULE_TRACEPOINT) && defined(STAPCONF_MODULE_TRACEPOINT_EXPORT_LOAD) && defined(STAPCONF_MODULE_TRACEPOINT_EXPORT_FREE)
|
|
|
d956f8 |
+#define STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+#elif defined(STAPCONF_MODULE_TRACEPOINT)
|
|
|
d956f8 |
+#define STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+
|
|
|
d956f8 |
|
|
|
d956f8 |
static int _stp_exit_flag = 0;
|
|
|
d956f8 |
|
|
|
d956f8 |
@@ -83,6 +100,11 @@ static void systemtap_module_exit(void);
|
|
|
d956f8 |
static int systemtap_module_init(void);
|
|
|
d956f8 |
|
|
|
d956f8 |
static int _stp_module_notifier_active = 0;
|
|
|
d956f8 |
+#ifdef STAPCONF_MODULE_TRACEPOINT
|
|
|
d956f8 |
+/* callbacks in runtime/transport/symbols.c */
|
|
|
d956f8 |
+static void _stp_module_load_tp(void *data, struct module* mod);
|
|
|
d956f8 |
+static void _stp_module_free_tp(void *data, struct module* mod);
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
static int _stp_module_notifier (struct notifier_block * nb,
|
|
|
d956f8 |
unsigned long val, void *data);
|
|
|
d956f8 |
static struct notifier_block _stp_module_notifier_nb = {
|
|
|
d956f8 |
@@ -158,11 +180,30 @@ static void _stp_handle_start(struct _stp_msg_start *st)
|
|
|
d956f8 |
failed: something nasty has happened, and
|
|
|
d956f8 |
we want no further probing started. PR16766 */
|
|
|
d956f8 |
if (!_stp_module_notifier_active) {
|
|
|
d956f8 |
- int rc = register_module_notifier(& _stp_module_notifier_nb);
|
|
|
d956f8 |
- if (rc == 0)
|
|
|
d956f8 |
- _stp_module_notifier_active = 1;
|
|
|
d956f8 |
- else
|
|
|
d956f8 |
- _stp_warn ("Cannot register module notifier (%d)\n", rc);
|
|
|
d956f8 |
+#ifdef STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
+ int rc0 = register_trace_module_load (& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
+ if (rc0)
|
|
|
d956f8 |
+ _stp_warn ("Cannot register module load tracepoint (%d)\n", rc0);
|
|
|
d956f8 |
+ else {
|
|
|
d956f8 |
+ int rc1 = register_trace_module_free (& _stp_module_free_tp, NULL);
|
|
|
d956f8 |
+ if (rc1) {
|
|
|
d956f8 |
+ _stp_warn ("Cannot register module free tracepoint (%d)\n", rc1);
|
|
|
d956f8 |
+ unregister_trace_module_load(& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
+ } else {
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+ int rc = register_module_notifier(& _stp_module_notifier_nb);
|
|
|
d956f8 |
+ if (rc == 0)
|
|
|
d956f8 |
+ _stp_module_notifier_active = 1;
|
|
|
d956f8 |
+ else {
|
|
|
d956f8 |
+ _stp_warn ("Cannot register module notifier (%d)\n", rc);
|
|
|
d956f8 |
+#ifdef STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
+ unregister_trace_module_load(& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
+ unregister_trace_module_free(& _stp_module_free_tp, NULL);
|
|
|
d956f8 |
+
|
|
|
d956f8 |
+ }
|
|
|
d956f8 |
+ }
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+ }
|
|
|
d956f8 |
}
|
|
|
d956f8 |
}
|
|
|
d956f8 |
|
|
|
d956f8 |
@@ -198,7 +239,12 @@ static void _stp_cleanup_and_exit(int send_exit)
|
|
|
d956f8 |
|
|
|
d956f8 |
/* Unregister the module notifier. */
|
|
|
d956f8 |
if (_stp_module_notifier_active) {
|
|
|
d956f8 |
- int rc = unregister_module_notifier(& _stp_module_notifier_nb);
|
|
|
d956f8 |
+ int rc;
|
|
|
d956f8 |
+#ifdef STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
+ unregister_trace_module_load(& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
+ unregister_trace_module_free(& _stp_module_free_tp, NULL);
|
|
|
d956f8 |
+#endif
|
|
|
d956f8 |
+ rc = unregister_module_notifier(& _stp_module_notifier_nb);
|
|
|
d956f8 |
if (rc)
|
|
|
d956f8 |
_stp_warn("module_notifier unregister error %d", rc);
|
|
|
d956f8 |
_stp_module_notifier_active = 0;
|
|
|
d956f8 |
|
|
|
d956f8 |
commit 2e67c14dad1c661d2ce0b0ed218b371c1af218ba
|
|
|
d956f8 |
Author: Frank Ch. Eigler <fche@redhat.com>
|
|
|
d956f8 |
Date: Wed Sep 2 11:16:46 2015 -0400
|
|
|
d956f8 |
|
|
|
d956f8 |
PR18889: switch to STP_TRACEPOINT* frontend for kernel tracepoint registration
|
|
|
d956f8 |
|
|
|
d956f8 |
jistone kindly reminded that the runtime/stp_tracepoint.[ch] machinery
|
|
|
d956f8 |
allows us to attach to kernel tracepoints, whether on string- or
|
|
|
d956f8 |
tp*-based kernel APIs, and whether or not the tp* objects are
|
|
|
d956f8 |
EXPORT_TRACEPOINT_SYMBOL_GPL'd. Let's use those; presto we get
|
|
|
d956f8 |
module-init probing back on kernels oldish and newish.
|
|
|
d956f8 |
|
|
|
d956f8 |
diff --git a/buildrun.cxx b/buildrun.cxx
|
|
|
d956f8 |
index 6d66b5a..2ca5933 100644
|
|
|
d956f8 |
--- a/buildrun.cxx
|
|
|
d956f8 |
+++ b/buildrun.cxx
|
|
|
d956f8 |
@@ -379,8 +379,6 @@ compile_pass (systemtap_session& s)
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-module-sect-attrs.c", "STAPCONF_MODULE_SECT_ATTRS", NULL);
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-utrace-via-tracepoints.c", "STAPCONF_UTRACE_VIA_TRACEPOINTS", NULL);
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-module-tracepoints.c", "STAPCONF_MODULE_TRACEPOINT", NULL);
|
|
|
d956f8 |
- output_exportconf(s, o, "__tracepoint_module_load", "STAPCONF_MODULE_TRACEPOINT_EXPORT_LOAD");
|
|
|
d956f8 |
- output_exportconf(s, o, "__tracepoint_module_free", "STAPCONF_MODULE_TRACEPOINT_EXPORT_FREE");
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-task_work-struct.c", "STAPCONF_TASK_WORK_STRUCT", NULL);
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-vm-area-pte.c", "STAPCONF_VM_AREA_PTE", NULL);
|
|
|
d956f8 |
output_autoconf(s, o, "autoconf-relay-umode_t.c", "STAPCONF_RELAY_UMODE_T", NULL);
|
|
|
d956f8 |
diff --git a/runtime/transport/transport.c b/runtime/transport/transport.c
|
|
|
d956f8 |
index e069a3d..db7de46 100644
|
|
|
d956f8 |
--- a/runtime/transport/transport.c
|
|
|
d956f8 |
+++ b/runtime/transport/transport.c
|
|
|
d956f8 |
@@ -1,8 +1,8 @@
|
|
|
d956f8 |
-/* -*- linux-c -*-
|
|
|
d956f8 |
+/* -*- linux-c -*-
|
|
|
d956f8 |
* transport.c - stp transport functions
|
|
|
d956f8 |
*
|
|
|
d956f8 |
* Copyright (C) IBM Corporation, 2005
|
|
|
d956f8 |
- * Copyright (C) Red Hat Inc, 2005-2014
|
|
|
d956f8 |
+ * Copyright (C) Red Hat Inc, 2005-2015
|
|
|
d956f8 |
* Copyright (C) Intel Corporation, 2006
|
|
|
d956f8 |
*
|
|
|
d956f8 |
* This file is part of systemtap, and is free software. You can
|
|
|
d956f8 |
@@ -23,19 +23,7 @@
|
|
|
d956f8 |
#include "../uidgid_compatibility.h"
|
|
|
d956f8 |
#ifdef STAPCONF_MODULE_TRACEPOINT
|
|
|
d956f8 |
#include <trace/events/module.h>
|
|
|
d956f8 |
-#endif
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-/* PR18889: After 3.17, commit #de7b2973903c6, tracepoints are
|
|
|
d956f8 |
- attached by symbol-address rather than by name string. That means
|
|
|
d956f8 |
- they must be EXPORT_TRACEPOINT_SYMBOL_GPL'd for a tracepoint
|
|
|
d956f8 |
- [un]register operation. On RHEL7 kernels with out that commit
|
|
|
d956f8 |
- backported, we can do a tracepoint attach even without the exports. */
|
|
|
d956f8 |
-#if LINUX_VERSION_CODE >= KERNEL_VERSION(3,17,0)
|
|
|
d956f8 |
-#if defined(STAPCONF_MODULE_TRACEPOINT) && defined(STAPCONF_MODULE_TRACEPOINT_EXPORT_LOAD) && defined(STAPCONF_MODULE_TRACEPOINT_EXPORT_FREE)
|
|
|
d956f8 |
-#define STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
-#endif
|
|
|
d956f8 |
-#elif defined(STAPCONF_MODULE_TRACEPOINT)
|
|
|
d956f8 |
-#define STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
+#include "../linux/stp_tracepoint.h"
|
|
|
d956f8 |
#endif
|
|
|
d956f8 |
|
|
|
d956f8 |
|
|
|
d956f8 |
@@ -149,7 +137,7 @@ static void _stp_handle_start(struct _stp_msg_start *st)
|
|
|
d956f8 |
// protect against excessive or premature startup
|
|
|
d956f8 |
handle_startup = (! _stp_start_called && ! _stp_exit_called);
|
|
|
d956f8 |
_stp_start_called = 1;
|
|
|
d956f8 |
-
|
|
|
d956f8 |
+
|
|
|
d956f8 |
if (handle_startup) {
|
|
|
d956f8 |
dbug_trans(1, "stp_handle_start\n");
|
|
|
d956f8 |
|
|
|
d956f8 |
@@ -180,15 +168,15 @@ static void _stp_handle_start(struct _stp_msg_start *st)
|
|
|
d956f8 |
failed: something nasty has happened, and
|
|
|
d956f8 |
we want no further probing started. PR16766 */
|
|
|
d956f8 |
if (!_stp_module_notifier_active) {
|
|
|
d956f8 |
-#ifdef STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
- int rc0 = register_trace_module_load (& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
+#ifdef STAPCONF_MODULE_TRACEPOINT
|
|
|
d956f8 |
+ int rc0 = STP_TRACE_REGISTER(module_load, & _stp_module_load_tp);
|
|
|
d956f8 |
if (rc0)
|
|
|
d956f8 |
_stp_warn ("Cannot register module load tracepoint (%d)\n", rc0);
|
|
|
d956f8 |
else {
|
|
|
d956f8 |
- int rc1 = register_trace_module_free (& _stp_module_free_tp, NULL);
|
|
|
d956f8 |
+ int rc1 = STP_TRACE_REGISTER(module_free, & _stp_module_free_tp);
|
|
|
d956f8 |
if (rc1) {
|
|
|
d956f8 |
_stp_warn ("Cannot register module free tracepoint (%d)\n", rc1);
|
|
|
d956f8 |
- unregister_trace_module_load(& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
+ STP_TRACE_UNREGISTER(module_load, & _stp_module_load_tp);
|
|
|
d956f8 |
} else {
|
|
|
d956f8 |
#endif
|
|
|
d956f8 |
int rc = register_module_notifier(& _stp_module_notifier_nb);
|
|
|
d956f8 |
@@ -196,10 +184,9 @@ static void _stp_handle_start(struct _stp_msg_start *st)
|
|
|
d956f8 |
_stp_module_notifier_active = 1;
|
|
|
d956f8 |
else {
|
|
|
d956f8 |
_stp_warn ("Cannot register module notifier (%d)\n", rc);
|
|
|
d956f8 |
-#ifdef STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
- unregister_trace_module_load(& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
- unregister_trace_module_free(& _stp_module_free_tp, NULL);
|
|
|
d956f8 |
-
|
|
|
d956f8 |
+#ifdef STAPCONF_MODULE_TRACEPOINT
|
|
|
d956f8 |
+ STP_TRACE_UNREGISTER(module_load, & _stp_module_load_tp);
|
|
|
d956f8 |
+ STP_TRACE_UNREGISTER(module_free, & _stp_module_free_tp);
|
|
|
d956f8 |
}
|
|
|
d956f8 |
}
|
|
|
d956f8 |
#endif
|
|
|
d956f8 |
@@ -240,9 +227,9 @@ static void _stp_cleanup_and_exit(int send_exit)
|
|
|
d956f8 |
/* Unregister the module notifier. */
|
|
|
d956f8 |
if (_stp_module_notifier_active) {
|
|
|
d956f8 |
int rc;
|
|
|
d956f8 |
-#ifdef STAP_USE_MODULE_TRACEPOINTS
|
|
|
d956f8 |
- unregister_trace_module_load(& _stp_module_load_tp, NULL);
|
|
|
d956f8 |
- unregister_trace_module_free(& _stp_module_free_tp, NULL);
|
|
|
d956f8 |
+#ifdef STAPCONF_MODULE_TRACEPOINT
|
|
|
d956f8 |
+ STP_TRACE_UNREGISTER(module_load, & _stp_module_load_tp);
|
|
|
d956f8 |
+ STP_TRACE_UNREGISTER(module_free, & _stp_module_free_tp);
|
|
|
d956f8 |
#endif
|
|
|
d956f8 |
rc = unregister_module_notifier(& _stp_module_notifier_nb);
|
|
|
d956f8 |
if (rc)
|
|
|
d956f8 |
@@ -380,7 +367,7 @@ static void _stp_ctl_work_callback(unsigned long val)
|
|
|
d956f8 |
* _stp_transport_close - close ctl and relayfs channels
|
|
|
d956f8 |
*
|
|
|
d956f8 |
* This is called automatically when the module is unloaded.
|
|
|
d956f8 |
- *
|
|
|
d956f8 |
+ *
|
|
|
d956f8 |
*/
|
|
|
d956f8 |
static void _stp_transport_close(void)
|
|
|
d956f8 |
{
|
|
|
d956f8 |
@@ -397,7 +384,7 @@ static void _stp_transport_close(void)
|
|
|
d956f8 |
|
|
|
d956f8 |
/**
|
|
|
d956f8 |
* _stp_transport_init() is called from the module initialization.
|
|
|
d956f8 |
- * It does the bare minimum to exchange commands with staprun
|
|
|
d956f8 |
+ * It does the bare minimum to exchange commands with staprun
|
|
|
d956f8 |
*/
|
|
|
d956f8 |
static int _stp_transport_init(void)
|
|
|
d956f8 |
{
|
|
|
d956f8 |
@@ -657,7 +644,7 @@ static struct dentry *_stp_get_module_dir(void)
|
|
|
d956f8 |
static int _stp_transport_fs_init(const char *module_name)
|
|
|
d956f8 |
{
|
|
|
d956f8 |
struct dentry *root_dir;
|
|
|
d956f8 |
-
|
|
|
d956f8 |
+
|
|
|
d956f8 |
dbug_trans(1, "entry\n");
|
|
|
d956f8 |
if (module_name == NULL)
|
|
|
d956f8 |
return -1;
|
|
|
d956f8 |
|
|
|
d956f8 |
commit 578f5f6f6792fc92d74539a927cd85de5bcbb4dd
|
|
|
d956f8 |
Author: Frank Ch. Eigler <fche@redhat.com>
|
|
|
d956f8 |
Date: Wed Sep 2 11:52:31 2015 -0400
|
|
|
d956f8 |
|
|
|
d956f8 |
PR18889 testing: already done by modules_out_of_tree.exp
|
|
|
d956f8 |
|
|
|
d956f8 |
Ditch bz6503, given that it wasn't reliable.
|
|
|
d956f8 |
|
|
|
d956f8 |
diff --git a/testsuite/systemtap.base/bz6503.exp b/testsuite/systemtap.base/bz6503.exp
|
|
|
d956f8 |
deleted file mode 100644
|
|
|
d956f8 |
index 5d4d2d0..0000000
|
|
|
d956f8 |
--- a/testsuite/systemtap.base/bz6503.exp
|
|
|
d956f8 |
+++ /dev/null
|
|
|
d956f8 |
@@ -1,55 +0,0 @@
|
|
|
d956f8 |
-# Note that this test is *really* testing the bug fix for pr6503:
|
|
|
d956f8 |
-# permit probes on module .init and __exit functions
|
|
|
d956f8 |
-# <http://sourceware.org/bugzilla/show_bug.cgi?id=6503>
|
|
|
d956f8 |
-#
|
|
|
d956f8 |
-# Not BZ6503:
|
|
|
d956f8 |
-# ypserve does not work
|
|
|
d956f8 |
-# <https://bugzilla.redhat.com/show_bug.cgi?id=6503>
|
|
|
d956f8 |
-#
|
|
|
d956f8 |
-# Unfortunately, PR17249 indicates that module-init probes
|
|
|
d956f8 |
-# have subsequently broken (due to kernel notification timing
|
|
|
d956f8 |
-# changes).
|
|
|
d956f8 |
-#
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-set test bz6503
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-if {! [installtest_p]} {
|
|
|
d956f8 |
- untested "$test"
|
|
|
d956f8 |
- return
|
|
|
d956f8 |
-}
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-# If we aren't root, make sure the test still succeeds.
|
|
|
d956f8 |
-set effective_pid [exec /usr/bin/id -u]
|
|
|
d956f8 |
-if {$effective_pid != 0} {
|
|
|
d956f8 |
- set root_cmd "sudo "
|
|
|
d956f8 |
-} else {
|
|
|
d956f8 |
- set root_cmd ""
|
|
|
d956f8 |
-}
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-# jffs2/ext2/fat/vfat should cover a span of kernels.
|
|
|
d956f8 |
-#
|
|
|
d956f8 |
-# Note that this test might fail if there is a filesystem of one of
|
|
|
d956f8 |
-# these types already mounted. The filesystem mount will be
|
|
|
d956f8 |
-# unaffected (since the module can't be removed).
|
|
|
d956f8 |
-spawn stap -t $srcdir/$subdir/bz6503.stp -c "( ($root_cmd /sbin/modprobe jffs2; $root_cmd /sbin/modprobe ext2; $root_cmd /sbin/modprobe fat; $root_cmd /sbin/modprobe vfat); wait; ($root_cmd /sbin/rmmod jffs2; $root_cmd /sbin/rmmod ext2; $root_cmd /sbin/rmmod vfat; $root_cmd /sbin/rmmod fat); wait) 2>/dev/null"
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-set ok 0
|
|
|
d956f8 |
-set ko 0
|
|
|
d956f8 |
-expect {
|
|
|
d956f8 |
- -timeout 60
|
|
|
d956f8 |
- timeout { fail "$test (timeout)" }
|
|
|
d956f8 |
- -re {^-----[^\r\n]*\r\n} { exp_continue }
|
|
|
d956f8 |
- -re {^module[^\r\n]*hits:[^\r\n]*\r\n} { incr ok; exp_continue }
|
|
|
d956f8 |
- -re {^WARNING:[\r\n]*\r\n} { incr ko; exp_continue }
|
|
|
d956f8 |
- -re {^ERROR:[\r\n]*\r\n} { incr ko; exp_continue }
|
|
|
d956f8 |
- eof { }
|
|
|
d956f8 |
-}
|
|
|
d956f8 |
-catch { close} ; catch { wait }
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-# Mark kernels without module refresh support as xfail
|
|
|
d956f8 |
-if {![module_refresh_p]} { setup_xfail *-*-* }
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-if {$ok > 0 && $ko == 0} then { pass "$test $ok" } else { fail "$test $ok $ko"}
|
|
|
d956f8 |
-
|
|
|
d956f8 |
-
|
|
|
d956f8 |
diff --git a/testsuite/systemtap.base/bz6503.stp b/testsuite/systemtap.base/bz6503.stp
|
|
|
d956f8 |
deleted file mode 100644
|
|
|
d956f8 |
index 409149f..0000000
|
|
|
d956f8 |
--- a/testsuite/systemtap.base/bz6503.stp
|
|
|
d956f8 |
+++ /dev/null
|
|
|
d956f8 |
@@ -1,5 +0,0 @@
|
|
|
d956f8 |
-probe module("jffs2").function("*").call ?,
|
|
|
d956f8 |
- module("ext2").function("*").call ?,
|
|
|
d956f8 |
- module("fat").function("*").call ?,
|
|
|
d956f8 |
- module("vfat").function("*").call ?,
|
|
|
d956f8 |
- never { }
|