Skip to content

Commit

Permalink
resolve: Relax shadowing restriction on macro-expanded macros
Browse files Browse the repository at this point in the history
... for both legacy and modern macros.
Fix previously introduced regressions, add tests.
  • Loading branch information
petrochenkov committed Sep 8, 2018
1 parent 2723569 commit c057d57
Show file tree
Hide file tree
Showing 6 changed files with 57 additions and 32 deletions.
15 changes: 12 additions & 3 deletions src/librustc_resolve/lib.rs
Expand Up @@ -1274,9 +1274,18 @@ impl<'a> NameBinding<'a> {
// expansion round `max(invoc_id, binding)` when they both emerged from macros.
// Then this function returns `true` if `self` may emerge from a macro *after* that
// in some later round and screw up our previously found resolution.
fn may_appear_after(&self, _invoc_id: Mark, _binding: &NameBinding) -> bool {
// FIXME: This is a very conservative estimation.
self.expansion != Mark::root()
fn may_appear_after(&self, invoc_id: Mark, binding: &NameBinding) -> bool {
// self > max(invoc_id, binding) => !(self <= invoc_id || self <= binding)
// Expansions are partially ordered, so "may appear after" is an inversion of
// "certainly appears before or simultaneously" and includes unordered cases.
let self_parent_expansion = self.expansion;
let other_parent_expansion = binding.expansion;
let invoc_parent_expansion = invoc_id.parent();
let certainly_before_other_or_simultaneously =
other_parent_expansion.is_descendant_of(self_parent_expansion);
let certainly_before_invoc_or_simultaneously =
invoc_parent_expansion.is_descendant_of(self_parent_expansion);
!(certainly_before_other_or_simultaneously || certainly_before_invoc_or_simultaneously)
}
}

Expand Down
6 changes: 3 additions & 3 deletions src/libunwind/libunwind.rs
Expand Up @@ -10,7 +10,7 @@

#![allow(nonstandard_style)]

macro_rules! cfg_if2 {
macro_rules! cfg_if {
( $( if #[cfg( $meta:meta )] { $($it1:item)* } else { $($it2:item)* } )* ) =>
( $( $( #[cfg($meta)] $it1)* $( #[cfg(not($meta))] $it2)* )* )
}
Expand Down Expand Up @@ -92,7 +92,7 @@ extern "C" {
pub fn _Unwind_GetDataRelBase(ctx: *mut _Unwind_Context) -> _Unwind_Ptr;
}

cfg_if2! {
cfg_if! {
if #[cfg(all(any(target_os = "ios", target_os = "netbsd", not(target_arch = "arm"))))] {
// Not ARM EHABI
#[repr(C)]
Expand Down Expand Up @@ -238,4 +238,4 @@ if #[cfg(not(all(target_os = "ios", target_arch = "arm")))] {
_Unwind_SjLj_RaiseException(exc)
}
}
} // cfg_if2!
} // cfg_if!
5 changes: 5 additions & 0 deletions src/test/ui/macros/auxiliary/macro-in-other-crate.rs
Expand Up @@ -17,3 +17,8 @@ macro_rules! mac {
macro_rules! inline {
() => ()
}

#[macro_export]
macro_rules! from_prelude {
() => ()
}
35 changes: 35 additions & 0 deletions src/test/ui/macros/macro-shadowing-relaxed.rs
@@ -0,0 +1,35 @@
// Copyright 2016 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
// http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
// <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
// option. This file may not be copied, modified, or distributed
// except according to those terms.

// compile-pass
// aux-build:macro-in-other-crate.rs

#![feature(decl_macro)]

macro_rules! my_include {() => {
// Outer
macro m() {}
#[macro_use(from_prelude)] extern crate macro_in_other_crate;

fn inner() {
// Inner
macro m() {}
macro_rules! from_prelude { () => {} }

// OK, both `m` and `from_prelude` are macro-expanded,
// but no more macro-expanded than their counterpart from outer scope.
m!();
from_prelude!();
}
}}

my_include!();

fn main() {}
2 changes: 1 addition & 1 deletion src/test/ui/macros/macro-shadowing.rs
Expand Up @@ -28,7 +28,7 @@ foo!(); //~ ERROR `foo` is ambiguous

macro_rules! m2 { () => {
macro_rules! foo { () => {} }
foo!(); //~ ERROR `foo` is ambiguous
foo!();
}}
m2!();
//^ Since `foo` is not used outside this expansion, it is not a shadowing error.
Expand Down
26 changes: 1 addition & 25 deletions src/test/ui/macros/macro-shadowing.stderr
Expand Up @@ -30,30 +30,6 @@ LL | macro_rules! foo { () => {} }
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
= note: macro-expanded macros do not shadow

error[E0659]: `foo` is ambiguous
--> $DIR/macro-shadowing.rs:31:5
|
LL | foo!(); //~ ERROR `foo` is ambiguous
| ^^^
|
note: `foo` could refer to the name defined here
--> $DIR/macro-shadowing.rs:30:5
|
LL | macro_rules! foo { () => {} }
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
...
LL | m2!();
| ------ in this macro invocation
note: `foo` could also refer to the name defined here
--> $DIR/macro-shadowing.rs:20:5
|
LL | macro_rules! foo { () => {} }
| ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
...
LL | m1!();
| ------ in this macro invocation
= note: macro-expanded macros do not shadow

error: aborting due to 3 previous errors
error: aborting due to 2 previous errors

For more information about this error, try `rustc --explain E0659`.

0 comments on commit c057d57

Please sign in to comment.