While double-checking my understanding of the meaning of `'static`, I made the following test program:
```rust
fn foo<X:'static>(_x: X) { }
#[cfg(not(acceptable))]
fn bar() {
let a = 3;
let b = &a;
foo(b);
}
#[cfg(acceptable)]
fn bar() {
static c : int = 4;;
let d : &'static int = &c;
foo(d);
}
fn main() {
bar();
}
```
Transcript of compiling above program, illustrating that the `--cfg acceptable` variant of `bar` compiles successfully, showing that the`'static` kind bound only disallows non-`static` references, not *all* references:
```
% rustc --version
/Users/fklock/opt/rust-dbg/bin/rustc 0.10-pre (
caf17fe 2014-03-21 02:21:50 -0700)
host: x86_64-apple-darwin
% rustc /tmp/s.rs
/tmp/s.rs:7:5: 7:8 error: instantiating a type parameter with an incompatible type `&int`, which does not fulfill `'static`
/tmp/s.rs:7 foo(b);
^~~
error: aborting due to previous error
% rustc --cfg acceptable /tmp/s.rs
% ./s
%
```
(Note that the explicit type annotation on `let d : &'static int` is necessary; it did not suffice for me to just write `let d = &'static c;`. That might be a latent bug, I am not sure yet.)
Anyway, a fix to the documentation seemed prudent.
pub fn raw_dummy_expr(sp: codemap::Span) -> @ast::Expr {
@ast::Expr {
id: ast::DUMMY_NODE_ID,
- node: ast::ExprTup(Vec::new()),
- span: sp
+ node: ast::ExprLit(@codemap::respan(sp, ast::LitNil)),
+ span: sp,
}
}
pub fn dummy_expr(sp: codemap::Span) -> MacResult {
MRExpr(MacResult::raw_dummy_expr(sp))
}
+ pub fn dummy_any(sp: codemap::Span) -> MacResult {
+ MRAny(~DummyMacResult { sp: sp })
+ }
+}
+struct DummyMacResult {
+ sp: codemap::Span
+}
+impl AnyMacro for DummyMacResult {
+ fn make_expr(&self) -> @ast::Expr {
+ MacResult::raw_dummy_expr(self.sp)
+ }
+ fn make_items(&self) -> SmallVector<@ast::Item> {
+ SmallVector::zero()
+ }
+ fn make_stmt(&self) -> @ast::Stmt {
+ @codemap::respan(self.sp,
+ ast::StmtExpr(MacResult::raw_dummy_expr(self.sp), ast::DUMMY_NODE_ID))
+ }
}
/// An enum representing the different kinds of syntax extensions.
use ast;
use codemap;
-use ext::base::*;
use ext::base;
use print;
-pub fn expand_syntax_ext(cx: &mut ExtCtxt,
+pub fn expand_syntax_ext(cx: &mut base::ExtCtxt,
sp: codemap::Span,
tt: &[ast::TokenTree])
-> base::MacResult {
println!("{}", print::pprust::tt_to_str(&ast::TTDelim(
@tt.iter().map(|x| (*x).clone()).collect())));
- //trivial expression
- MRExpr(@ast::Expr {
- id: ast::DUMMY_NODE_ID,
- node: ast::ExprLit(@codemap::Spanned {
- node: ast::LitNil,
- span: sp
- }),
- span: sp,
- })
+ // any so that `log_syntax` can be invoked as an expression and item.
+ base::MacResult::dummy_any(sp)
}
use codemap::Span;
use ext::base::ExtCtxt;
use ext::base;
-use parse::lexer::{new_tt_reader, Reader};
-use parse::parser::Parser;
-use parse::token::keywords;
+use parse::token::{keywords, is_keyword};
pub fn expand_trace_macros(cx: &mut ExtCtxt,
sp: Span,
tt: &[ast::TokenTree])
-> base::MacResult {
- let sess = cx.parse_sess();
- let cfg = cx.cfg();
- let tt_rdr = new_tt_reader(&cx.parse_sess().span_diagnostic,
- None,
- tt.iter().map(|x| (*x).clone()).collect());
- let mut rust_parser = Parser(sess, cfg.clone(), tt_rdr.dup());
-
- if rust_parser.is_keyword(keywords::True) {
- cx.set_trace_macros(true);
- } else if rust_parser.is_keyword(keywords::False) {
- cx.set_trace_macros(false);
- } else {
- cx.span_err(sp, "trace_macros! only accepts `true` or `false`");
- return base::MacResult::dummy_expr(sp);
+ match tt {
+ [ast::TTTok(_, ref tok)] if is_keyword(keywords::True, tok) => {
+ cx.set_trace_macros(true);
+ }
+ [ast::TTTok(_, ref tok)] if is_keyword(keywords::False, tok) => {
+ cx.set_trace_macros(false);
+ }
+ _ => cx.span_err(sp, "trace_macros! accepts only `true` or `false`"),
}
- rust_parser.bump();
-
- let mut rust_parser = Parser(sess, cfg, tt_rdr.dup());
- let result = rust_parser.parse_expr();
- base::MRExpr(result)
+ base::MacResult::dummy_any(sp)
}
html_root_url = "http://static.rust-lang.org/doc/master")];
#[feature(macro_rules)];
+#[deny(missing_doc)];
extern crate collections;
// FIXME (#2807): Windows support.
+/// Terminal color definitions
pub mod color {
+ /// Number for a terminal color
pub type Color = u16;
pub static BLACK: Color = 0u16;
pub static BRIGHT_WHITE: Color = 15u16;
}
+/// Terminal attributes
pub mod attr {
/// Terminal attributes for use with term.attr().
+ ///
/// Most attributes can only be turned on and must be turned off with term.reset().
/// The ones that can be turned off explicitly take a boolean value.
/// Color is also represented as an attribute for convenience.
}
}
+/// A Terminal that knows how many colors it supports, with a reference to its
+/// parsed TermInfo database record.
pub struct Terminal<T> {
priv num_colors: u16,
priv out: T,
}
impl<T: Writer> Terminal<T> {
+ /// Returns a wrapped output stream (`Terminal<T>`) as a `Result`.
+ ///
+ /// Returns `Err()` if the TERM environment variable is undefined.
+ /// TERM should be set to something like `xterm-color` or `screen-256color`.
+ ///
+ /// Returns `Err()` on failure to open the terminfo database correctly.
+ /// Also, in the event that the individual terminfo database entry can not
+ /// be parsed.
pub fn new(out: T) -> Result<Terminal<T>, ~str> {
let term = match os::getenv("TERM") {
Some(t) => t,
/// If the color is a bright color, but the terminal only supports 8 colors,
/// the corresponding normal color will be used instead.
///
- /// Returns Ok(true) if the color was set, Ok(false) otherwise, and Err(e)
- /// if there was an I/O error
+ /// Returns `Ok(true)` if the color was set, `Ok(false)` otherwise, and `Err(e)`
+ /// if there was an I/O error.
pub fn fg(&mut self, color: color::Color) -> io::IoResult<bool> {
let color = self.dim_if_necessary(color);
if self.num_colors > color {
/// If the color is a bright color, but the terminal only supports 8 colors,
/// the corresponding normal color will be used instead.
///
- /// Returns Ok(true) if the color was set, Ok(false) otherwise, and Err(e)
- /// if there was an I/O error
+ /// Returns `Ok(true)` if the color was set, `Ok(false)` otherwise, and `Err(e)`
+ /// if there was an I/O error.
pub fn bg(&mut self, color: color::Color) -> io::IoResult<bool> {
let color = self.dim_if_necessary(color);
if self.num_colors > color {
}
/// Sets the given terminal attribute, if supported.
- /// Returns Ok(true) if the attribute was supported, Ok(false) otherwise,
- /// and Err(e) if there was an I/O error.
+ /// Returns `Ok(true)` if the attribute was supported, `Ok(false)` otherwise,
+ /// and `Err(e)` if there was an I/O error.
pub fn attr(&mut self, attr: attr::Attr) -> io::IoResult<bool> {
match attr {
attr::ForegroundColor(c) => self.fg(c),
}
/// Resets all terminal attributes and color to the default.
+ /// Returns `Ok()`.
pub fn reset(&mut self) -> io::IoResult<()> {
let mut cap = self.ti.strings.find_equiv(&("sgr0"));
if cap.is_none() {
} else { color }
}
+ /// Returns the contained stream
pub fn unwrap(self) -> T { self.out }
+ /// Gets an immutable reference to the stream inside
pub fn get_ref<'a>(&'a self) -> &'a T { &self.out }
+ /// Gets a mutable reference to the stream inside
pub fn get_mut<'a>(&'a mut self) -> &'a mut T { &mut self.out }
}
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-#[allow(missing_doc)];
+//! Terminfo database interface.
use collections::HashMap;
-/// A parsed terminfo entry.
+/// A parsed terminfo database entry.
pub struct TermInfo {
/// Names for the terminal
priv names: Vec<~str> ,
}
pub mod searcher;
+
+/// TermInfo format parsing.
pub mod parser {
+ //! ncurses-compatible compiled terminfo format parsing (term(5))
pub mod compiled;
}
pub mod parm;
}
/// Types of parameters a capability can use
-#[deriving(Clone)]
#[allow(missing_doc)]
+#[deriving(Clone)]
pub enum Param {
String(~str),
Number(int)
#[allow(non_uppercase_statics)];
-/// ncurses-compatible compiled terminfo format parsing (term(5))
+//! ncurses-compatible compiled terminfo format parsing (term(5))
use collections::HashMap;
use std::io;
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-/// Implement ncurses-compatible database discovery
-/// Does not support hashed database, only filesystem!
+//! ncurses-compatible database discovery
+//!
+//! Does not support hashed database, only filesystem!
use std::io::File;
use std::os::getenv;
concat!(test!());
//~^ ERROR: macro undefined: 'test'
- //~^^ ERROR: expected a literal
}
--- /dev/null
+// Copyright 2014 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.
+
+// ignore-fast feature doesn't work
+#[feature(macro_rules, trace_macros)];
+
+fn main() {
+ trace_macros!(); //~ ERROR trace_macros! accepts only `true` or `false`
+ trace_macros!(1); //~ ERROR trace_macros! accepts only `true` or `false`
+ trace_macros!(ident); //~ ERROR trace_macros! accepts only `true` or `false`
+ trace_macros!(for); //~ ERROR trace_macros! accepts only `true` or `false`
+ trace_macros!(true,); //~ ERROR trace_macros! accepts only `true` or `false`
+ trace_macros!(false 1); //~ ERROR trace_macros! accepts only `true` or `false`
+
+
+ // should be fine:
+ macro_rules! expando {
+ ($x: ident) => { trace_macros!($x) }
+ }
+
+ expando!(true);
+}
--- /dev/null
+// Copyright 2014 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.
+
+// ignore-fast feature doesn't work
+#[feature(trace_macros, log_syntax)];
+
+// make sure these macros can be used as in the various places that
+// macros can occur.
+
+// items
+trace_macros!(false)
+log_syntax!()
+
+fn main() {
+
+ // statements
+ trace_macros!(false);
+ log_syntax!();
+
+ // expressions
+ (trace_macros!(false),
+ log_syntax!());
+}