summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRajan Arora <rarora@redhat.com>2008-10-09 19:58:30 -0400
committerRajan Arora <rarora@redhat.com>2008-10-09 19:58:30 -0400
commit1b1b4cebda9ceaa7a2a2b695a32ecb2588045076 (patch)
treed40f4da6cd854250b2523ddc5ab0563efef050d7
parente2607b19ce56830d64affed6a8ab169697bf2ccf (diff)
downloadsystemtap-steved-1b1b4cebda9ceaa7a2a2b695a32ecb2588045076.tar.gz
systemtap-steved-1b1b4cebda9ceaa7a2a2b695a32ecb2588045076.tar.xz
systemtap-steved-1b1b4cebda9ceaa7a2a2b695a32ecb2588045076.zip
Display source context for error and warning messages (6701)
-rw-r--r--ChangeLog24
-rw-r--r--elaborate.cxx43
-rw-r--r--parse.cxx30
-rw-r--r--parse.h10
-rw-r--r--session.h1
-rw-r--r--staptree.h4
-rw-r--r--tapsets.cxx2
-rw-r--r--testsuite/ChangeLog5
-rwxr-xr-xtestsuite/parseko/source_context.stp5
-rw-r--r--testsuite/systemtap.base/warnings.exp2
10 files changed, 118 insertions, 8 deletions
diff --git a/ChangeLog b/ChangeLog
index 8b1645e4..3806b475 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,27 @@
+2008-10-09 Rajan Arora <rarora@redhat.com>
+
+ * elaborate.cxx (systemtap_session::print_error_source): New.
+ (systemtap_session::print_error): Call it.
+ (systemtap_session::print_warning): Likewise.
+ * parse.cxx (parser::print_error): Likewise.
+ * session.h (struct systemtap_session::print_error_source):
+ Declare it.
+ * parse.cxx (lexer::get_input_contents): New.
+ (parser::parse): Call it.
+ (lexer::set_current_file): New.
+ (parser::parse): Call it.
+ * parse.h (class lexer::get_input_contents): Declare it.
+ (class lexer::set_current_file): Declare it.
+ (class lexer): New member current_file.
+ (class lexer): Update input_contents from vector<char>
+ to std::string.
+ (struct source_loc): New member stap_file.
+ * staptree.h (struct stapfile): New member file_contents.
+
+2008-10-09 Stan Cox <scox@redhat.com>
+
+ * tapsets.cxx (query_cu): Fix typo.
+
2008-10-06 Wenji Huang <wenji.huang@oracle.com>
PR 4886
diff --git a/elaborate.cxx b/elaborate.cxx
index afdc796e..9f0a2a74 100644
--- a/elaborate.cxx
+++ b/elaborate.cxx
@@ -1426,6 +1426,7 @@ void
systemtap_session::print_error (const semantic_error& e)
{
string message_str[2];
+ string align_semantic_error (" ");
// NB: we don't print error messages during listing mode.
if (listing_mode) return;
@@ -1462,6 +1463,12 @@ systemtap_session::print_error (const semantic_error& e)
{
seen_errors.insert (message_str[1]);
cerr << message_str[0];
+
+ if (e.tok1)
+ print_error_source (cerr, align_semantic_error, e.tok1);
+
+ if (e.tok2)
+ print_error_source (cerr, align_semantic_error, e.tok2);
}
if (e.chain)
@@ -1469,15 +1476,51 @@ systemtap_session::print_error (const semantic_error& e)
}
void
+systemtap_session::print_error_source (std::ostream& message,
+ std::string& align, const token* tok)
+{
+ unsigned i = 0;
+ unsigned line = tok->location.line;
+ unsigned col = tok->location.column;
+ string file_contents;
+ if (tok->location.stap_file)
+ file_contents = tok->location.stap_file->file_contents;
+ else
+ //No source to print, silently exit
+ return;
+ size_t start_pos = 0, end_pos = 0;
+ //Navigate to the appropriate line
+ while (i != line && end_pos != std::string::npos)
+ {
+ start_pos = end_pos;
+ end_pos = file_contents.find ('\n', start_pos) + 1;
+ i++;
+ }
+ message << align << "source: " << file_contents.substr (start_pos, end_pos-start_pos-1) << endl;
+ message << align << " ";
+ //Navigate to the appropriate column
+ for (i=start_pos; i<start_pos+col-1; i++)
+ {
+ if(isspace(file_contents[i]))
+ message << file_contents[i];
+ else
+ message << ' ';
+ }
+ message << "^" << endl;
+}
+
+void
systemtap_session::print_warning (const string& message_str, const token* tok)
{
// Duplicate elimination
+ string align_warning (" ");
if (seen_warnings.find (message_str) == seen_warnings.end())
{
seen_warnings.insert (message_str);
clog << "WARNING: " << message_str;
if (tok) { clog << ": "; print_token (clog, tok); }
clog << endl;
+ print_error_source (clog, align_warning, tok);
}
}
diff --git a/parse.cxx b/parse.cxx
index 1c1772f6..1982eb44 100644
--- a/parse.cxx
+++ b/parse.cxx
@@ -124,17 +124,22 @@ operator << (ostream& o, const token& t)
void
parser::print_error (const parse_error &pe)
{
+ string align_parse_error (" ");
cerr << "parse error: " << pe.what () << endl;
if (pe.tok)
{
cerr << "\tat: " << *pe.tok << endl;
+ session.print_error_source (cerr, align_parse_error, pe.tok);
}
else
{
const token* t = last_t;
if (t)
- cerr << "\tsaw: " << *t << endl;
+ {
+ cerr << "\tsaw: " << *t << endl;
+ session.print_error_source (cerr, align_parse_error, t);
+ }
else
cerr << "\tsaw: " << input_name << " EOF" << endl;
}
@@ -579,15 +584,27 @@ parser::peek_kw (std::string const & kw)
lexer::lexer (istream& i, const string& in, systemtap_session& s):
- input (i), input_name (in),
+ input (i), input_name (in), input_contents (""),
input_pointer (0), cursor_suspend_count(0),
- cursor_line (1), cursor_column (1), session(s)
+ cursor_line (1), cursor_column (1), session(s),
+ current_file (0)
{
char c;
while(input.get(c))
input_contents.push_back(c);
}
+std::string
+lexer::get_input_contents ()
+{
+ return input_contents;
+}
+
+void
+lexer::set_current_file (stapfile* f)
+{
+ current_file = f;
+}
int
lexer::input_peek (unsigned n)
@@ -642,6 +659,8 @@ lexer::scan (bool wildcard)
{
token* n = new token;
n->location.file = input_name;
+ if (current_file)
+ n->location.stap_file = current_file;
unsigned semiskipped_p = 0;
@@ -945,6 +964,8 @@ stapfile*
parser::parse ()
{
stapfile* f = new stapfile;
+ input.set_current_file (f);
+ f->file_contents = input.get_input_contents ();
f->name = input_name;
bool empty = true;
@@ -1013,15 +1034,18 @@ parser::parse ()
{
cerr << "Input file '" << input_name << "' is empty or missing." << endl;
delete f;
+ input.set_current_file (0);
return 0;
}
else if (num_errors > 0)
{
cerr << num_errors << " parse error(s)." << endl;
delete f;
+ input.set_current_file (0);
return 0;
}
+ input.set_current_file (0);
return f;
}
diff --git a/parse.h b/parse.h
index cf31f4f8..2e2b656f 100644
--- a/parse.h
+++ b/parse.h
@@ -18,11 +18,14 @@
#include <stdexcept>
#include <stdint.h>
+struct stapfile;
+
struct source_loc
{
std::string file;
unsigned line;
unsigned column;
+ stapfile* stap_file;
};
std::ostream& operator << (std::ostream& o, const source_loc& loc);
@@ -71,6 +74,8 @@ class lexer
public:
token* scan (bool wildcard=false);
lexer (std::istream&, const std::string&, systemtap_session&);
+ std::string get_input_contents ();
+ void set_current_file (stapfile* f);
private:
int input_get ();
@@ -79,16 +84,15 @@ private:
int input_peek (unsigned n=0);
std::istream& input;
std::string input_name;
- std::vector<char> input_contents;
+ std::string input_contents;
int input_pointer; // index into input_contents
unsigned cursor_suspend_count;
unsigned cursor_line;
unsigned cursor_column;
systemtap_session& session;
+ stapfile* current_file;
};
-
-struct stapfile;
struct probe;
struct probe_alias;
struct vardecl;
diff --git a/session.h b/session.h
index b8bd971a..4746422f 100644
--- a/session.h
+++ b/session.h
@@ -179,6 +179,7 @@ struct systemtap_session
const token* last_token;
void print_token (std::ostream& o, const token* tok);
void print_error (const semantic_error& e);
+ void print_error_source (std::ostream&, std::string&, const token* tok);
void print_warning (const std::string& w, const token* tok = 0);
// reNB: new POD members likely need to be explicitly cleared in the ctor.
diff --git a/staptree.h b/staptree.h
index 770a731e..c35728cb 100644
--- a/staptree.h
+++ b/staptree.h
@@ -574,8 +574,10 @@ struct stapfile
std::vector<functiondecl*> functions;
std::vector<vardecl*> globals;
std::vector<embeddedcode*> embeds;
+ std::string file_contents;
bool privileged;
- stapfile (): privileged (false) {}
+ stapfile (): file_contents (""),
+ privileged (false) {}
void print (std::ostream& o) const;
};
diff --git a/tapsets.cxx b/tapsets.cxx
index a5a62c7a..3a70936f 100644
--- a/tapsets.cxx
+++ b/tapsets.cxx
@@ -3799,7 +3799,7 @@ query_cu (Dwarf_Die * cudie, void * arg)
{
stringstream msg;
msg << "address 0x" << hex << queryaddr
- << "does not match the begining of a statement";
+ << " does not match the beginning of a statement";
throw semantic_error(msg.str());
}
}
diff --git a/testsuite/ChangeLog b/testsuite/ChangeLog
index 5ddee32c..ceef8c40 100644
--- a/testsuite/ChangeLog
+++ b/testsuite/ChangeLog
@@ -1,3 +1,8 @@
+2008-10-09 Rajan Arora <rarora@redhat.com>
+
+ * systemtap.base/warnings.exp: Allow for source: lines.
+ * parseko/source_context.stp: New file.
+
2008-10-04 Mark Wielaard <mjw@redhat.com>
* systemtap.base/debugpath.exp: Guess a bit more intelligently
diff --git a/testsuite/parseko/source_context.stp b/testsuite/parseko/source_context.stp
new file mode 100755
index 00000000..403b203b
--- /dev/null
+++ b/testsuite/parseko/source_context.stp
@@ -0,0 +1,5 @@
+probe timer.ms(123)
+{
+printf("Probe successful\n")
+ eeexit ()
+}
diff --git a/testsuite/systemtap.base/warnings.exp b/testsuite/systemtap.base/warnings.exp
index a90860d9..4bbef40d 100644
--- a/testsuite/systemtap.base/warnings.exp
+++ b/testsuite/systemtap.base/warnings.exp
@@ -6,6 +6,8 @@ expect {
-timeout 30
-re {^WARNING:[^\r\n]*\r\n} { incr ok; exp_continue }
-re {^[^\r\n]*.ko\r\n} { incr ok; exp_continue }
+ -re {^[^\r]*source:[^\r\n]*\r\n} {exp_continue}
+ -re {^[^\r\n]*\^[^\r\n]*\r\n} {exp_continue}
timeout { fail "$test (timeout)" }
eof { }
}