Skip to content

Commit 96670e9

Browse files
committed
auto merge of #14320 : kballard/rust/fix_stdlib_inject_attrs, r=alexcrichton
The #[phase(syntax,link)] attribute on `extern crate std` needs to be an outer attribute so it can pretty-print properly. Also add `#![no_std]` and `#[feature(phase)]` so compiling the pretty-printed source will work.
2 parents 803e92d + 23ca66e commit 96670e9

File tree

5 files changed

+48
-28
lines changed

5 files changed

+48
-28
lines changed

src/librustc/front/std_inject.rs

Lines changed: 29 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,8 @@ use syntax::parse::token::InternedString;
2222
use syntax::parse::token;
2323
use syntax::util::small_vector::SmallVector;
2424

25+
use std::mem;
26+
2527
pub static VERSION: &'static str = "0.11.0-pre";
2628

2729
pub fn maybe_inject_crates_ref(sess: &Session, krate: ast::Crate)
@@ -70,13 +72,13 @@ pub fn with_version(krate: &str) -> Option<(InternedString, ast::StrStyle)> {
7072
}
7173

7274
impl<'a> fold::Folder for StandardLibraryInjector<'a> {
73-
fn fold_crate(&mut self, krate: ast::Crate) -> ast::Crate {
75+
fn fold_crate(&mut self, mut krate: ast::Crate) -> ast::Crate {
7476
let mut vis = vec!(ast::ViewItem {
7577
node: ast::ViewItemExternCrate(token::str_to_ident("std"),
7678
with_version("std"),
7779
ast::DUMMY_NODE_ID),
7880
attrs: vec!(
79-
attr::mk_attr(attr::mk_list_item(
81+
attr::mk_attr_outer(attr::mk_list_item(
8082
InternedString::new("phase"),
8183
vec!(
8284
attr::mk_word_item(InternedString::new("syntax")),
@@ -101,16 +103,20 @@ impl<'a> fold::Folder for StandardLibraryInjector<'a> {
101103
}
102104

103105
// `extern crate` must be precede `use` items
104-
vis.push_all_move(krate.module.view_items.clone());
105-
let new_module = ast::Mod {
106-
view_items: vis,
107-
..krate.module.clone()
108-
};
106+
mem::swap(&mut vis, &mut krate.module.view_items);
107+
krate.module.view_items.push_all_move(vis);
109108

110-
ast::Crate {
111-
module: new_module,
112-
..krate
113-
}
109+
// don't add #![no_std] here, that will block the prelude injection later.
110+
// Add it during the prelude injection instead.
111+
112+
// Add #![feature(phase)] here, because we use #[phase] on extern crate std.
113+
let feat_phase_attr = attr::mk_attr_inner(attr::mk_list_item(
114+
InternedString::new("feature"),
115+
vec![attr::mk_word_item(InternedString::new("phase"))],
116+
));
117+
krate.attrs.push(feat_phase_attr);
118+
119+
krate
114120
}
115121
}
116122

@@ -127,29 +133,29 @@ struct PreludeInjector<'a> {
127133

128134

129135
impl<'a> fold::Folder for PreludeInjector<'a> {
130-
fn fold_crate(&mut self, krate: ast::Crate) -> ast::Crate {
136+
fn fold_crate(&mut self, mut krate: ast::Crate) -> ast::Crate {
137+
// Add #![no_std] here, so we don't re-inject when compiling pretty-printed source.
138+
// This must happen here and not in StandardLibraryInjector because this
139+
// fold happens second.
140+
141+
let no_std_attr = attr::mk_attr_inner(attr::mk_word_item(InternedString::new("no_std")));
142+
krate.attrs.push(no_std_attr);
143+
131144
if !no_prelude(krate.attrs.as_slice()) {
132145
// only add `use std::prelude::*;` if there wasn't a
133146
// `#![no_implicit_prelude]` at the crate level.
134147

135-
let mut attrs = krate.attrs.clone();
136-
137148
// fold_mod() will insert glob path.
138-
let globs_attr = attr::mk_attr(attr::mk_list_item(
149+
let globs_attr = attr::mk_attr_inner(attr::mk_list_item(
139150
InternedString::new("feature"),
140151
vec!(
141152
attr::mk_word_item(InternedString::new("globs")),
142153
)));
143-
attrs.push(globs_attr);
154+
krate.attrs.push(globs_attr);
144155

145-
ast::Crate {
146-
module: self.fold_mod(&krate.module),
147-
attrs: attrs,
148-
..krate
149-
}
150-
} else {
151-
krate
156+
krate.module = self.fold_mod(&krate.module);
152157
}
158+
krate
153159
}
154160

155161
fn fold_item(&mut self, item: @ast::Item) -> SmallVector<@ast::Item> {

src/librustc/front/test.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -341,7 +341,7 @@ fn mk_test_module(cx: &TestCtxt) -> @ast::Item {
341341
// This attribute tells resolve to let us call unexported functions
342342
let resolve_unexported_str = InternedString::new("!resolve_unexported");
343343
let resolve_unexported_attr =
344-
attr::mk_attr(attr::mk_word_item(resolve_unexported_str));
344+
attr::mk_attr_inner(attr::mk_word_item(resolve_unexported_str));
345345

346346
let item = ast::Item {
347347
ident: token::str_to_ident("__test"),

src/librustc/metadata/encoder.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1436,7 +1436,7 @@ fn synthesize_crate_attrs(ecx: &EncodeContext,
14361436
fn synthesize_crateid_attr(ecx: &EncodeContext) -> Attribute {
14371437
assert!(!ecx.link_meta.crateid.name.is_empty());
14381438

1439-
attr::mk_attr(
1439+
attr::mk_attr_inner(
14401440
attr::mk_name_value_item_str(
14411441
InternedString::new("crate_id"),
14421442
token::intern_and_get_ident(ecx.link_meta.crateid.to_str())))

src/librustc/middle/trans/base.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -232,7 +232,7 @@ fn get_extern_rust_fn(ccx: &CrateContext, inputs: &[ty::t], output: ty::t,
232232

233233
let f = decl_rust_fn(ccx, false, inputs, output, name);
234234
csearch::get_item_attrs(&ccx.sess().cstore, did, |meta_items| {
235-
set_llvm_fn_attrs(meta_items.iter().map(|&x| attr::mk_attr(x))
235+
set_llvm_fn_attrs(meta_items.iter().map(|&x| attr::mk_attr_outer(x))
236236
.collect::<Vec<_>>().as_slice(), f)
237237
});
238238

src/libsyntax/attr.rs

Lines changed: 16 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -126,7 +126,11 @@ impl AttributeMethods for Attribute {
126126
InternedString::new("doc"),
127127
token::intern_and_get_ident(strip_doc_comment_decoration(
128128
comment.get()).as_slice()));
129-
mk_attr(meta)
129+
if self.node.style == ast::AttrOuter {
130+
mk_attr_outer(meta)
131+
} else {
132+
mk_attr_inner(meta)
133+
}
130134
} else {
131135
*self
132136
}
@@ -154,14 +158,24 @@ pub fn mk_word_item(name: InternedString) -> @MetaItem {
154158
@dummy_spanned(MetaWord(name))
155159
}
156160

157-
pub fn mk_attr(item: @MetaItem) -> Attribute {
161+
/// Returns an inner attribute with the given value.
162+
pub fn mk_attr_inner(item: @MetaItem) -> Attribute {
158163
dummy_spanned(Attribute_ {
159164
style: ast::AttrInner,
160165
value: item,
161166
is_sugared_doc: false,
162167
})
163168
}
164169

170+
/// Returns an outer attribute with the given value.
171+
pub fn mk_attr_outer(item: @MetaItem) -> Attribute {
172+
dummy_spanned(Attribute_ {
173+
style: ast::AttrOuter,
174+
value: item,
175+
is_sugared_doc: false,
176+
})
177+
}
178+
165179
pub fn mk_sugared_doc_attr(text: InternedString, lo: BytePos, hi: BytePos)
166180
-> Attribute {
167181
let style = doc_comment_style(text.get());

0 commit comments

Comments
 (0)