1
Fork 0

Implement the notion of a "generated unsafe block"

This way syntax extensions can generate unsafe blocks without worrying about
them generating unnecessary unsafe warnings. Perhaps a special keyword could be
added to be used in macros, but I don't think that's the best solution.
This commit is contained in:
Alex Crichton 2013-08-28 23:47:26 -07:00
parent ba9fa89bfb
commit 19a6fabad8
6 changed files with 11 additions and 7 deletions

View file

@ -102,8 +102,10 @@ impl Visitor<()> for EffectCheckVisitor {
fn visit_block(&mut self, block:&Block, _:()) { fn visit_block(&mut self, block:&Block, _:()) {
let old_unsafe_context = self.context.unsafe_context; let old_unsafe_context = self.context.unsafe_context;
if block.rules == ast::UnsafeBlock && let is_unsafe = match block.rules {
self.context.unsafe_context == SafeContext { ast::UnsafeBlock(*) => true, ast::DefaultBlock => false
};
if is_unsafe && self.context.unsafe_context == SafeContext {
self.context.unsafe_context = UnsafeBlock(block.id) self.context.unsafe_context = UnsafeBlock(block.id)
} }

View file

@ -1131,7 +1131,9 @@ impl Visitor<@mut Context> for UnusedUnsafeLintVisitor {
fn visit_expr(&mut self, e:@ast::Expr, cx:@mut Context) { fn visit_expr(&mut self, e:@ast::Expr, cx:@mut Context) {
match e.node { match e.node {
ast::ExprBlock(ref blk) if blk.rules == ast::UnsafeBlock => { // Don't warn about generated blocks, that'll just pollute the
// output.
ast::ExprBlock(ref blk) if blk.rules == ast::UnsafeBlock(false) => {
if !cx.tcx.used_unsafe.contains(&blk.id) { if !cx.tcx.used_unsafe.contains(&blk.id) {
cx.span_lint(unused_unsafe, blk.span, cx.span_lint(unused_unsafe, blk.span,
"unnecessary `unsafe` block"); "unnecessary `unsafe` block");

View file

@ -200,7 +200,7 @@ impl PurityState {
purity => { purity => {
let (purity, def) = match blk.rules { let (purity, def) = match blk.rules {
ast::UnsafeBlock => (ast::unsafe_fn, blk.id), ast::UnsafeBlock(*) => (ast::unsafe_fn, blk.id),
ast::DefaultBlock => (purity, self.def), ast::DefaultBlock => (purity, self.def),
}; };
PurityState{ def: def, PurityState{ def: def,

View file

@ -479,7 +479,7 @@ pub struct Field {
#[deriving(Clone, Eq, Encodable, Decodable, IterBytes)] #[deriving(Clone, Eq, Encodable, Decodable, IterBytes)]
pub enum BlockCheckMode { pub enum BlockCheckMode {
DefaultBlock, DefaultBlock,
UnsafeBlock, UnsafeBlock(/* generated internally */ bool),
} }
#[deriving(Clone, Eq, Encodable, Decodable,IterBytes)] #[deriving(Clone, Eq, Encodable, Decodable,IterBytes)]

View file

@ -1792,7 +1792,7 @@ impl Parser {
} else if self.eat_keyword(keywords::Match) { } else if self.eat_keyword(keywords::Match) {
return self.parse_match_expr(); return self.parse_match_expr();
} else if self.eat_keyword(keywords::Unsafe) { } else if self.eat_keyword(keywords::Unsafe) {
return self.parse_block_expr(lo, UnsafeBlock); return self.parse_block_expr(lo, UnsafeBlock(false));
} else if *self.token == token::LBRACKET { } else if *self.token == token::LBRACKET {
self.bump(); self.bump();
let mutbl = self.parse_mutability(); let mutbl = self.parse_mutability();

View file

@ -951,7 +951,7 @@ pub fn print_possibly_embedded_block_(s: @ps,
attrs: &[ast::Attribute], attrs: &[ast::Attribute],
close_box: bool) { close_box: bool) {
match blk.rules { match blk.rules {
ast::UnsafeBlock => word_space(s, "unsafe"), ast::UnsafeBlock(*) => word_space(s, "unsafe"),
ast::DefaultBlock => () ast::DefaultBlock => ()
} }
maybe_print_comment(s, blk.span.lo); maybe_print_comment(s, blk.span.lo);