/mingw-build/
src/.DS_Store
/tmp/
+/dist/
/stage0/
/dl/
/stage1/
need_ok() {
if [ $? -ne 0 ]
then
- err $1
+ err "$1"
fi
}
CFG_SRC_DIR="$(cd $(dirname $0) && pwd)/"
CFG_BUILD_DIR="$(pwd)/"
-CFG_SELF=${CFG_SRC_DIR}$(basename $0)
+CFG_SELF="$0"
CFG_CONFIGURE_ARGS="$@"
OPTIONS=""
valopt libdir "${CFG_PREFIX}/${CFG_LIBDIR_RELATIVE}" "install libraries"
valopt rustlibdir "rustlib" "subdirectory name for rustc's libraries"
-# Validate Options
-step_msg "validating $CFG_SELF args"
-validate_opt
-
if [ $HELP -eq 1 ]
then
echo
exit 0
fi
+# Validate Options
+step_msg "validating $CFG_SELF args"
+validate_opt
step_msg "looking for build programs"
for i in \
doc doc/std doc/extra \
- dl tmp
+ dl tmp dist
do
make_dir $i
done
TARGET_CRATES := std extra green rustuv native flate arena glob term semver \
uuid serialize sync getopts collections num test time
-HOST_CRATES := syntax rustc rustdoc fourcc
+HOST_CRATES := syntax rustc rustdoc fourcc hexfloat
CRATES := $(TARGET_CRATES) $(HOST_CRATES)
TOOLS := compiletest rustdoc rustc
DEPS_getopts := std
DEPS_collections := std
DEPS_fourcc := syntax std
+DEPS_hexfloat := syntax std
DEPS_num := std
DEPS_test := std extra collections getopts serialize term
DEPS_time := std serialize
PKG_NAME := rust
PKG_DIR = $(PKG_NAME)-$(CFG_RELEASE)
-PKG_TAR = $(PKG_DIR).tar.gz
+PKG_TAR = dist/$(PKG_DIR).tar.gz
ifdef CFG_ISCC
PKG_ISS = $(wildcard $(S)src/etc/pkg/*.iss)
PKG_ICO = $(S)src/etc/pkg/rust-logo.ico
-PKG_EXE = $(PKG_DIR)-install.exe
+PKG_EXE = dist/$(PKG_DIR)-install.exe
endif
ifeq ($(CFG_OSTYPE), apple-darwin)
-PKG_OSX = $(PKG_DIR).pkg
+PKG_OSX = dist/$(PKG_DIR).pkg
endif
PKG_GITMODULES := $(S)src/libuv $(S)src/llvm $(S)src/gyp $(S)src/compiler-rt
dist-prepare-win: PREPARE_BIN_CMD=$(DEFAULT_PREPARE_BIN_CMD)
dist-prepare-win: PREPARE_LIB_CMD=$(DEFAULT_PREPARE_LIB_CMD)
dist-prepare-win: PREPARE_MAN_CMD=$(DEFAULT_PREPARE_MAN_CMD)
+dist-prepare-win: PREPARE_CLEAN=true
dist-prepare-win: prepare-base
endif
$(PKG_TAR): $(PKG_FILES)
@$(call E, making dist dir)
- $(Q)rm -Rf dist
- $(Q)mkdir -p dist/$(PKG_DIR)
+ $(Q)rm -Rf tmp/dist/$(PKG_DIR)
+ $(Q)mkdir -p tmp/dist/$(PKG_DIR)
$(Q)tar \
-C $(S) \
--exclude-vcs \
--exclude=*/llvm/test/*/*/*.ll \
--exclude=*/llvm/test/*/*/*.td \
--exclude=*/llvm/test/*/*/*.s \
- -c $(UNROOTED_PKG_FILES) | tar -x -C dist/$(PKG_DIR)
- $(Q)tar -czf $(PKG_TAR) -C dist $(PKG_DIR)
- $(Q)rm -Rf dist
+ -c $(UNROOTED_PKG_FILES) | tar -x -C tmp/dist/$(PKG_DIR)
+ $(Q)tar -czf $(PKG_TAR) -C tmp/dist $(PKG_DIR)
+ $(Q)rm -Rf tmp/dist/$(PKG_DIR)
.PHONY: dist distcheck
@echo -----------------------------------------------
endif
+
+dist-install-dir: $(foreach host,$(CFG_HOST),dist-install-dir-$(host))
+
+dist-tar-bins: $(foreach host,$(CFG_HOST),dist/$(PKG_DIR)-$(host).tar.gz)
+
+define DEF_INSTALLER
+dist-install-dir-$(1): PREPARE_HOST=$(1)
+dist-install-dir-$(1): PREPARE_TARGETS=$(1)
+dist-install-dir-$(1): PREPARE_STAGE=2
+dist-install-dir-$(1): PREPARE_DEST_DIR=tmp/dist/$$(PKG_DIR)-$(1)
+dist-install-dir-$(1): PREPARE_DIR_CMD=$(DEFAULT_PREPARE_DIR_CMD)
+dist-install-dir-$(1): PREPARE_BIN_CMD=$(DEFAULT_PREPARE_BIN_CMD)
+dist-install-dir-$(1): PREPARE_LIB_CMD=$(DEFAULT_PREPARE_LIB_CMD)
+dist-install-dir-$(1): PREPARE_MAN_CMD=$(DEFAULT_PREPARE_MAN_CMD)
+dist-install-dir-$(1): PREPARE_CLEAN=true
+dist-install-dir-$(1): prepare-base
+ $$(Q)(cd $$(PREPARE_DEST_DIR)/ && find -type f) \
+ > $$(PREPARE_DEST_DIR)/$$(CFG_LIBDIR_RELATIVE)/$$(CFG_RUSTLIBDIR)/manifest
+ $$(Q)$$(PREPARE_MAN_CMD) $$(S)COPYRIGHT $$(PREPARE_DEST_DIR)
+ $$(Q)$$(PREPARE_MAN_CMD) $$(S)LICENSE-APACHE $$(PREPARE_DEST_DIR)
+ $$(Q)$$(PREPARE_MAN_CMD) $$(S)LICENSE-MIT $$(PREPARE_DEST_DIR)
+ $$(Q)$$(PREPARE_MAN_CMD) $$(S)README.md $$(PREPARE_DEST_DIR)
+ $$(Q)$$(PREPARE_BIN_CMD) $$(S)src/etc/install.sh $$(PREPARE_DEST_DIR)
+
+dist/$$(PKG_DIR)-$(1).tar.gz: dist-install-dir-$(1)
+ @$(call E, build: $$@)
+ $$(Q)tar -czf dist/$$(PKG_DIR)-$(1).tar.gz -C tmp/dist $$(PKG_DIR)-$(1)
+
+endef
+
+$(foreach host,$(CFG_HOST),\
+ $(eval $(call DEF_INSTALLER,$(host))))
prepare-base: PREPARE_SOURCE_MAN_DIR=$(S)/man
prepare-base: PREPARE_DEST_BIN_DIR=$(PREPARE_DEST_DIR)/bin
prepare-base: PREPARE_DEST_LIB_DIR=$(PREPARE_DEST_DIR)/$(CFG_LIBDIR_RELATIVE)
-prepare-base: PREPARE_DEST_MAN_DIR=$(PREPARE_DEST_DIR)/man1
+prepare-base: PREPARE_DEST_MAN_DIR=$(PREPARE_DEST_DIR)/man/man1
prepare-base: prepare-host prepare-targets
prepare-everything: prepare-host prepare-targets
DEFAULT_PREPARE_DIR_CMD = umask 022 && mkdir -p
DEFAULT_PREPARE_BIN_CMD = install -m755
DEFAULT_PREPARE_LIB_CMD = install -m644
-DEFAULT_PREPARE_MAN_CMD = install -m755
+DEFAULT_PREPARE_MAN_CMD = install -m644
# On windows we install from stage3, but on unix only stage2
# Because of the way these rules are organized, preparing from any
# Create a directory
# $(1) is the directory
define PREPARE_DIR
- @$(Q)$(call E, install: $(1))
+ @$(Q)$(call E, prepare: $(1))
$(Q)$(PREPARE_DIR_CMD) $(1)
endef
# Copy an executable
# $(1) is the filename/libname-glob
define PREPARE_BIN
- @$(call E, install: $(PREPARE_DEST_BIN_DIR)/$(1))
+ @$(call E, prepare: $(PREPARE_DEST_BIN_DIR)/$(1))
$(Q)$(PREPARE_BIN_CMD) $(PREPARE_SOURCE_BIN_DIR)/$(1) $(PREPARE_DEST_BIN_DIR)/$(1)
endef
# problem. I'm sorry, just don't remove the $(nop), alright?
define PREPARE_LIB
$(nop)
- @$(call E, install: $(PREPARE_WORKING_DEST_LIB_DIR)/$(1))
+ @$(call E, prepare: $(PREPARE_WORKING_DEST_LIB_DIR)/$(1))
$(Q)LIB_NAME="$(notdir $(lastword $(wildcard $(PREPARE_WORKING_SOURCE_LIB_DIR)/$(1))))"; \
MATCHES="$(filter-out %$(notdir $(lastword $(wildcard $(PREPARE_WORKING_SOURCE_LIB_DIR)/$(1)))),\
$(wildcard $(PREPARE_WORKING_DEST_LIB_DIR)/$(1)))"; \
# Copy a man page
# $(1) - source dir
define PREPARE_MAN
- @$(call E, install: $(PREPARE_DEST_MAN_DIR)/$(1))
+ @$(call E, prepare: $(PREPARE_DEST_MAN_DIR)/$(1))
$(Q)$(PREPARE_MAN_CMD) $(PREPARE_SOURCE_MAN_DIR)/$(1) $(PREPARE_DEST_MAN_DIR)/$(1)
endef
$(foreach host,$(CFG_HOST),\
prepare-host-tool-$(tool)-$(stage)-$(host))))
-prepare-host-dirs:
+prepare-host-dirs: prepare-maybe-clean
$(call PREPARE_DIR,$(PREPARE_DEST_BIN_DIR))
$(call PREPARE_DIR,$(PREPARE_DEST_LIB_DIR))
$(call PREPARE_DIR,$(PREPARE_DEST_MAN_DIR))
# $(2) is stage
# $(3) is host
define DEF_PREPARE_HOST_TOOL
-prepare-host-tool-$(1)-$(2)-$(3): $$(foreach dep,$$(TOOL_DEPS_$(1)),prepare-host-lib-$$(dep)-$(2)-$(3)) \
+prepare-host-tool-$(1)-$(2)-$(3): prepare-maybe-clean \
+ $$(foreach dep,$$(TOOL_DEPS_$(1)),prepare-host-lib-$$(dep)-$(2)-$(3)) \
$$(HBIN$(2)_H_$(3))/$(1)$$(X_$(3)) \
prepare-host-dirs
$$(if $$(findstring $(2), $$(PREPARE_STAGE)),\
define DEF_PREPARE_HOST_LIB
prepare-host-lib-$(1)-$(2)-$(3): PREPARE_WORKING_SOURCE_LIB_DIR=$$(PREPARE_SOURCE_LIB_DIR)
prepare-host-lib-$(1)-$(2)-$(3): PREPARE_WORKING_DEST_LIB_DIR=$$(PREPARE_DEST_LIB_DIR)
-prepare-host-lib-$(1)-$(2)-$(3): $$(foreach dep,$$(RUST_DEPS_$(1)),prepare-host-lib-$$(dep)-$(2)-$(3))\
+prepare-host-lib-$(1)-$(2)-$(3): prepare-maybe-clean \
+ $$(foreach dep,$$(RUST_DEPS_$(1)),prepare-host-lib-$$(dep)-$(2)-$(3))\
$$(HLIB$(2)_H_$(3))/stamp.$(1) \
prepare-host-dirs
$$(if $$(findstring $(2), $$(PREPARE_STAGE)),\
# Rebind PREPARE_*_LIB_DIR to point to rustlib, then install the libs for the targets
prepare-target-$(2)-host-$(3)-$(1): PREPARE_WORKING_SOURCE_LIB_DIR=$$(PREPARE_SOURCE_LIB_DIR)/$$(CFG_RUSTLIBDIR)/$(2)/lib
prepare-target-$(2)-host-$(3)-$(1): PREPARE_WORKING_DEST_LIB_DIR=$$(PREPARE_DEST_LIB_DIR)/$$(CFG_RUSTLIBDIR)/$(2)/lib
-prepare-target-$(2)-host-$(3)-$(1): \
+prepare-target-$(2)-host-$(3)-$(1): prepare-maybe-clean \
$$(foreach crate,$$(TARGET_CRATES), \
$$(TLIB$(1)_T_$(2)_H_$(3))/stamp.$$(crate)) \
$$(if $$(findstring $(2),$$(CFG_HOST)), \
$(foreach target,$(CFG_TARGET), \
$(foreach stage,$(PREPARE_STAGES),\
$(eval $(call DEF_PREPARE_TARGET_N,$(stage),$(target),$(host))))))
+
+prepare-maybe-clean:
+ $(if $(findstring true,$(PREPARE_CLEAN)),\
+ @$(call E, cleaning destination $@),)
+ $(if $(findstring true,$(PREPARE_CLEAN)),\
+ $(Q)rm -rf $(PREPARE_DEST_DIR),)
--- /dev/null
+#!/bin/sh
+# 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.
+
+msg() {
+ echo "install: $1"
+}
+
+step_msg() {
+ msg
+ msg "$1"
+ msg
+}
+
+warn() {
+ echo "install: WARNING: $1"
+}
+
+err() {
+ echo "install: error: $1"
+ exit 1
+}
+
+need_ok() {
+ if [ $? -ne 0 ]
+ then
+ err "$1"
+ fi
+}
+
+putvar() {
+ local T
+ eval T=\$$1
+ eval TLEN=\${#$1}
+ if [ $TLEN -gt 35 ]
+ then
+ printf "install: %-20s := %.35s ...\n" $1 "$T"
+ else
+ printf "install: %-20s := %s %s\n" $1 "$T" "$2"
+ fi
+ printf "%-20s := %s\n" $1 "$T" >>config.tmp
+}
+
+valopt() {
+ VAL_OPTIONS="$VAL_OPTIONS $1"
+
+ local OP=$1
+ local DEFAULT=$2
+ shift
+ shift
+ local DOC="$*"
+ if [ $HELP -eq 0 ]
+ then
+ local UOP=$(echo $OP | tr '[:lower:]' '[:upper:]' | tr '\-' '\_')
+ local V="CFG_${UOP}"
+ eval $V="$DEFAULT"
+ for arg in $CFG_ARGS
+ do
+ if echo "$arg" | grep -q -- "--$OP="
+ then
+ val=$(echo "$arg" | cut -f2 -d=)
+ eval $V=$val
+ fi
+ done
+ putvar $V
+ else
+ if [ -z "$DEFAULT" ]
+ then
+ DEFAULT="<none>"
+ fi
+ OP="${OP}=[${DEFAULT}]"
+ printf " --%-30s %s\n" "$OP" "$DOC"
+ fi
+}
+
+opt() {
+ BOOL_OPTIONS="$BOOL_OPTIONS $1"
+
+ local OP=$1
+ local DEFAULT=$2
+ shift
+ shift
+ local DOC="$*"
+ local FLAG=""
+
+ if [ $DEFAULT -eq 0 ]
+ then
+ FLAG="enable"
+ else
+ FLAG="disable"
+ DOC="don't $DOC"
+ fi
+
+ if [ $HELP -eq 0 ]
+ then
+ for arg in $CFG_ARGS
+ do
+ if [ "$arg" = "--${FLAG}-${OP}" ]
+ then
+ OP=$(echo $OP | tr 'a-z-' 'A-Z_')
+ FLAG=$(echo $FLAG | tr 'a-z' 'A-Z')
+ local V="CFG_${FLAG}_${OP}"
+ eval $V=1
+ putvar $V
+ fi
+ done
+ else
+ if [ ! -z "$META" ]
+ then
+ OP="$OP=<$META>"
+ fi
+ printf " --%-30s %s\n" "$FLAG-$OP" "$DOC"
+ fi
+}
+
+flag() {
+ BOOL_OPTIONS="$BOOL_OPTIONS $1"
+
+ local OP=$1
+ shift
+ local DOC="$*"
+
+ if [ $HELP -eq 0 ]
+ then
+ for arg in $CFG_ARGS
+ do
+ if [ "$arg" = "--${OP}" ]
+ then
+ OP=$(echo $OP | tr 'a-z-' 'A-Z_')
+ local V="CFG_${OP}"
+ eval $V=1
+ putvar $V
+ fi
+ done
+ else
+ if [ ! -z "$META" ]
+ then
+ OP="$OP=<$META>"
+ fi
+ printf " --%-30s %s\n" "$OP" "$DOC"
+ fi
+}
+
+validate_opt () {
+ for arg in $CFG_ARGS
+ do
+ isArgValid=0
+ for option in $BOOL_OPTIONS
+ do
+ if test --disable-$option = $arg
+ then
+ isArgValid=1
+ fi
+ if test --enable-$option = $arg
+ then
+ isArgValid=1
+ fi
+ if test --$option = $arg
+ then
+ isArgValid=1
+ fi
+ done
+ for option in $VAL_OPTIONS
+ do
+ if echo "$arg" | grep -q -- "--$option="
+ then
+ isArgValid=1
+ fi
+ done
+ if [ "$arg" = "--help" ]
+ then
+ echo
+ echo "No more help available for Configure options,"
+ echo "check the Wiki or join our IRC channel"
+ break
+ else
+ if test $isArgValid -eq 0
+ then
+ err "Option '$arg' is not recognized"
+ fi
+ fi
+ done
+}
+
+CFG_SRC_DIR="$(cd $(dirname $0) && pwd)/"
+CFG_SELF="$0"
+CFG_ARGS="$@"
+
+HELP=0
+if [ "$1" = "--help" ]
+then
+ HELP=1
+ shift
+ echo
+ echo "Usage: $CFG_SELF [options]"
+ echo
+ echo "Options:"
+ echo
+else
+ step_msg "processing $CFG_SELF args"
+fi
+
+OPTIONS=""
+BOOL_OPTIONS=""
+VAL_OPTIONS=""
+
+flag uninstall "only uninstall from the installation prefix"
+valopt prefix "/usr/local" "set installation prefix"
+
+if [ $HELP -eq 1 ]
+then
+ echo
+ exit 0
+fi
+
+step_msg "validating $CFG_SELF args"
+validate_opt
+
+# Sanity check: can we can write to the destination?
+touch "${CFG_PREFIX}/lib/rust-install-probe" 2> /dev/null
+if [ $? -ne 0 ]
+then
+ err "can't write to destination. try again with 'sudo'."
+fi
+rm -r "${CFG_PREFIX}/lib/rust-install-probe"
+need_ok "failed to remove install probe"
+
+# Sanity check: can we run these binaries?
+"${CFG_SRC_DIR}/bin/rustc" --version > /dev/null
+need_ok "can't run these binaries on this platform"
+
+# First, uninstall from the installation prefix
+# FIXME: Hardcoded 'rustlib' ignores CFG_RUSTLIBDIR
+if [ -f "${CFG_PREFIX}/lib/rustlib/manifest" ]
+then
+ while read p; do
+ msg "uninstall ${CFG_PREFIX}/$p"
+ rm "${CFG_PREFIX}/$p"
+ need_ok "failed to remove file"
+ done < "${CFG_PREFIX}/lib/rustlib/manifest"
+
+ # Remove 'rustlib' directory
+ msg "uninstall ${CFG_PREFIX}/lib/rustlib"
+ rm -r "${CFG_PREFIX}/lib/rustlib"
+ need_ok "failed to remove rustlib"
+fi
+
+# If we're only uninstalling then exit
+if [ -n "${CFG_UNINSTALL}" ]
+then
+ exit 0
+fi
+
+# Iterate through the new manifest and install files
+while read p; do
+
+ umask 022 && mkdir -p "${CFG_PREFIX}/$(dirname $p)"
+ need_ok "directory creation failed"
+
+ msg "${CFG_PREFIX}/$p"
+ if echo "$p" | grep "/bin/" > /dev/null
+ then
+ install -m755 "${CFG_SRC_DIR}/$p" "${CFG_PREFIX}/$p"
+ else
+ install -m644 "${CFG_SRC_DIR}/$p" "${CFG_PREFIX}/$p"
+ fi
+ need_ok "file creation failed"
+
+# The manifest lists all files to install
+done < "${CFG_SRC_DIR}/lib/rustlib/manifest"
+
+echo
+echo " Rust is ready to roll."
+echo
+
+
--- /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.
+
+/*!
+Syntax extension to create floating point literals from hexadecimal strings
+
+Once loaded, hexfloat!() is called with a string containing the hexadecimal
+floating-point literal, and an optional type (f32 or f64).
+If the type is omitted, the literal is treated the same as a normal unsuffixed
+literal.
+
+# Examples
+
+To load the extension and use it:
+
+```rust,ignore
+#[phase(syntax)]
+extern crate hexfloat;
+
+fn main() {
+ let val = hexfloat!("0x1.ffffb4", f32);
+}
+ ```
+
+# References
+
+* [ExploringBinary: hexadecimal floating point constants]
+ (http://www.exploringbinary.com/hexadecimal-floating-point-constants/)
+
+*/
+
+#[crate_id = "hexfloat#0.10-pre"];
+#[crate_type = "rlib"];
+#[crate_type = "dylib"];
+#[license = "MIT/ASL2"];
+
+#[feature(macro_registrar, managed_boxes)];
+
+extern crate syntax;
+
+use syntax::ast;
+use syntax::ast::Name;
+use syntax::codemap::{Span, mk_sp};
+use syntax::ext::base;
+use syntax::ext::base::{SyntaxExtension, BasicMacroExpander, NormalTT, ExtCtxt, MRExpr};
+use syntax::ext::build::AstBuilder;
+use syntax::parse;
+use syntax::parse::token;
+
+#[macro_registrar]
+pub fn macro_registrar(register: |Name, SyntaxExtension|) {
+ register(token::intern("hexfloat"),
+ NormalTT(~BasicMacroExpander {
+ expander: expand_syntax_ext,
+ span: None,
+ },
+ None));
+}
+
+//Check if the literal is valid (as LLVM expects),
+//and return a descriptive error if not.
+fn hex_float_lit_err(s: &str) -> Option<(uint, ~str)> {
+ let mut chars = s.chars().peekable();
+ let mut i = 0;
+ if chars.peek() == Some(&'-') { chars.next(); i+= 1 }
+ if chars.next() != Some('0') { return Some((i, ~"Expected '0'")); } i+=1;
+ if chars.next() != Some('x') { return Some((i, ~"Expected 'x'")); } i+=1;
+ let mut d_len = 0;
+ for _ in chars.take_while(|c| c.is_digit_radix(16)) { chars.next(); i+=1; d_len += 1;}
+ if chars.next() != Some('.') { return Some((i, ~"Expected '.'")); } i+=1;
+ let mut f_len = 0;
+ for _ in chars.take_while(|c| c.is_digit_radix(16)) { chars.next(); i+=1; f_len += 1;}
+ if d_len == 0 && f_len == 0 {
+ return Some((i, ~"Expected digits before or after decimal point"));
+ }
+ if chars.next() != Some('p') { return Some((i, ~"Expected 'p'")); } i+=1;
+ if chars.peek() == Some(&'-') { chars.next(); i+= 1 }
+ let mut e_len = 0;
+ for _ in chars.take_while(|c| c.is_digit()) { chars.next(); i+=1; e_len += 1}
+ if e_len == 0 {
+ return Some((i, ~"Expected exponent digits"));
+ }
+ match chars.next() {
+ None => None,
+ Some(_) => Some((i, ~"Expected end of string"))
+ }
+}
+
+pub fn expand_syntax_ext(cx: &mut ExtCtxt, sp: Span, tts: &[ast::TokenTree]) -> base::MacResult {
+ let (expr, ty_lit) = parse_tts(cx, tts);
+
+ let ty = match ty_lit {
+ None => None,
+ Some(Ident{ident, span}) => match token::get_ident(ident).get() {
+ "f32" => Some(ast::TyF32),
+ "f64" => Some(ast::TyF64),
+ _ => {
+ cx.span_err(span, "invalid floating point type in hexfloat!");
+ None
+ }
+ }
+ };
+
+ let s = match expr.node {
+ // expression is a literal
+ ast::ExprLit(lit) => match lit.node {
+ // string literal
+ ast::LitStr(ref s, _) => {
+ s.clone()
+ }
+ _ => {
+ cx.span_err(expr.span, "unsupported literal in hexfloat!");
+ return base::MacResult::dummy_expr(sp);
+ }
+ },
+ _ => {
+ cx.span_err(expr.span, "non-literal in hexfloat!");
+ return base::MacResult::dummy_expr(sp);
+ }
+ };
+
+ {
+ let err = hex_float_lit_err(s.get());
+ match err {
+ Some((err_pos, err_str)) => {
+ let pos = expr.span.lo + syntax::codemap::Pos::from_uint(err_pos + 1);
+ let span = syntax::codemap::mk_sp(pos,pos);
+ cx.span_err(span, format!("invalid hex float literal in hexfloat!: {}", err_str));
+ return base::MacResult::dummy_expr(sp);
+ }
+ _ => ()
+ }
+ }
+
+ let lit = match ty {
+ None => ast::LitFloatUnsuffixed(s),
+ Some (ty) => ast::LitFloat(s, ty)
+ };
+ MRExpr(cx.expr_lit(sp, lit))
+}
+
+struct Ident {
+ ident: ast::Ident,
+ span: Span
+}
+
+fn parse_tts(cx: &ExtCtxt, tts: &[ast::TokenTree]) -> (@ast::Expr, Option<Ident>) {
+ let p = &mut parse::new_parser_from_tts(cx.parse_sess(),
+ cx.cfg(),
+ tts.iter()
+ .map(|x| (*x).clone())
+ .collect());
+ let ex = p.parse_expr();
+ let id = if p.token == token::EOF {
+ None
+ } else {
+ p.expect(&token::COMMA);
+ let lo = p.span.lo;
+ let ident = p.parse_ident();
+ let hi = p.last_span.hi;
+ Some(Ident{ident: ident, span: mk_sp(lo, hi)})
+ };
+ if p.token != token::EOF {
+ p.unexpected();
+ }
+ (ex, id)
+}
+
+// FIXME (10872): This is required to prevent an LLVM assert on Windows
+#[test]
+fn dummy_test() { }
("simd", Active),
("default_type_params", Active),
("quote", Active),
+ ("linkage", Active),
// These are used to test this portion of the compiler, they don't actually
// mean anything
}
}
+ fn visit_foreign_item(&mut self, i: &ast::ForeignItem, _: ()) {
+ match i.node {
+ ast::ForeignItemFn(..) | ast::ForeignItemStatic(..) => {
+ if attr::contains_name(i.attrs.as_slice(), "linkage") {
+ self.gate_feature("linkage", i.span,
+ "the `linkage` attribute is experimental \
+ and not portable across platforms")
+ }
+ }
+ }
+ visit::walk_foreign_item(self, i, ())
+ }
+
fn visit_ty(&mut self, t: &ast::Ty, _: ()) {
match t.node {
ast::TyClosure(closure) if closure.onceness == ast::Once &&
assignee_loan_path,
assignment_id,
assignment_span,
- assignee_id);
+ assignee_id,
+ false);
+}
+
+pub fn gather_move_and_assignment(bccx: &BorrowckCtxt,
+ move_data: &MoveData,
+ assignment_id: ast::NodeId,
+ assignment_span: Span,
+ assignee_loan_path: @LoanPath,
+ assignee_id: ast::NodeId) {
+ move_data.add_assignment(bccx.tcx,
+ assignee_loan_path,
+ assignment_id,
+ assignment_span,
+ assignee_id,
+ true);
}
fn check_is_legal_to_move_from(bccx: &BorrowckCtxt,
visit::walk_expr(this, ex, ());
}
- ast::ExprAssign(l, _) | ast::ExprAssignOp(_, l, _) => {
- let l_cmt = this.bccx.cat_expr(l);
- match opt_loan_path(l_cmt) {
- Some(l_lp) => {
- gather_moves::gather_assignment(this.bccx, &this.move_data,
- ex.id, ex.span,
- l_lp, l.id);
- }
- None => {
- // This can occur with e.g. `*foo() = 5`. In such
- // cases, there is no need to check for conflicts
- // with moves etc, just ignore.
- }
- }
+ ast::ExprAssign(l, _) => {
+ with_assignee_loan_path(
+ this.bccx, l,
+ |lp| gather_moves::gather_assignment(this.bccx, &this.move_data,
+ ex.id, ex.span, lp, l.id));
+ visit::walk_expr(this, ex, ());
+ }
+
+ ast::ExprAssignOp(_, l, _) => {
+ with_assignee_loan_path(
+ this.bccx, l,
+ |lp| gather_moves::gather_move_and_assignment(this.bccx, &this.move_data,
+ ex.id, ex.span, lp, l.id));
visit::walk_expr(this, ex, ());
}
ast::ExprInlineAsm(ref ia) => {
for &(_, out) in ia.outputs.iter() {
- let out_cmt = this.bccx.cat_expr(out);
- match opt_loan_path(out_cmt) {
- Some(out_lp) => {
- gather_moves::gather_assignment(this.bccx, &this.move_data,
- ex.id, ex.span,
- out_lp, out.id);
- }
- None => {
- // See the comment for ExprAssign.
- }
- }
+ with_assignee_loan_path(
+ this.bccx, out,
+ |lp| gather_moves::gather_assignment(this.bccx, &this.move_data,
+ ex.id, ex.span, lp, out.id));
}
visit::walk_expr(this, ex, ());
}
}
}
+fn with_assignee_loan_path(bccx: &BorrowckCtxt, expr: &ast::Expr, op: |@LoanPath|) {
+ let cmt = bccx.cat_expr(expr);
+ match opt_loan_path(cmt) {
+ Some(lp) => op(lp),
+ None => {
+ // This can occur with e.g. `*foo() = 5`. In such
+ // cases, there is no need to check for conflicts
+ // with moves etc, just ignore.
+ }
+ }
+}
+
impl<'a> GatherLoanCtxt<'a> {
pub fn tcx(&self) -> ty::ctxt { self.bccx.tcx }
move_data::Declared => {
self.tcx.sess.span_err(
use_span,
- format!("{} of possibly uninitialized value: `{}`",
+ format!("{} of possibly uninitialized variable: `{}`",
verb,
self.loan_path_to_str(lp)));
}
pub struct MoveData {
/// Move paths. See section "Move paths" in `doc.rs`.
- paths: RefCell<Vec<MovePath> >,
+ paths: RefCell<Vec<MovePath>>,
/// Cache of loan path to move path index, for easy lookup.
path_map: RefCell<HashMap<@LoanPath, MovePathIndex>>,
/// Each move or uninitialized variable gets an entry here.
- moves: RefCell<Vec<Move> >,
+ moves: RefCell<Vec<Move>>,
/// Assignments to a variable, like `x = foo`. These are assigned
/// bits for dataflow, since we must track them to ensure that
/// immutable variables are assigned at most once along each path.
- var_assignments: RefCell<Vec<Assignment> >,
+ var_assignments: RefCell<Vec<Assignment>>,
/// Assignments to a path, like `x.f = foo`. These are not
/// assigned dataflow bits, but we track them because they still
/// kill move bits.
- path_assignments: RefCell<Vec<Assignment> >,
+ path_assignments: RefCell<Vec<Assignment>>,
+
+ /// Assignments to a variable or path, like `x = foo`, but not `x += foo`.
assignee_ids: RefCell<HashSet<ast::NodeId>>,
}
lp: @LoanPath,
assign_id: ast::NodeId,
span: Span,
- assignee_id: ast::NodeId) {
+ assignee_id: ast::NodeId,
+ is_also_move: bool) {
/*!
* Adds a new record for an assignment to `lp` that occurs at
* location `id` with the given `span`.
let path_index = self.move_path(tcx, lp);
- {
+ if !is_also_move {
let mut assignee_ids = self.assignee_ids.borrow_mut();
assignee_ids.get().insert(assignee_id);
}
// fn-level
"test", "bench", "should_fail", "ignore", "inline", "lang", "main", "start",
- "no_split_stack", "cold", "macro_registrar",
+ "no_split_stack", "cold", "macro_registrar", "linkage",
// internal attribute: bypass privacy inside items
"!resolve_unexported",
fn check_local(this: &mut Liveness, local: &Local) {
match local.init {
- Some(_) => {
- this.warn_about_unused_or_dead_vars_in_pat(local.pat);
- }
- None => {
-
- // No initializer: the variable might be unused; if not, it
- // should not be live at this point.
-
- debug!("check_local() with no initializer");
- this.pat_bindings(local.pat, |ln, var, sp, id| {
- if !this.warn_about_unused(sp, id, ln, var) {
- match this.live_on_exit(ln, var) {
- None => { /* not live: good */ }
- Some(lnk) => {
- this.report_illegal_read(
- local.span, lnk, var,
- PossiblyUninitializedVariable);
- }
- }
- }
- })
- }
+ Some(_) => {
+ this.warn_about_unused_or_dead_vars_in_pat(local.pat);
+ },
+ None => {
+ this.pat_bindings(local.pat, |ln, var, sp, id| {
+ this.warn_about_unused(sp, id, ln, var);
+ })
+ }
}
visit::walk_local(this, local, ());
}
}
- pub fn report_illegal_read(&self,
- chk_span: Span,
- lnk: LiveNodeKind,
- var: Variable,
- rk: ReadKind) {
- let msg = match rk {
- PossiblyUninitializedVariable => "possibly uninitialized \
- variable",
- PossiblyUninitializedField => "possibly uninitialized field",
- MovedValue => "moved value",
- PartiallyMovedValue => "partially moved value"
- };
- let name = self.ir.variable_name(var);
- match lnk {
- FreeVarNode(span) => {
- self.tcx.sess.span_err(
- span,
- format!("capture of {}: `{}`", msg, name));
- }
- ExprNode(span) => {
- self.tcx.sess.span_err(
- span,
- format!("use of {}: `{}`", msg, name));
- }
- ExitNode | VarDefNode(_) => {
- self.tcx.sess.span_bug(
- chk_span,
- format!("illegal reader: {:?}", lnk));
- }
- }
- }
-
pub fn should_warn(&self, var: Variable) -> Option<~str> {
let name = self.ir.variable_name(var);
if name.len() == 0 || name[0] == ('_' as u8) { None } else { Some(name) }
}
ast_map::NodeForeignItem(ni) => {
- let ty = ty::node_id_to_type(ccx.tcx, ni.id);
foreign = true;
match ni.node {
foreign::register_foreign_item_fn(ccx, abis, ni)
}
ast::ForeignItemStatic(..) => {
- // Treat the crate map static specially in order to
- // a weak-linkage-like functionality where it's
- // dynamically resolved at runtime. If we're
- // building a library, then we declare the static
- // with weak linkage, but if we're building a
- // library then we've already declared the crate map
- // so use that instead.
- if attr::contains_name(ni.attrs.as_slice(),
- "crate_map") {
- if ccx.sess.building_library.get() {
- let s = "_rust_crate_map_toplevel";
- let g = unsafe {
- s.with_c_str(|buf| {
- let ty = type_of(ccx, ty);
- llvm::LLVMAddGlobal(ccx.llmod,
- ty.to_ref(),
- buf)
- })
- };
- lib::llvm::SetLinkage(g,
- lib::llvm::ExternalWeakLinkage);
- g
- } else {
- ccx.crate_map
- }
- } else {
- let ident = foreign::link_name(ni);
- unsafe {
- ident.get().with_c_str(|buf| {
- let ty = type_of(ccx, ty);
- llvm::LLVMAddGlobal(ccx.llmod,
- ty.to_ref(), buf)
- })
- }
- }
+ foreign::register_static(ccx, ni)
}
}
}
use back::{link};
use lib::llvm::llvm;
-use lib::llvm::{ValueRef, CallConv, StructRetAttribute};
+use lib::llvm::{ValueRef, CallConv, StructRetAttribute, Linkage};
use lib;
use middle::trans::base::push_ctxt;
use middle::trans::base;
})
}
+pub fn llvm_linkage_by_name(name: &str) -> Option<Linkage> {
+ // Use the names from src/llvm/docs/LangRef.rst here. Most types are only
+ // applicable to variable declarations and may not really make sense for
+ // Rust code in the first place but whitelist them anyway and trust that
+ // the user knows what s/he's doing. Who knows, unanticipated use cases
+ // may pop up in the future.
+ //
+ // ghost, dllimport, dllexport and linkonce_odr_autohide are not supported
+ // and don't have to be, LLVM treats them as no-ops.
+ match name {
+ "appending" => Some(lib::llvm::AppendingLinkage),
+ "available_externally" => Some(lib::llvm::AvailableExternallyLinkage),
+ "common" => Some(lib::llvm::CommonLinkage),
+ "extern_weak" => Some(lib::llvm::ExternalWeakLinkage),
+ "external" => Some(lib::llvm::ExternalLinkage),
+ "internal" => Some(lib::llvm::InternalLinkage),
+ "linker_private" => Some(lib::llvm::LinkerPrivateLinkage),
+ "linker_private_weak" => Some(lib::llvm::LinkerPrivateWeakLinkage),
+ "linkonce" => Some(lib::llvm::LinkOnceAnyLinkage),
+ "linkonce_odr" => Some(lib::llvm::LinkOnceODRLinkage),
+ "private" => Some(lib::llvm::PrivateLinkage),
+ "weak" => Some(lib::llvm::WeakAnyLinkage),
+ "weak_odr" => Some(lib::llvm::WeakODRLinkage),
+ _ => None,
+ }
+}
+
+pub fn register_static(ccx: @CrateContext,
+ foreign_item: @ast::ForeignItem) -> ValueRef {
+ let ty = ty::node_id_to_type(ccx.tcx, foreign_item.id);
+ let llty = type_of::type_of(ccx, ty);
+
+ // Treat the crate map static specially in order to
+ // a weak-linkage-like functionality where it's
+ // dynamically resolved at runtime. If we're
+ // building a library, then we declare the static
+ // with weak linkage, but if we're building a
+ // library then we've already declared the crate map
+ // so use that instead.
+ if attr::contains_name(foreign_item.attrs.as_slice(), "crate_map") {
+ return if ccx.sess.building_library.get() {
+ let s = "_rust_crate_map_toplevel";
+ let g = unsafe {
+ s.with_c_str(|buf| {
+ llvm::LLVMAddGlobal(ccx.llmod, llty.to_ref(), buf)
+ })
+ };
+ lib::llvm::SetLinkage(g, lib::llvm::ExternalWeakLinkage);
+ g
+ } else {
+ ccx.crate_map
+ }
+ }
+
+ let ident = link_name(foreign_item);
+ match attr::first_attr_value_str_by_name(foreign_item.attrs.as_slice(),
+ "linkage") {
+ // If this is a static with a linkage specified, then we need to handle
+ // it a little specially. The typesystem prevents things like &T and
+ // extern "C" fn() from being non-null, so we can't just declare a
+ // static and call it a day. Some linkages (like weak) will make it such
+ // that the static actually has a null value.
+ Some(name) => {
+ let linkage = match llvm_linkage_by_name(name.get()) {
+ Some(linkage) => linkage,
+ None => {
+ ccx.sess.span_fatal(foreign_item.span,
+ "invalid linkage specified");
+ }
+ };
+ let llty2 = match ty::get(ty).sty {
+ ty::ty_ptr(ref mt) => type_of::type_of(ccx, mt.ty),
+ _ => {
+ ccx.sess.span_fatal(foreign_item.span,
+ "must have type `*T` or `*mut T`");
+ }
+ };
+ unsafe {
+ let g1 = ident.get().with_c_str(|buf| {
+ llvm::LLVMAddGlobal(ccx.llmod, llty2.to_ref(), buf)
+ });
+ lib::llvm::SetLinkage(g1, linkage);
+
+ let real_name = "_rust_extern_with_linkage_" + ident.get();
+ let g2 = real_name.with_c_str(|buf| {
+ llvm::LLVMAddGlobal(ccx.llmod, llty.to_ref(), buf)
+ });
+ lib::llvm::SetLinkage(g2, lib::llvm::InternalLinkage);
+ llvm::LLVMSetInitializer(g2, g1);
+ g2
+ }
+ }
+ None => unsafe {
+ ident.get().with_c_str(|buf| {
+ llvm::LLVMAddGlobal(ccx.llmod, llty.to_ref(), buf)
+ })
+ }
+ }
+}
pub fn register_foreign_item_fn(ccx: @CrateContext, abis: AbiSet,
foreign_item: @ast::ForeignItem) -> ValueRef {
self.to_pretty_writer(&mut s as &mut io::Writer).unwrap();
str::from_utf8_owned(s.unwrap()).unwrap()
}
+
+ /// If the Json value is an Object, returns the value associated with the provided key.
+ /// Otherwise, returns None.
+ pub fn find<'a>(&'a self, key: &~str) -> Option<&'a Json>{
+ match self {
+ &Object(ref map) => map.find(key),
+ _ => None
+ }
+ }
+
+ /// Attempts to get a nested Json Object for each key in `keys`.
+ /// If any key is found not to exist, get_path will return None.
+ /// Otherwise, it will return the Json value associated with the final key.
+ pub fn find_path<'a>(&'a self, keys: &[&~str]) -> Option<&'a Json>{
+ keys.iter().fold(Some(self), |target, key| target.map_or(None, |t| t.find(*key)))
+ }
+
+ /// If the Json value is an Object, performs a depth-first search until
+ /// a value associated with the provided key is found. If no value is found
+ /// or the Json value is not an Object, returns None.
+ pub fn search<'a>(&'a self, key: &~str) -> Option<&'a Json> {
+ match self {
+ &Object(ref map) => {
+ match map.find(key) {
+ Some(json_value) => Some(json_value),
+ None => {
+ let mut value : Option<&'a Json> = None;
+ for (_, v) in map.iter() {
+ value = v.search(key);
+ if value.is_some() {
+ break;
+ }
+ }
+ value
+ }
+ }
+ },
+ _ => None
+ }
+ }
+
+ /// Returns true if the Json value is an Object. Returns false otherwise.
+ pub fn is_object<'a>(&'a self) -> bool {
+ match self {
+ &Object(_) => true,
+ _ => false
+ }
+ }
+
+ /// If the Json value is an Object, returns the associated TreeMap.
+ /// Returns None otherwise.
+ pub fn as_object<'a>(&'a self) -> Option<&'a Object> {
+ match self {
+ &Object(ref map) => Some(&**map),
+ _ => None
+ }
+ }
+
+ /// Returns true if the Json value is a List. Returns false otherwise.
+ pub fn is_list<'a>(&'a self) -> bool {
+ match self {
+ &List(_) => true,
+ _ => false
+ }
+ }
+
+ /// If the Json value is a List, returns the associated vector.
+ /// Returns None otherwise.
+ pub fn as_list<'a>(&'a self) -> Option<&'a List> {
+ match self {
+ &List(ref list) => Some(&*list),
+ _ => None
+ }
+ }
+
+ /// Returns true if the Json value is a String. Returns false otherwise.
+ pub fn is_str<'a>(&'a self) -> bool {
+ match self {
+ &String(_) => true,
+ _ => false
+ }
+ }
+
+ /// If the Json value is a String, returns the associated str.
+ /// Returns None otherwise.
+ pub fn as_str<'a>(&'a self) -> Option<&'a str> {
+ match *self {
+ String(ref s) => Some(s.as_slice()),
+ _ => None
+ }
+ }
+
+ /// Returns true if the Json value is a Number. Returns false otherwise.
+ pub fn is_number(&self) -> bool {
+ match self {
+ &Number(_) => true,
+ _ => false
+ }
+ }
+
+ /// If the Json value is a Number, returns the associated f64.
+ /// Returns None otherwise.
+ pub fn as_number(&self) -> Option<f64> {
+ match self {
+ &Number(n) => Some(n),
+ _ => None
+ }
+ }
+
+ /// Returns true if the Json value is a Boolean. Returns false otherwise.
+ pub fn is_boolean(&self) -> bool {
+ match self {
+ &Boolean(_) => true,
+ _ => false
+ }
+ }
+
+ /// If the Json value is a Boolean, returns the associated bool.
+ /// Returns None otherwise.
+ pub fn as_boolean(&self) -> Option<bool> {
+ match self {
+ &Boolean(b) => Some(b),
+ _ => None
+ }
+ }
+
+ /// Returns true if the Json value is a Null. Returns false otherwise.
+ pub fn is_null(&self) -> bool {
+ match self {
+ &Null => true,
+ _ => false
+ }
+ }
+
+ /// If the Json value is a Null, returns ().
+ /// Returns None otherwise.
+ pub fn as_null(&self) -> Option<()> {
+ match self {
+ &Null => Some(()),
+ _ => None
+ }
+ }
}
pub struct Parser<T> {
check_err::<DecodeEnum>("{\"variant\": \"C\", \"fields\": []}",
"unknown variant name");
}
+
+ #[test]
+ fn test_find(){
+ let json_value = from_str("{\"dog\" : \"cat\"}").unwrap();
+ let found_str = json_value.find(&~"dog");
+ assert!(found_str.is_some() && found_str.unwrap().as_str().unwrap() == &"cat");
+ }
+
+ #[test]
+ fn test_find_path(){
+ let json_value = from_str("{\"dog\":{\"cat\": {\"mouse\" : \"cheese\"}}}").unwrap();
+ let found_str = json_value.find_path(&[&~"dog", &~"cat", &~"mouse"]);
+ assert!(found_str.is_some() && found_str.unwrap().as_str().unwrap() == &"cheese");
+ }
+
+ #[test]
+ fn test_search(){
+ let json_value = from_str("{\"dog\":{\"cat\": {\"mouse\" : \"cheese\"}}}").unwrap();
+ let found_str = json_value.search(&~"mouse").and_then(|j| j.as_str());
+ assert!(found_str.is_some());
+ assert!(found_str.unwrap() == &"cheese");
+ }
+
+ #[test]
+ fn test_is_object(){
+ let json_value = from_str("{}").unwrap();
+ assert!(json_value.is_object());
+ }
+
+ #[test]
+ fn test_as_object(){
+ let json_value = from_str("{}").unwrap();
+ let json_object = json_value.as_object();
+ assert!(json_object.is_some());
+ }
+
+ #[test]
+ fn test_is_list(){
+ let json_value = from_str("[1, 2, 3]").unwrap();
+ assert!(json_value.is_list());
+ }
+
+ #[test]
+ fn test_as_list(){
+ let json_value = from_str("[1, 2, 3]").unwrap();
+ let json_list = json_value.as_list();
+ let expected_length = 3;
+ assert!(json_list.is_some() && json_list.unwrap().len() == expected_length);
+ }
+
+ #[test]
+ fn test_is_str(){
+ let json_value = from_str("\"dog\"").unwrap();
+ assert!(json_value.is_str());
+ }
+
+ #[test]
+ fn test_as_str(){
+ let json_value = from_str("\"dog\"").unwrap();
+ let json_str = json_value.as_str();
+ let expected_str = &"dog";
+ assert_eq!(json_str, Some(expected_str));
+ }
+
+ #[test]
+ fn test_is_number(){
+ let json_value = from_str("12").unwrap();
+ assert!(json_value.is_number());
+ }
+
+ #[test]
+ fn test_as_number(){
+ let json_value = from_str("12").unwrap();
+ let json_num = json_value.as_number();
+ let expected_num = 12f64;
+ assert!(json_num.is_some() && json_num.unwrap() == expected_num);
+ }
+
+ #[test]
+ fn test_is_boolean(){
+ let json_value = from_str("false").unwrap();
+ assert!(json_value.is_boolean());
+ }
+
+ #[test]
+ fn test_as_boolean(){
+ let json_value = from_str("false").unwrap();
+ let json_bool = json_value.as_boolean();
+ let expected_bool = false;
+ assert!(json_bool.is_some() && json_bool.unwrap() == expected_bool);
+ }
+
+ #[test]
+ fn test_is_null(){
+ let json_value = from_str("null").unwrap();
+ assert!(json_value.is_null());
+ }
+
+ #[test]
+ fn test_as_null(){
+ let json_value = from_str("null").unwrap();
+ let json_null = json_value.as_null();
+ let expected_null = ();
+ assert!(json_null.is_some() && json_null.unwrap() == expected_null);
+ }
}
html_favicon_url = "http://www.rust-lang.org/favicon.ico",
html_root_url = "http://static.rust-lang.org/doc/master")];
-#[feature(macro_rules, globs, asm, managed_boxes, thread_local, link_args, simd)];
+#[feature(macro_rules, globs, asm, managed_boxes, thread_local, link_args,
+ simd, linkage, default_type_params)];
-// Turn on default type parameters.
-#[feature(default_type_params)];
// NOTE remove the following two attributes after the next snapshot.
#[allow(unrecognized_lint)];
#[allow(default_type_param_usage)];
PTHREAD_CREATE_JOINABLE), 0);
// Reserve room for the red zone, the runtime's stack of last resort.
- let stack_size = cmp::max(stack, RED_ZONE + __pthread_get_minstack(&attr) as uint);
+ let stack_size = cmp::max(stack, RED_ZONE + min_stack_size(&attr) as uint);
match pthread_attr_setstacksize(&mut attr, stack_size as libc::size_t) {
0 => {
},
#[cfg(not(target_os = "macos"), not(target_os = "android"))]
pub unsafe fn yield_now() { assert_eq!(pthread_yield(), 0); }
- #[cfg(not(target_os = "linux"))]
- unsafe fn __pthread_get_minstack(_: *libc::pthread_attr_t) -> libc::size_t {
- libc::PTHREAD_STACK_MIN
- }
-
// glibc >= 2.15 has a __pthread_get_minstack() function that returns
// PTHREAD_STACK_MIN plus however many bytes are needed for thread-local
// storage. We need that information to avoid blowing up when a small stack
// is created in an application with big thread-local storage requirements.
// See #6233 for rationale and details.
//
- // Dynamically resolve the symbol for compatibility with older versions
- // of glibc. Assumes that we've been dynamically linked to libpthread
- // but that is currently always the case. Note that this means we take
- // a dlopen/dlsym/dlclose hit for every new thread. Mitigating that by
- // caching the symbol or the function's return value has its drawbacks:
- //
- // * Caching the symbol breaks when libpthread.so is reloaded because
- // its address changes.
- //
- // * Caching the return value assumes that it's a fixed quantity.
- // Not very future-proof and untrue in the presence of guard pages
- // The reason __pthread_get_minstack() takes a *libc::pthread_attr_t
- // as its argument is because it takes pthread_attr_setguardsize() into
- // account.
- //
- // A better solution is to define __pthread_get_minstack() as a weak symbol
- // but there is currently no way to express that in Rust code.
- #[cfg(target_os = "linux")]
- unsafe fn __pthread_get_minstack(attr: *libc::pthread_attr_t) -> libc::size_t {
- use option::None;
- use result::{Err, Ok};
- use unstable::dynamic_lib;
- match dynamic_lib::DynamicLibrary::open(None) {
- Err(err) => fail!("DynamicLibrary::open(): {}", err),
- Ok(handle) => {
- match handle.symbol::<extern "C" fn(*libc::pthread_attr_t) ->
- libc::size_t>("__pthread_get_minstack") {
- Err(_) => libc::PTHREAD_STACK_MIN,
- Ok(__pthread_get_minstack) => __pthread_get_minstack(attr),
- }
- }
+ // Link weakly to the symbol for compatibility with older versions of glibc.
+ // Assumes that we've been dynamically linked to libpthread but that is
+ // currently always the case. Note that you need to check that the symbol
+ // is non-null before calling it!
+ #[cfg(target_os = "linux", not(stage0))]
+ fn min_stack_size(attr: *libc::pthread_attr_t) -> libc::size_t {
+ use ptr::RawPtr;
+ type F = extern "C" unsafe fn(*libc::pthread_attr_t) -> libc::size_t;
+ extern {
+ #[linkage = "extern_weak"]
+ static __pthread_get_minstack: *();
+ }
+ if __pthread_get_minstack.is_null() {
+ PTHREAD_STACK_MIN
+ } else {
+ unsafe { cast::transmute::<*(), F>(__pthread_get_minstack)(attr) }
}
}
+ // __pthread_get_minstack() is marked as weak but extern_weak linkage is
+ // not supported on OS X, hence this kludge...
+ #[cfg(not(target_os = "linux"))]
+ #[cfg(stage0)]
+ fn min_stack_size(_: *libc::pthread_attr_t) -> libc::size_t {
+ PTHREAD_STACK_MIN
+ }
+
extern {
fn pthread_create(native: *mut libc::pthread_t,
attr: *libc::pthread_attr_t,
assert_eq!(42, Thread::start_stack(1, proc () 42).join());
}
}
+
}
*self.get_mut(index) = val;
}
+
+ pub fn partitioned(&self, f: |&T| -> bool) -> (Vec<T>, Vec<T>) {
+ let mut lefts = Vec::new();
+ let mut rights = Vec::new();
+
+ for elt in self.iter() {
+ if f(elt) {
+ lefts.push(elt.clone());
+ } else {
+ rights.push(elt.clone());
+ }
+ }
+
+ (lefts, rights)
+ }
}
impl<T:Clone> Clone for Vec<T> {
// UNCHECKED INVARIANT: these offsets must be added in the right
// order and must be in the right places; there is shared knowledge
// about what ends a line between this file and parse.rs
+ // WARNING: pos param here is the offset relative to start of CodeMap,
+ // and CodeMap will append a newline when adding a filemap without a newline at the end,
+ // so the safe way to call this is with value calculated as
+ // filemap.start_pos + newline_offset_relative_to_the_start_of_filemap.
pub fn next_line(&self, pos: BytePos) {
// the new charpos must be > the last one (or it's the first one).
let mut lines = self.lines.borrow_mut();;
}
}
- pub fn new_filemap(&self, filename: FileName, src: ~str) -> @FileMap {
+ pub fn new_filemap(&self, filename: FileName, mut src: ~str) -> @FileMap {
let mut files = self.files.borrow_mut();
let start_pos = match files.get().last() {
None => 0,
Some(last) => last.start_pos.to_uint() + last.src.len(),
};
+ // Append '\n' in case it's not already there.
+ // This is a workaround to prevent CodeMap.lookup_filemap_idx from accidentally
+ // overflowing into the next filemap in case the last byte of span is also the last
+ // byte of filemap, which leads to incorrect results from CodeMap.span_to_*.
+ if src.len() > 0 && !src.ends_with("\n") {
+ src.push_char('\n');
+ }
+
let filemap = @FileMap {
name: filename,
src: src,
fm1.next_line(BytePos(0));
fm1.next_line(BytePos(12));
- fm2.next_line(BytePos(23));
- fm3.next_line(BytePos(23));
- fm3.next_line(BytePos(33));
+ fm2.next_line(BytePos(24));
+ fm3.next_line(BytePos(24));
+ fm3.next_line(BytePos(34));
cm
}
assert_eq!(fmabp1.fm.name, ~"blork.rs");
assert_eq!(fmabp1.pos, BytePos(22));
- let fmabp2 = cm.lookup_byte_offset(BytePos(23));
+ let fmabp2 = cm.lookup_byte_offset(BytePos(24));
assert_eq!(fmabp2.fm.name, ~"blork2.rs");
assert_eq!(fmabp2.pos, BytePos(0));
}
let cp1 = cm.bytepos_to_file_charpos(BytePos(22));
assert_eq!(cp1, CharPos(22));
- let cp2 = cm.bytepos_to_file_charpos(BytePos(23));
+ let cp2 = cm.bytepos_to_file_charpos(BytePos(24));
assert_eq!(cp2, CharPos(0));
}
assert_eq!(loc1.line, 2);
assert_eq!(loc1.col, CharPos(10));
- let loc2 = cm.lookup_char_pos(BytePos(23));
+ let loc2 = cm.lookup_char_pos(BytePos(24));
assert_eq!(loc2.file.name, ~"blork2.rs");
assert_eq!(loc2.line, 1);
assert_eq!(loc2.col, CharPos(0));
fm1.next_line(BytePos(0));
fm1.next_line(BytePos(22));
- fm2.next_line(BytePos(39));
- fm2.next_line(BytePos(57));
+ fm2.next_line(BytePos(40));
+ fm2.next_line(BytePos(58));
fm1.record_multibyte_char(BytePos(3), 3);
fm1.record_multibyte_char(BytePos(9), 3);
fm1.record_multibyte_char(BytePos(12), 3);
fm1.record_multibyte_char(BytePos(15), 3);
fm1.record_multibyte_char(BytePos(18), 3);
- fm2.record_multibyte_char(BytePos(49), 3);
- fm2.record_multibyte_char(BytePos(52), 3);
- fm2.record_multibyte_char(BytePos(57), 3);
+ fm2.record_multibyte_char(BytePos(50), 3);
+ fm2.record_multibyte_char(BytePos(53), 3);
+ fm2.record_multibyte_char(BytePos(58), 3);
cm
}
let cp2 = cm.bytepos_to_file_charpos(BytePos(6));
assert_eq!(cp2, CharPos(4));
- let cp3 = cm.bytepos_to_file_charpos(BytePos(55));
+ let cp3 = cm.bytepos_to_file_charpos(BytePos(56));
assert_eq!(cp3, CharPos(12));
- let cp4 = cm.bytepos_to_file_charpos(BytePos(60));
+ let cp4 = cm.bytepos_to_file_charpos(BytePos(61));
assert_eq!(cp4, CharPos(15));
}
+
+ #[test]
+ fn t7() {
+ // Test span_to_lines for a span ending at the end of filemap
+ let cm = init_code_map();
+ let span = Span {lo: BytePos(12), hi: BytePos(23), expn_info: None};
+ let file_lines = cm.span_to_lines(span);
+
+ assert_eq!(file_lines.file.name, ~"blork.rs");
+ assert_eq!(file_lines.lines.len(), 1);
+ assert_eq!(*file_lines.lines.get(0), 1u);
+ }
+
+ #[test]
+ fn t8() {
+ // Test span_to_snippet for a span ending at the end of filemap
+ let cm = init_code_map();
+ let span = Span {lo: BytePos(12), hi: BytePos(23), expn_info: None};
+ let snippet = cm.span_to_snippet(span);
+
+ assert_eq!(snippet, Some(~"second line"));
+ }
+
+ #[test]
+ fn t9() {
+ // Test span_to_str for a span ending at the end of filemap
+ let cm = init_code_map();
+ let span = Span {lo: BytePos(12), hi: BytePos(23), expn_info: None};
+ let sstr = cm.span_to_str(span);
+
+ assert_eq!(sstr, ~"blork.rs:2:1: 2:12");
+ }
}
pub type ItemDecorator =
fn(&mut ExtCtxt, Span, @ast::MetaItem, @ast::Item, |@ast::Item|);
+pub type ItemModifier =
+ fn(&mut ExtCtxt, Span, @ast::MetaItem, @ast::Item) -> @ast::Item;
+
pub struct BasicMacroExpander {
expander: MacroExpanderFn,
span: Option<Span>
}
}
+/// An enum representing the different kinds of syntax extensions.
pub enum SyntaxExtension {
- // #[deriving] and such
+ /// A syntax extension that is attached to an item and creates new items
+ /// based upon it.
+ ///
+ /// `#[deriving(...)]` is an `ItemDecorator`.
ItemDecorator(ItemDecorator),
- // Token-tree expanders
- NormalTT(~MacroExpander:'static, Option<Span>),
+ /// A syntax extension that is attached to an item and modifies it
+ /// in-place.
+ ItemModifier(ItemModifier),
- // An IdentTT is a macro that has an
- // identifier in between the name of the
- // macro and the argument. Currently,
- // the only examples of this is
- // macro_rules!
+ /// A normal, function-like syntax extension.
+ ///
+ /// `bytes!` is a `NormalTT`.
+ NormalTT(~MacroExpander:'static, Option<Span>),
- // perhaps macro_rules! will lose its odd special identifier argument,
- // and this can go away also
+ /// A function-like syntax extension that has an extra ident before
+ /// the block.
+ ///
+ /// `macro_rules!` is an `IdentTT`.
IdentTT(~IdentMacroExpander:'static, Option<Span>),
}
// When we enter a module, record it, for the sake of `module!`
pub fn expand_item(it: @ast::Item, fld: &mut MacroExpander)
-> SmallVector<@ast::Item> {
- let mut decorator_items: SmallVector<@ast::Item> = SmallVector::zero();
+ let it = expand_item_modifiers(it, fld);
+
+ let mut decorator_items = SmallVector::zero();
for attr in it.attrs.rev_iter() {
let mname = attr.name();
new_items
}
+fn expand_item_modifiers(mut it: @ast::Item, fld: &mut MacroExpander)
+ -> @ast::Item {
+ let (modifiers, attrs) = it.attrs.partitioned(|attr| {
+ match fld.extsbox.find(&intern(attr.name().get())) {
+ Some(&ItemModifier(_)) => true,
+ _ => false
+ }
+ });
+
+ it = @ast::Item {
+ attrs: attrs,
+ ..(*it).clone()
+ };
+
+ if modifiers.is_empty() {
+ return it;
+ }
+
+ for attr in modifiers.iter() {
+ let mname = attr.name();
+
+ match fld.extsbox.find(&intern(mname.get())) {
+ Some(&ItemModifier(dec_fn)) => {
+ fld.cx.bt_push(ExpnInfo {
+ call_site: attr.span,
+ callee: NameAndSpan {
+ name: mname.get().to_str(),
+ format: MacroAttribute,
+ span: None,
+ }
+ });
+ it = dec_fn(fld.cx, attr.span, attr.node.value, it);
+ fld.cx.bt_pop();
+ }
+ _ => unreachable!()
+ }
+ }
+
+ // expansion may have added new ItemModifiers
+ expand_item_modifiers(it, fld)
+}
+
// does this attribute list contain "macro_escape" ?
pub fn contains_macro_escape(attrs: &[ast::Attribute]) -> bool {
attr::contains_name(attrs, "macro_escape")
NormalTT(ext, _) => NormalTT(ext, Some(krate.span)),
IdentTT(ext, _) => IdentTT(ext, Some(krate.span)),
ItemDecorator(ext) => ItemDecorator(ext),
+ ItemModifier(ext) => ItemModifier(ext),
};
fld.extsbox.insert(name, extension);
});
--- /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.
+
+#[no_mangle]
+pub static foo: int = 3;
// force-host
-#[feature(globs, macro_registrar, macro_rules, quote)];
+#[feature(globs, macro_registrar, macro_rules, quote, managed_boxes)];
extern crate syntax;
-use syntax::ast::{Name, TokenTree};
+use syntax::ast::{Name, TokenTree, Item, MetaItem};
use syntax::codemap::Span;
use syntax::ext::base::*;
use syntax::parse::token;
span: None,
},
None));
+ register(token::intern("into_foo"), ItemModifier(expand_into_foo));
}
-pub fn expand_make_a_1(cx: &mut ExtCtxt, sp: Span, tts: &[TokenTree]) -> MacResult {
+fn expand_make_a_1(cx: &mut ExtCtxt, sp: Span, tts: &[TokenTree]) -> MacResult {
if !tts.is_empty() {
cx.span_fatal(sp, "make_a_1 takes no arguments");
}
MRExpr(quote_expr!(cx, 1i))
}
+fn expand_into_foo(cx: &mut ExtCtxt, sp: Span, attr: @MetaItem, it: @Item)
+ -> @Item {
+ @Item {
+ attrs: it.attrs.clone(),
+ ..(*quote_item!(cx, enum Foo { Bar, Baz }).unwrap()).clone()
+ }
+}
+
pub fn foo() {}
// except according to those terms.
// ignore-android doesn't terminate?
+// ignore-pretty
use std::iter::range_step;
use std::io::{stdin, stdout, File};
*front = complements[*back];
*back = tmp;
}
+ (Some(last), None) => *last = complements[*last], // last element
_ => break // vector exhausted.
}
}
}
- stdout().write(data);
+ stdout().write(data).unwrap();
}
-// Copyright 2012-2013-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
// file at the top-level directory of this distribution and at
// http://rust-lang.org/COPYRIGHT.
//
// option. This file may not be copied, modified, or distributed
// except according to those terms.
-// ignore-test arcs no longer unwrap
-
extern crate sync;
use std::from_str::FromStr;
use std::cmp::min;
use std::os;
use std::vec::from_elem;
-use sync::Arc;
use sync::RWArc;
fn A(i: uint, j: uint) -> f64 {
}
fn mult(v: RWArc<~[f64]>, out: RWArc<~[f64]>, f: fn(&~[f64], uint) -> f64) {
- let wait = Arc::new(());
+ // We lanch in different tasks the work to be done. To finish
+ // this fuction, we need to wait for the completion of every
+ // tasks. To do that, we give to each tasks a wait_chan that we
+ // drop at the end of the work. At the end of this function, we
+ // wait until the channel hang up.
+ let (wait_port, wait_chan) = Chan::new();
+
let len = out.read(|out| out.len());
let chunk = len / 100 + 1;
for chk in count(0, chunk) {
if chk >= len {break;}
- let w = wait.clone();
+ let w = wait_chan.clone();
let v = v.clone();
let out = out.clone();
spawn(proc() {
let val = v.read(|v| f(v, i));
out.write(|out| out[i] = val);
}
- let _ = w;
+ drop(w)
});
}
- let _ = wait.unwrap();
+
+ // wait until the channel hang up (every task finished)
+ drop(wait_chan);
+ for () in wait_port.iter() {}
}
fn mult_Av_impl(v: &~[f64], i: uint) -> f64 {
mult_AtAv(u.clone(), v.clone(), tmp.clone());
mult_AtAv(v.clone(), u.clone(), tmp.clone());
}
- let u = u.unwrap();
- let v = v.unwrap();
- println!("{:.9f}", (dot(u,v) / dot(v,v)).sqrt());
+
+ u.read(|u| v.read(|v| {
+ println!("{:.9f}", (dot(*u, *v) / dot(*v, *v)).sqrt());
+ }))
}
pub fn main() {
let x: int;
unsafe {
- asm!("mov $1, $0" : "=r"(x) : "r"(x)); //~ ERROR use of possibly uninitialized value: `x`
+ asm!("mov $1, $0" : "=r"(x) : "r"(x)); //~ ERROR use of possibly uninitialized variable: `x`
}
foo(x);
}
--- /dev/null
+// Copyright 2012 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.
+
+fn main() {
+ let i: int;
+
+ info!("{}", false && { i = 5; true });
+ info!("{}", i); //~ ERROR use of possibly uninitialized variable: `i`
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn force(f: ||) { f(); }
+fn main() {
+ let x: int;
+ force(|| { //~ ERROR capture of possibly uninitialized variable: `x`
+ info!("{}", x);
+ });
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn foo() -> int {
+ let x: int;
+
+ while 1 != 2 {
+ break;
+ x = 0;
+ }
+
+ info!("{}", x); //~ ERROR use of possibly uninitialized variable: `x`
+
+ return 17;
+}
+
+fn main() { info!("{}", foo()); }
--- /dev/null
+// Copyright 2012 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.
+
+fn foo() -> int {
+ let x: int;
+
+ loop {
+ break;
+ x = 0;
+ }
+
+ info!("{}", x); //~ ERROR use of possibly uninitialized variable: `x`
+
+ return 17;
+}
+
+fn main() { info!("{}", foo()); }
--- /dev/null
+// Copyright 2012 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.
+
+fn foo(x: int) { info!("{}", x); }
+
+fn main() {
+ let x: int; if 1 > 2 { x = 10; }
+ foo(x); //~ ERROR use of possibly uninitialized variable: `x`
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn foo(x: int) { info!("{:?}", x); }
+
+fn main() {
+ let x: int;
+ if 1 > 2 {
+ info!("whoops");
+ } else {
+ x = 10;
+ }
+ foo(x); //~ ERROR use of possibly uninitialized variable: `x`
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn main() {
+ let j: || -> int = || {
+ let i: int;
+ i //~ ERROR use of possibly uninitialized variable: `i`
+ };
+ j();
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn main() {
+ let f: || -> int = || {
+ let i: int;
+ i //~ ERROR use of possibly uninitialized variable: `i`
+ };
+ error!("{:?}", f());
+}
--- /dev/null
+// Copyright 2012 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.
+
+#[deriving(Clone)]
+struct point {
+ x: int,
+ y: int,
+}
+
+fn main() {
+ let mut origin: point;
+ origin = point {x: 10,.. origin}; //~ ERROR use of possibly uninitialized variable: `origin`
+ origin.clone();
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn test() {
+ let v: int;
+ v += 1; //~ ERROR use of possibly uninitialized variable: `v`
+ v.clone();
+}
+
+fn main() {
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn test() {
+ let mut v: int;
+ v = v + 1; //~ ERROR use of possibly uninitialized variable: `v`
+ v.clone();
+}
+
+fn main() {
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn main() {
+ let i: int;
+
+ info!("{}", false || { i = 5; true });
+ info!("{}", i); //~ ERROR use of possibly uninitialized variable: `i`
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn f() -> int {
+ let x: int;
+ return x; //~ ERROR use of possibly uninitialized variable: `x`
+}
+
+fn main() { f(); }
--- /dev/null
+// Copyright 2012 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.
+
+fn main() {
+ let bar;
+ fn baz(_x: int) { }
+ baz(bar); //~ ERROR use of possibly uninitialized variable: `bar`
+}
--- /dev/null
+// Copyright 2012-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.
+
+// Tests that the use of uninitialized variable in assignment operator
+// expression is detected.
+
+pub fn main() {
+ let x: int;
+ x += 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x -= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x *= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x /= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x %= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x ^= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x &= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x |= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x <<= 1; //~ ERROR use of possibly uninitialized variable: `x`
+
+ let x: int;
+ x >>= 1; //~ ERROR use of possibly uninitialized variable: `x`
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn foo(x: int) { info!("{}", x); }
+
+fn main() {
+ let x: int;
+ foo(x); //~ ERROR use of possibly uninitialized variable: `x`
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn test() {
+ let w: ~[int];
+ w[5] = 0; //~ ERROR use of possibly uninitialized variable: `w`
+ //~^ ERROR cannot assign to immutable vec content `w[..]`
+
+ let mut w: ~[int];
+ w[5] = 0; //~ ERROR use of possibly uninitialized variable: `w`
+}
+
+fn main() { test(); }
--- /dev/null
+// Copyright 2012 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.
+
+fn test(cond: bool) {
+ let v;
+ while cond {
+ v = 3;
+ break;
+ }
+ info!("{}", v); //~ ERROR use of possibly uninitialized variable: `v`
+}
+
+fn main() {
+ test(true);
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn main() {
+ let x: bool;
+ while x { } //~ ERROR use of possibly uninitialized variable: `x`
+}
--- /dev/null
+// Copyright 2012 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.
+
+fn f() -> int {
+ let mut x: int;
+ while 1 == 1 { x = 10; }
+ return x; //~ ERROR use of possibly uninitialized variable: `x`
+}
+
+fn main() { f(); }
--- /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.
+
+extern {
+ #[linkage = "extern_weak"] static foo: int;
+ //~^ ERROR: the `linkage` attribute is experimental and not portable
+}
--- /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.
+
+#[feature(linkage)];
+
+extern {
+ #[linkage = "extern_weak"] static foo: i32;
+ //~^ ERROR: must have type `*T`
+}
+
+fn main() {
+ println!("{}", foo);
+}
--- /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.
+
+#[feature(linkage)];
+
+extern {
+ #[linkage = "foo"] static foo: *i32;
+ //~^ ERROR: invalid linkage specified
+}
+
+fn main() {
+ println!("{}", foo);
+}
+
+++ /dev/null
-// Copyright 2012 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.
-
-fn main() {
- let i: int;
-
- info!("{}", false && { i = 5; true });
- info!("{}", i); //~ ERROR use of possibly uninitialized variable: `i`
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn force(f: ||) { f(); }
-fn main() {
- let x: int;
- force(|| {
- info!("{}", x); //~ ERROR capture of possibly uninitialized variable: `x`
- });
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn foo() -> int {
- let x: int;
-
- while 1 != 2 {
- break;
- x = 0;
- }
-
- info!("{}", x); //~ ERROR use of possibly uninitialized variable: `x`
-
- return 17;
-}
-
-fn main() { info!("{}", foo()); }
+++ /dev/null
-// Copyright 2012 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.
-
-fn foo() -> int {
- let x: int;
-
- loop {
- break;
- x = 0;
- }
-
- info!("{}", x); //~ ERROR use of possibly uninitialized variable: `x`
-
- return 17;
-}
-
-fn main() { info!("{}", foo()); }
+++ /dev/null
-// Copyright 2012 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.
-
-fn foo(x: int) { info!("{}", x); }
-
-fn main() {
- let x: int; if 1 > 2 { x = 10; }
- foo(x); //~ ERROR use of possibly uninitialized variable: `x`
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn foo(x: int) { info!("{:?}", x); }
-
-fn main() {
- let x: int;
- if 1 > 2 {
- info!("whoops");
- } else {
- x = 10;
- }
- foo(x); //~ ERROR use of possibly uninitialized variable: `x`
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn main() {
- let j: || -> int = || {
- let i: int;
- i //~ ERROR use of possibly uninitialized variable: `i`
- };
- j();
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn main() {
- let f: || -> int = || {
- let i: int;
- i //~ ERROR use of possibly uninitialized variable: `i`
- };
- error!("{:?}", f());
-}
+++ /dev/null
-// Copyright 2012 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.
-
-#[deriving(Clone)]
-struct point {
- x: int,
- y: int,
-}
-
-fn main() {
- let mut origin: point;
- origin = point {x: 10,.. origin}; //~ ERROR use of possibly uninitialized variable: `origin`
- origin.clone();
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn test() {
- let v: int;
- v += 1; //~ ERROR use of possibly uninitialized variable: `v`
- v.clone();
-}
-
-fn main() {
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn test() {
- let mut v: int;
- v = v + 1; //~ ERROR use of possibly uninitialized variable: `v`
- v.clone();
-}
-
-fn main() {
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn main() {
- let i: int;
-
- info!("{}", false || { i = 5; true });
- info!("{}", i); //~ ERROR use of possibly uninitialized variable: `i`
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn f() -> int {
- let x: int;
- return x; //~ ERROR use of possibly uninitialized variable: `x`
-}
-
-fn main() { f(); }
+++ /dev/null
-// Copyright 2012 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.
-
-fn main() {
- let bar;
- fn baz(_x: int) { }
- baz(bar); //~ ERROR use of possibly uninitialized variable: `bar`
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn foo(x: int) { info!("{}", x); }
-
-fn main() {
- let x: int;
- foo(x); //~ ERROR use of possibly uninitialized variable: `x`
-}
#[allow(unused_variable)]
fn f1c(x: int) {}
+fn f1d() {
+ let x: int;
+ //~^ ERROR unused variable: `x`
+}
+
fn f2() {
let x = 3;
//~^ ERROR unused variable: `x`
+++ /dev/null
-// Copyright 2012 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.
-
-fn test() {
- let w: ~[int];
- w[5] = 0; //~ ERROR use of possibly uninitialized variable: `w`
-}
-
-fn main() { test(); }
+++ /dev/null
-// Copyright 2012 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.
-
-fn test(cond: bool) {
- let v;
- while cond {
- v = 3;
- break;
- }
- info!("{}", v); //~ ERROR use of possibly uninitialized variable: `v`
-}
-
-fn main() {
- test(true);
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn main() {
- let x: bool;
- while x { } //~ ERROR use of possibly uninitialized variable: `x`
-}
+++ /dev/null
-// Copyright 2012 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.
-
-fn f() -> int {
- let mut x: int;
- while 1 == 1 { x = 10; }
- return x; //~ ERROR use of possibly uninitialized variable: `x`
-}
-
-fn main() { f(); }
--- /dev/null
+// Copyright 2013-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-stage1
+// ignore-pretty
+// ignore-cross-compile #12102
+
+#[feature(phase)];
+
+#[phase(syntax)]
+extern crate hexfloat;
+
+fn main() {
+ hexfloat!("foo");
+ //~^ ERROR invalid hex float literal in hexfloat!: Expected '0'
+ hexfloat!("0");
+ //~^ERROR invalid hex float literal in hexfloat!: Expected 'x'
+ hexfloat!("0x");
+ //~^ERROR invalid hex float literal in hexfloat!: Expected '.'
+ hexfloat!("0x.");
+ //~^ERROR invalid hex float literal in hexfloat!: Expected digits before or after decimal point
+ hexfloat!("0x0.0");
+ //~^ERROR invalid hex float literal in hexfloat!: Expected 'p'
+ hexfloat!("0x0.0p");
+ //~^ERROR invalid hex float literal in hexfloat!: Expected exponent digits
+ hexfloat!("0x0.0p0f");
+ //~^ERROR invalid hex float literal in hexfloat!: Expected end of string
+}
--- /dev/null
+// Copyright 2013-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-stage1
+// ignore-pretty
+// ignore-cross-compile #12102
+
+#[feature(phase)];
+
+#[phase(syntax)]
+extern crate hexfloat;
+
+fn main() {
+ hexfloat!(foo);
+ //~^ ERROR non-literal in hexfloat!
+ hexfloat!(0);
+ //~^ ERROR unsupported literal in hexfloat!
+ hexfloat!("0x0.p0", invalid);
+ //~^ ERROR invalid floating point type in hexfloat!
+}
#[phase(syntax)]
extern crate macro_crate_test;
+#[into_foo]
+#[deriving(Eq, Clone, Show)]
+fn foo() -> AFakeTypeThatHadBetterGoAway {}
+
pub fn main() {
assert_eq!(1, make_a_1!());
assert_eq!(2, exported_macro!());
+
+ assert_eq!(Bar, Bar);
+ test(None::<Foo>);
}
+
+fn test<T: Eq+Clone>(_: Option<T>) {}
--- /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-win32
+// ignore-fast
+// ignore-android
+// ignore-macos
+// aux-build:linkage1.rs
+
+#[feature(linkage)];
+
+extern crate other = "linkage1";
+
+extern {
+ #[linkage = "extern_weak"]
+ static foo: *int;
+ #[linkage = "extern_weak"]
+ static something_that_should_never_exist: *mut int;
+}
+
+fn main() {
+ assert!(!foo.is_null());
+ assert_eq!(unsafe { *foo }, 3);
+ assert!(something_that_should_never_exist.is_null());
+}
--- /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-stage1
+// ignore-pretty
+// ignore-cross-compile #12102
+// ignore-fast
+
+#[feature(phase)];
+#[phase(syntax)]
+extern crate hexfloat;
+
+pub fn main() {
+ let a = hexfloat!("0x1.999999999999ap-4");
+ assert_eq!(a, 0.1);
+ let b = hexfloat!("-0x1.fffp-4", f32);
+ assert_eq!(b, -0.12498474_f32);
+ let c = hexfloat!("0x.12345p5", f64);
+ let d = hexfloat!("0x0.12345p5", f64);
+ assert_eq!(c,d);
+ let f = hexfloat!("0x10.p4", f32);
+ let g = hexfloat!("0x10.0p4", f32);
+ assert_eq!(f,g);
+}