summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--buildrun.cxx13
-rw-r--r--buildrun.h3
-rw-r--r--hash.cxx7
-rw-r--r--hash.h4
-rw-r--r--tapsets.cxx58
5 files changed, 55 insertions, 30 deletions
diff --git a/buildrun.cxx b/buildrun.cxx
index cebe3b8e..86940643 100644
--- a/buildrun.cxx
+++ b/buildrun.cxx
@@ -374,8 +374,7 @@ run_pass (systemtap_session& s)
// Build a tiny kernel module to query tracepoints
int
make_tracequery(systemtap_session& s, string& name,
- const std::string& header,
- const vector<string>& extra_headers)
+ const vector<string>& headers)
{
static unsigned tick = 0;
string basename("tracequery_kmod_" + lex_cast(++tick));
@@ -415,13 +414,9 @@ make_tracequery(systemtap_session& s, string& name,
osrc << "#define DEFINE_TRACE(name, proto, args) \\" << endl;
osrc << " DECLARE_TRACE(name, TPPROTO(proto), TPARGS(args))" << endl;
- // PR9993: Add extra headers to work around undeclared types in individual
- // include/trace/foo.h files
- for (unsigned z=0; z<extra_headers.size(); z++)
- osrc << "#include <" << extra_headers[z] << ">\n";
-
- // add the requested tracepoint header
- osrc << "#include <" << header << ">" << endl;
+ // add the specified headers
+ for (unsigned z=0; z<headers.size(); z++)
+ osrc << "#include <" << headers[z] << ">\n";
// finish up the module source
osrc << "#endif /* CONFIG_TRACEPOINTS */" << endl;
diff --git a/buildrun.h b/buildrun.h
index bec81aca..318befd7 100644
--- a/buildrun.h
+++ b/buildrun.h
@@ -15,8 +15,7 @@ int compile_pass (systemtap_session& s);
int run_pass (systemtap_session& s);
int make_tracequery(systemtap_session& s, std::string& name,
- const std::string& header,
- const std::vector<std::string>& extra_headers);
+ const std::vector<std::string>& headers);
int make_typequery(systemtap_session& s, std::string& module);
#endif // BUILDRUN_H
diff --git a/hash.cxx b/hash.cxx
index df29afed..a4589577 100644
--- a/hash.cxx
+++ b/hash.cxx
@@ -263,13 +263,14 @@ find_hash (systemtap_session& s, const string& script)
string
-find_tracequery_hash (systemtap_session& s, const string& header)
+find_tracequery_hash (systemtap_session& s, const vector<string>& headers)
{
hash h;
get_base_hash(s, h);
- // Add the tracepoint header to the computed hash
- h.add_file(header);
+ // Add the tracepoint headers to the computed hash
+ for (size_t i = 0; i < headers.size(); ++i)
+ h.add_file(headers[i]);
// Add any custom kbuild flags
for (unsigned i = 0; i < s.kbuildflags.size(); i++)
diff --git a/hash.h b/hash.h
index f52fd89e..6bb1c78a 100644
--- a/hash.h
+++ b/hash.h
@@ -1,4 +1,5 @@
#include <string>
+#include <vector>
extern "C" {
#include <string.h>
@@ -36,7 +37,8 @@ public:
};
void find_hash (systemtap_session& s, const std::string& script);
-std::string find_tracequery_hash (systemtap_session& s, const std::string& header);
+std::string find_tracequery_hash (systemtap_session& s,
+ const std::vector<std::string>& headers);
std::string find_typequery_hash (systemtap_session& s, const std::string& name);
/* vim: set sw=2 ts=8 cino=>4,n-2,{2,^-2,t0,(0,u0,w1,M1 : */
diff --git a/tapsets.cxx b/tapsets.cxx
index bedb267a..dfa5f302 100644
--- a/tapsets.cxx
+++ b/tapsets.cxx
@@ -6047,7 +6047,8 @@ struct tracepoint_builder: public derived_probe_builder
private:
dwflpp *dw;
bool init_dw(systemtap_session& s);
- string get_tracequery_module(systemtap_session& s, const string& header);
+ string get_tracequery_module(systemtap_session& s,
+ const vector<string>& headers);
public:
@@ -6071,16 +6072,21 @@ public:
string
tracepoint_builder::get_tracequery_module(systemtap_session& s,
- const string& header)
+ const vector<string>& headers)
{
if (s.verbose > 2)
- clog << "Pass 2: getting a tracequery for " << header << endl;
+ {
+ clog << "Pass 2: getting a tracequery for "
+ << headers.size() << " headers:" << endl;
+ for (size_t i = 0; i < headers.size(); ++i)
+ clog << " " << headers[i] << endl;
+ }
string tracequery_path;
if (s.use_cache)
{
// see if the cached module exists
- tracequery_path = find_tracequery_hash(s, header);
+ tracequery_path = find_tracequery_hash(s, headers);
if (!tracequery_path.empty())
{
int fd = open(tracequery_path.c_str(), O_RDONLY);
@@ -6096,13 +6102,22 @@ tracepoint_builder::get_tracequery_module(systemtap_session& s,
// no cached module, time to make it
- size_t root_pos = header.rfind("/include/");
- string short_header = (root_pos != string::npos) ?
- header.substr(root_pos + 9) : header;
+ // PR9993: Add extra headers to work around undeclared types in individual
+ // include/trace/foo.h files
+ vector<string> short_headers = tracepoint_extra_headers();
+
+ // add each requested tracepoint header
+ for (size_t i = 0; i < headers.size(); ++i)
+ {
+ const string &header = headers[i];
+ size_t root_pos = header.rfind("/include/");
+ short_headers.push_back((root_pos != string::npos) ?
+ header.substr(root_pos + 9) :
+ header);
+ }
string tracequery_ko;
- int rc = make_tracequery(s, tracequery_ko, short_header,
- tracepoint_extra_headers());
+ int rc = make_tracequery(s, tracequery_ko, short_headers);
if (rc != 0)
tracequery_ko = "/dev/null";
@@ -6128,6 +6143,7 @@ tracepoint_builder::init_dw(systemtap_session& s)
return true;
vector<string> tracequery_modules;
+ vector<string> system_headers;
glob_t trace_glob;
string globs[] = {
@@ -6145,6 +6161,8 @@ tracepoint_builder::init_dw(systemtap_session& s)
string header(trace_glob.gl_pathv[i]);
// filter out a few known "internal-only" headers
+ if (header.find("/define_trace.h") != string::npos)
+ continue;
if (header.find("/ftrace.h") != string::npos)
continue;
if (header.find("/trace_events.h") != string::npos)
@@ -6152,16 +6170,26 @@ tracepoint_builder::init_dw(systemtap_session& s)
if (header.find("_event_types.h") != string::npos)
continue;
- string tracequery_path = get_tracequery_module(s, header);
-
- /* NB: An empty tracequery means that the
- * header didn't even compile correctly. */
- if (get_file_size(tracequery_path))
- tracequery_modules.push_back(tracequery_path);
+ system_headers.push_back(header);
}
globfree(&trace_glob);
}
+ // First attempt to do all system headers in one go
+ string tracequery_path = get_tracequery_module(s, system_headers);
+ // NB: An empty tracequery means that the header didn't compile correctly
+ if (get_file_size(tracequery_path))
+ tracequery_modules.push_back(tracequery_path);
+ else
+ // Otherwise try to do them one at a time (PR10424)
+ for (size_t i = 0; i < system_headers.size(); ++i)
+ {
+ vector<string> one_header(1, system_headers[i]);
+ tracequery_path = get_tracequery_module(s, one_header);
+ if (get_file_size(tracequery_path))
+ tracequery_modules.push_back(tracequery_path);
+ }
+
// TODO: consider other sources of tracepoint headers too, like from
// a command-line parameter or some environment or .systemtaprc