From 9ecd5ee81d642fed89246924b240bf3d3b0b8e64 Mon Sep 17 00:00:00 2001 From: Patrick Walton Date: Tue, 24 Jan 2012 21:42:54 -0800 Subject: [PATCH] rustc: Split diagnostics into "span diagnostics" and "diagnostics". The former contain a codemap (which is per-crate), and the latter don't. This will be useful in order to allow more than one crate to be compiled in one run of the compiler. --- src/cargo/cargo.rs | 3 +- src/comp/driver/diagnostic.rs | 104 ++++++++++++++++++++------------ src/comp/driver/driver.rs | 10 +-- src/comp/driver/session.rs | 30 ++++----- src/comp/syntax/parse/lexer.rs | 13 ++-- src/comp/syntax/parse/parser.rs | 21 ++++--- src/comp/syntax/print/pprust.rs | 5 +- src/fuzzer/fuzzer.rs | 13 ++-- src/rustdoc/parse.rs | 3 +- 9 files changed, 118 insertions(+), 84 deletions(-) diff --git a/src/cargo/cargo.rs b/src/cargo/cargo.rs index c2b51c15e04..69546118c49 100644 --- a/src/cargo/cargo.rs +++ b/src/cargo/cargo.rs @@ -100,10 +100,11 @@ fn load_link(mis: [@ast::meta_item]) -> (option::t, fn load_pkg(filename: str) -> option::t { let cm = codemap::new_codemap(); + let handler = diagnostic::mk_handler(none); let sess = @{ cm: cm, mutable next_id: 1, - diagnostic: diagnostic::mk_handler(cm, none), + span_diagnostic: diagnostic::mk_span_handler(handler, cm), mutable chpos: 0u, mutable byte_pos: 0u }; diff --git a/src/comp/driver/diagnostic.rs b/src/comp/driver/diagnostic.rs index 0694a357f1b..3d7cbf3701e 100644 --- a/src/comp/driver/diagnostic.rs +++ b/src/comp/driver/diagnostic.rs @@ -5,51 +5,82 @@ import codemap::span; export emitter, emit; export level, fatal, error, warning, note; -export handler, mk_handler; +export span_handler, handler, mk_span_handler, mk_handler; +export codemap_span_handler, codemap_handler; export ice_msg; type emitter = fn@(cmsp: option<(codemap::codemap, span)>, msg: str, lvl: level); -iface handler { +iface span_handler { fn span_fatal(sp: span, msg: str) -> !; - fn fatal(msg: str) -> !; fn span_err(sp: span, msg: str); - fn err(msg: str); - fn has_errors() -> bool; - fn abort_if_errors(); fn span_warn(sp: span, msg: str); - fn warn(msg: str); fn span_note(sp: span, msg: str); - fn note(msg: str); fn span_bug(sp: span, msg: str) -> !; - fn bug(msg: str) -> !; fn span_unimpl(sp: span, msg: str) -> !; - fn unimpl(msg: str) -> !; + fn handler() -> handler; } -type codemap_t = @{ - cm: codemap::codemap, +iface handler { + fn fatal(msg: str) -> !; + fn err(msg: str); + fn bump_err_count(); + fn has_errors() -> bool; + fn abort_if_errors(); + fn warn(msg: str); + fn note(msg: str); + fn bug(msg: str) -> !; + fn unimpl(msg: str) -> !; + fn emit(cmsp: option<(codemap::codemap, span)>, msg: str, lvl: level); +} + +type handler_t = @{ mutable err_count: uint, - emit: emitter + _emit: emitter }; -impl codemap_handler of handler for codemap_t { +type codemap_t = @{ + handler: handler, + cm: codemap::codemap +}; + +impl codemap_span_handler of span_handler for codemap_t { fn span_fatal(sp: span, msg: str) -> ! { - self.emit(some((self.cm, sp)), msg, fatal); - fail; - } - fn fatal(msg: str) -> ! { - self.emit(none, msg, fatal); + self.handler.emit(some((self.cm, sp)), msg, fatal); fail; } fn span_err(sp: span, msg: str) { - self.emit(some((self.cm, sp)), msg, error); - self.err_count += 1u; + self.handler.emit(some((self.cm, sp)), msg, error); + self.handler.bump_err_count(); + } + fn span_warn(sp: span, msg: str) { + self.handler.emit(some((self.cm, sp)), msg, warning); + } + fn span_note(sp: span, msg: str) { + self.handler.emit(some((self.cm, sp)), msg, note); + } + fn span_bug(sp: span, msg: str) -> ! { + self.span_fatal(sp, ice_msg(msg)); + } + fn span_unimpl(sp: span, msg: str) -> ! { + self.span_bug(sp, "unimplemented " + msg); + } + fn handler() -> handler { + self.handler + } +} + +impl codemap_handler of handler for handler_t { + fn fatal(msg: str) -> ! { + self._emit(none, msg, fatal); + fail; } fn err(msg: str) { - self.emit(none, msg, error); + self._emit(none, msg, error); + } + fn bump_err_count() { self.err_count += 1u; } fn has_errors() -> bool { self.err_count > 0u } @@ -58,36 +89,30 @@ impl codemap_handler of handler for codemap_t { self.fatal("aborting due to previous errors"); } } - fn span_warn(sp: span, msg: str) { - self.emit(some((self.cm, sp)), msg, warning); - } fn warn(msg: str) { - self.emit(none, msg, warning); - } - fn span_note(sp: span, msg: str) { - self.emit(some((self.cm, sp)), msg, note); + self._emit(none, msg, warning); } fn note(msg: str) { - self.emit(none, msg, note); - } - fn span_bug(sp: span, msg: str) -> ! { - self.span_fatal(sp, ice_msg(msg)); + self._emit(none, msg, note); } fn bug(msg: str) -> ! { self.fatal(ice_msg(msg)); } - fn span_unimpl(sp: span, msg: str) -> ! { - self.span_bug(sp, "unimplemented " + msg); - } fn unimpl(msg: str) -> ! { self.bug("unimplemented " + msg); } + fn emit(cmsp: option<(codemap::codemap, span)>, msg: str, lvl: level) { + self._emit(cmsp, msg, lvl); + } } fn ice_msg(msg: str) -> str { #fmt["internal compiler error %s", msg] } -fn mk_handler(cm: codemap::codemap, - emitter: option) -> handler { +fn mk_span_handler(handler: handler, cm: codemap::codemap) -> span_handler { + @{ handler: handler, cm: cm } as span_handler +} + +fn mk_handler(emitter: option) -> handler { let emit = alt emitter { some(e) { e } @@ -101,9 +126,8 @@ fn mk_handler(cm: codemap::codemap, }; @{ - cm: cm, mutable err_count: 0u, - emit: emit + _emit: emit } as handler } diff --git a/src/comp/driver/driver.rs b/src/comp/driver/driver.rs index 9d8d9ac03b7..f500936aa73 100644 --- a/src/comp/driver/driver.rs +++ b/src/comp/driver/driver.rs @@ -299,7 +299,7 @@ fn pretty_print_input(sess: session, cfg: ast::crate_cfg, input: str, } ppm_expanded | ppm_normal {} } - pprust::print_crate(sess.codemap, sess.diagnostic, crate, input, + pprust::print_crate(sess.codemap, sess.span_diagnostic, crate, input, io::string_reader(src), io::stdout(), ann); } @@ -481,21 +481,23 @@ fn build_session(sopts: @session::options, input: str, sopts.addl_lib_search_paths); let codemap = codemap::new_codemap(); let diagnostic_handler = - diagnostic::mk_handler(codemap, some(demitter)); + diagnostic::mk_handler(some(demitter)); + let span_diagnostic_handler = + diagnostic::mk_span_handler(diagnostic_handler, codemap); @{targ_cfg: target_cfg, opts: sopts, cstore: cstore, parse_sess: @{ cm: codemap, mutable next_id: 1, - diagnostic: diagnostic_handler, + span_diagnostic: span_diagnostic_handler, mutable chpos: 0u, mutable byte_pos: 0u }, codemap: codemap, // For a library crate, this is always none mutable main_fn: none, - diagnostic: diagnostic_handler, + span_diagnostic: span_diagnostic_handler, filesearch: filesearch, mutable building_library: false, working_dir: fs::dirname(input)} diff --git a/src/comp/driver/session.rs b/src/comp/driver/session.rs index ec9d71c6f79..31ddd3d241f 100644 --- a/src/comp/driver/session.rs +++ b/src/comp/driver/session.rs @@ -60,53 +60,53 @@ type session = @{targ_cfg: @config, codemap: codemap::codemap, // For a library crate, this is always none mutable main_fn: option::t, - diagnostic: diagnostic::handler, + span_diagnostic: diagnostic::span_handler, filesearch: filesearch::filesearch, mutable building_library: bool, working_dir: str}; impl session for session { fn span_fatal(sp: span, msg: str) -> ! { - self.diagnostic.span_fatal(sp, msg) + self.span_diagnostic.span_fatal(sp, msg) } fn fatal(msg: str) -> ! { - self.diagnostic.fatal(msg) + self.span_diagnostic.handler().fatal(msg) } fn span_err(sp: span, msg: str) { - self.diagnostic.span_err(sp, msg) + self.span_diagnostic.span_err(sp, msg) } fn err(msg: str) { - self.diagnostic.err(msg) + self.span_diagnostic.handler().err(msg) } fn has_errors() -> bool { - self.diagnostic.has_errors() + self.span_diagnostic.handler().has_errors() } fn abort_if_errors() { - self.diagnostic.abort_if_errors() + self.span_diagnostic.handler().abort_if_errors() } fn span_warn(sp: span, msg: str) { - self.diagnostic.span_warn(sp, msg) + self.span_diagnostic.span_warn(sp, msg) } fn warn(msg: str) { - self.diagnostic.warn(msg) + self.span_diagnostic.handler().warn(msg) } fn span_note(sp: span, msg: str) { - self.diagnostic.span_note(sp, msg) + self.span_diagnostic.span_note(sp, msg) } fn note(msg: str) { - self.diagnostic.note(msg) + self.span_diagnostic.handler().note(msg) } fn span_bug(sp: span, msg: str) -> ! { - self.diagnostic.span_bug(sp, msg) + self.span_diagnostic.span_bug(sp, msg) } fn bug(msg: str) -> ! { - self.diagnostic.bug(msg) + self.span_diagnostic.handler().bug(msg) } fn span_unimpl(sp: span, msg: str) -> ! { - self.diagnostic.span_unimpl(sp, msg) + self.span_diagnostic.span_unimpl(sp, msg) } fn unimpl(msg: str) -> ! { - self.diagnostic.unimpl(msg) + self.span_diagnostic.handler().unimpl(msg) } fn next_node_id() -> ast::node_id { ret syntax::parse::parser::next_node_id(self.parse_sess); diff --git a/src/comp/syntax/parse/lexer.rs b/src/comp/syntax/parse/lexer.rs index 3dc1666b11e..f51838ef28e 100644 --- a/src/comp/syntax/parse/lexer.rs +++ b/src/comp/syntax/parse/lexer.rs @@ -10,7 +10,7 @@ import driver::diagnostic; type reader = @{ cm: codemap::codemap, - diagnostic: diagnostic::handler, + span_diagnostic: diagnostic::span_handler, src: str, len: uint, mutable col: uint, @@ -49,17 +49,18 @@ impl reader for reader { } else { self.curr = -1 as char; } } fn fatal(m: str) -> ! { - self.diagnostic.span_fatal( + self.span_diagnostic.span_fatal( ast_util::mk_sp(self.chpos, self.chpos), m) } } fn new_reader(cm: codemap::codemap, - diagnostic: diagnostic::handler, + span_diagnostic: diagnostic::span_handler, src: str, filemap: codemap::filemap, itr: @interner::interner) -> reader { - let r = @{cm: cm, diagnostic: diagnostic, + let r = @{cm: cm, + span_diagnostic: span_diagnostic, src: src, len: str::byte_len(src), mutable col: 0u, mutable pos: 0u, mutable curr: -1 as char, mutable chpos: filemap.start_pos.ch, mutable strs: [], @@ -667,13 +668,13 @@ fn is_lit(t: token::token) -> bool { type lit = {lit: str, pos: uint}; fn gather_comments_and_literals(cm: codemap::codemap, - diagnostic: diagnostic::handler, + span_diagnostic: diagnostic::span_handler, path: str, srdr: io::reader) -> {cmnts: [cmnt], lits: [lit]} { let src = str::unsafe_from_bytes(srdr.read_whole_stream()); let itr = @interner::mk::(str::hash, str::eq); - let rdr = new_reader(cm, diagnostic, src, + let rdr = new_reader(cm, span_diagnostic, src, codemap::new_filemap(path, 0u, 0u), itr); let comments: [cmnt] = []; let literals: [lit] = []; diff --git a/src/comp/syntax/parse/parser.rs b/src/comp/syntax/parse/parser.rs index 1ae1cc2ecb9..504a37647b8 100644 --- a/src/comp/syntax/parse/parser.rs +++ b/src/comp/syntax/parse/parser.rs @@ -24,7 +24,7 @@ enum file_type { CRATE_FILE, SOURCE_FILE, } type parse_sess = @{ cm: codemap::codemap, mutable next_id: node_id, - diagnostic: diagnostic::handler, + span_diagnostic: diagnostic::span_handler, // these two must be kept up to date mutable chpos: uint, mutable byte_pos: uint @@ -78,13 +78,13 @@ impl parser for parser { ret self.buffer[distance - 1u].tok; } fn fatal(m: str) -> ! { - self.sess.diagnostic.span_fatal(self.span, m) + self.sess.span_diagnostic.span_fatal(self.span, m) } fn span_fatal(sp: span, m: str) -> ! { - self.sess.diagnostic.span_fatal(sp, m) + self.sess.span_diagnostic.span_fatal(sp, m) } fn warn(m: str) { - self.sess.diagnostic.span_warn(self.span, m) + self.sess.span_diagnostic.span_warn(self.span, m) } fn get_str(i: token::str_num) -> str { interner::get(*self.reader.interner, i) @@ -101,14 +101,14 @@ fn new_parser_from_file(sess: parse_sess, cfg: ast::crate_cfg, path: str, src } result::err(e) { - sess.diagnostic.fatal(e) + sess.span_diagnostic.handler().fatal(e) } }; let filemap = codemap::new_filemap(path, sess.chpos, sess.byte_pos); sess.cm.files += [filemap]; let itr = @interner::mk(str::hash, str::eq); - let rdr = lexer::new_reader(sess.cm, sess.diagnostic, - src, filemap, itr); + let rdr = lexer::new_reader(sess.cm, sess.span_diagnostic, src, filemap, + itr); ret new_parser(sess, cfg, rdr, ftype); } @@ -118,8 +118,8 @@ fn new_parser_from_source_str(sess: parse_sess, cfg: ast::crate_cfg, let filemap = codemap::new_filemap(name, sess.chpos, sess.byte_pos); sess.cm.files += [filemap]; let itr = @interner::mk(str::hash, str::eq); - let rdr = lexer::new_reader(sess.cm, sess.diagnostic, - source, filemap, itr); + let rdr = lexer::new_reader(sess.cm, sess.span_diagnostic, source, + filemap, itr); ret new_parser(sess, cfg, rdr, ftype); } @@ -2628,7 +2628,8 @@ fn parse_crate_from_file(input: str, cfg: ast::crate_cfg, sess: parse_sess) -> } else if str::ends_with(input, ".rs") { parse_crate_from_source_file(input, cfg, sess) } else { - sess.diagnostic.fatal("unknown input file type: " + input) + sess.span_diagnostic.handler().fatal("unknown input file type: " + + input) } } diff --git a/src/comp/syntax/print/pprust.rs b/src/comp/syntax/print/pprust.rs index 4327ccf9ac0..1f09436361d 100644 --- a/src/comp/syntax/print/pprust.rs +++ b/src/comp/syntax/print/pprust.rs @@ -60,11 +60,12 @@ const default_columns: uint = 78u; // Requires you to pass an input filename and reader so that // it can scan the input text for comments and literals to // copy forward. -fn print_crate(cm: codemap, diagnostic: diagnostic::handler, +fn print_crate(cm: codemap, span_diagnostic: diagnostic::span_handler, crate: @ast::crate, filename: str, in: io::reader, out: io::writer, ann: pp_ann) { let boxes: [pp::breaks] = []; - let r = lexer::gather_comments_and_literals(cm, diagnostic, filename, in); + let r = lexer::gather_comments_and_literals(cm, span_diagnostic, filename, + in); let s = @{s: pp::mk_printer(out, default_columns), cm: some(cm), diff --git a/src/fuzzer/fuzzer.rs b/src/fuzzer/fuzzer.rs index c1b3ad5f341..8ca129dbe50 100644 --- a/src/fuzzer/fuzzer.rs +++ b/src/fuzzer/fuzzer.rs @@ -259,10 +259,11 @@ fn check_variants_T( let crate2 = @replacer(crate, i, things[j], cx.mode); // It would be best to test the *crate* for stability, but testing the // string for stability is easier and ok for now. + let handler = diagnostic::mk_handler(none); let str3 = as_str(bind pprust::print_crate( codemap, - diagnostic::mk_handler(codemap, none), + diagnostic::mk_span_handler(handler, codemap), crate2, filename, io::string_reader(""), _, @@ -416,10 +417,11 @@ fn check_compiling(filename: str) -> happiness { fn parse_and_print(code: str) -> str { let filename = "tmp.rs"; let cm = codemap::new_codemap(); + let handler = diagnostic::mk_handler(none); let sess = @{ cm: cm, mutable next_id: 0, - diagnostic: diagnostic::mk_handler(cm, none), + span_diagnostic: diagnostic::mk_span_handler(handler, cm), mutable chpos: 0u, mutable byte_pos: 0u }; @@ -427,7 +429,7 @@ fn parse_and_print(code: str) -> str { let crate = parser::parse_crate_from_source_str( filename, code, [], sess); ret as_str(bind pprust::print_crate(sess.cm, - sess.diagnostic, + sess.span_diagnostic, crate, filename, io::string_reader(code), _, @@ -565,10 +567,11 @@ fn check_variants(files: [str], cx: context) { log(error, "check_variants: " + file); let cm = codemap::new_codemap(); + let handler = diagnostic::mk_handler(none); let sess = @{ cm: cm, mutable next_id: 0, - diagnostic: diagnostic::mk_handler(cm, none), + span_diagnostic: diagnostic::mk_span_handler(handler, cm), mutable chpos: 0u, mutable byte_pos: 0u }; @@ -578,7 +581,7 @@ fn check_variants(files: [str], cx: context) { s, [], sess); #error("%s", as_str(bind pprust::print_crate(sess.cm, - sess.diagnostic, + sess.span_diagnostic, crate, file, io::string_reader(s), _, diff --git a/src/rustdoc/parse.rs b/src/rustdoc/parse.rs index 11eb469e641..9be1c996451 100644 --- a/src/rustdoc/parse.rs +++ b/src/rustdoc/parse.rs @@ -9,10 +9,11 @@ export from_file, from_str; fn new_parse_sess() -> parser::parse_sess { let cm = codemap::new_codemap(); + let handler = diagnostic::mk_handler(none); let sess = @{ cm: cm, mutable next_id: 1, - diagnostic: diagnostic::mk_handler(cm, none), + span_diagnostic: diagnostic::mk_span_handler(handler, cm), mutable chpos: 0u, mutable byte_pos: 0u };