]> git.lizzy.rs Git - rust.git/commitdiff
Auto merge of #23251 - tbu-:pr_rm_core_str_checked_add, r=alexcrichton
authorbors <bors@rust-lang.org>
Wed, 11 Mar 2015 01:39:49 +0000 (01:39 +0000)
committerbors <bors@rust-lang.org>
Wed, 11 Mar 2015 01:39:49 +0000 (01:39 +0000)
994 files changed:
README.md
configure
man/rustc.1
man/rustdoc.1
mk/debuggers.mk
mk/docs.mk
mk/llvm.mk
mk/main.mk
mk/target.mk
mk/tests.mk
src/compiletest/common.rs
src/compiletest/compiletest.rs
src/compiletest/errors.rs
src/compiletest/header.rs
src/compiletest/procsrv.rs
src/compiletest/runtest.rs
src/compiletest/util.rs
src/doc/complement-design-faq.md
src/doc/grammar.md
src/doc/guide-tasks.md
src/doc/intro.md
src/doc/reference.md
src/doc/style/errors/ergonomics.md
src/doc/trpl/SUMMARY.md
src/doc/trpl/arrays-vectors-and-slices.md
src/doc/trpl/compound-data-types.md
src/doc/trpl/concurrency.md
src/doc/trpl/crates-and-modules.md
src/doc/trpl/documentation.md
src/doc/trpl/guessing-game.md
src/doc/trpl/method-syntax.md
src/doc/trpl/more-strings.md
src/doc/trpl/plugins.md
src/doc/trpl/pointers.md
src/doc/trpl/traits.md
src/etc/tidy.py
src/etc/unicode.py
src/grammar/parser-lalr.y
src/jemalloc
src/liballoc/arc.rs
src/liballoc/boxed.rs
src/liballoc/boxed_test.rs
src/liballoc/heap.rs
src/liballoc/lib.rs
src/liballoc/rc.rs
src/libarena/lib.rs
src/libcollections/binary_heap.rs
src/libcollections/bit.rs
src/libcollections/btree/map.rs
src/libcollections/btree/node.rs
src/libcollections/enum_set.rs
src/libcollections/fmt.rs
src/libcollections/lib.rs
src/libcollections/linked_list.rs
src/libcollections/slice.rs
src/libcollections/str.rs
src/libcollections/string.rs
src/libcollections/vec.rs
src/libcollections/vec_deque.rs
src/libcollections/vec_map.rs
src/libcore/atomic.rs
src/libcore/cell.rs
src/libcore/char.rs
src/libcore/fmt/float.rs
src/libcore/fmt/mod.rs
src/libcore/fmt/num.rs
src/libcore/hash/mod.rs
src/libcore/hash/sip.rs
src/libcore/intrinsics.rs
src/libcore/iter.rs
src/libcore/lib.rs
src/libcore/macros.rs
src/libcore/marker.rs
src/libcore/num/f32.rs
src/libcore/num/f64.rs
src/libcore/num/int_macros.rs
src/libcore/num/mod.rs
src/libcore/num/uint_macros.rs
src/libcore/num/wrapping.rs [new file with mode: 0644]
src/libcore/ops.rs
src/libcore/option.rs
src/libcore/raw.rs
src/libcore/result.rs
src/libcore/slice.rs
src/libcore/str/mod.rs
src/libcoretest/any.rs
src/libcoretest/cell.rs
src/libcoretest/char.rs
src/libcoretest/finally.rs
src/libcoretest/fmt/num.rs
src/libcoretest/hash/mod.rs
src/libcoretest/hash/sip.rs
src/libcoretest/iter.rs
src/libcoretest/lib.rs
src/libcoretest/mem.rs
src/libcoretest/num/int_macros.rs
src/libcoretest/num/mod.rs
src/libcoretest/num/uint_macros.rs
src/libcoretest/option.rs
src/libcoretest/ptr.rs
src/libcoretest/result.rs
src/libcoretest/str.rs
src/libflate/lib.rs
src/libfmt_macros/lib.rs
src/libgetopts/lib.rs
src/libgraphviz/lib.rs
src/liblibc/lib.rs
src/liblog/lib.rs
src/liblog/macros.rs
src/librand/chacha.rs
src/librand/distributions/exponential.rs
src/librand/distributions/gamma.rs
src/librand/distributions/mod.rs
src/librand/distributions/normal.rs
src/librand/distributions/range.rs
src/librand/isaac.rs
src/librand/lib.rs
src/librand/rand_impls.rs
src/librand/reseeding.rs
src/librbml/io.rs
src/librbml/lib.rs
src/librustc/lib.rs
src/librustc/lint/context.rs
src/librustc/metadata/common.rs
src/librustc/metadata/creader.rs
src/librustc/metadata/csearch.rs
src/librustc/metadata/cstore.rs
src/librustc/metadata/decoder.rs
src/librustc/metadata/encoder.rs
src/librustc/metadata/filesearch.rs
src/librustc/metadata/loader.rs
src/librustc/metadata/macro_import.rs
src/librustc/metadata/tydecode.rs
src/librustc/metadata/tyencode.rs
src/librustc/middle/astencode.rs
src/librustc/middle/check_const.rs
src/librustc/middle/check_match.rs
src/librustc/middle/const_eval.rs
src/librustc/middle/dataflow.rs
src/librustc/middle/fast_reject.rs
src/librustc/middle/infer/combine.rs
src/librustc/middle/infer/error_reporting.rs
src/librustc/middle/infer/region_inference/graphviz.rs
src/librustc/middle/lang_items.rs
src/librustc/middle/liveness.rs
src/librustc/middle/mem_categorization.rs
src/librustc/middle/region.rs
src/librustc/middle/stability.rs
src/librustc/middle/traits/mod.rs
src/librustc/middle/traits/object_safety.rs
src/librustc/middle/traits/project.rs
src/librustc/middle/traits/select.rs
src/librustc/middle/traits/util.rs
src/librustc/middle/ty.rs
src/librustc/middle/ty_fold.rs
src/librustc/middle/ty_walk.rs
src/librustc/plugin/load.rs
src/librustc/plugin/registry.rs
src/librustc/session/config.rs
src/librustc/session/mod.rs
src/librustc/session/search_paths.rs
src/librustc/util/common.rs
src/librustc/util/lev_distance.rs
src/librustc/util/nodemap.rs
src/librustc/util/ppaux.rs
src/librustc_back/archive.rs
src/librustc_back/fs.rs
src/librustc_back/lib.rs
src/librustc_back/rpath.rs
src/librustc_back/sha2.rs
src/librustc_back/target/apple_ios_base.rs
src/librustc_back/target/mod.rs
src/librustc_back/tempdir.rs [new file with mode: 0644]
src/librustc_bitflags/lib.rs
src/librustc_borrowck/borrowck/gather_loans/move_error.rs
src/librustc_borrowck/borrowck/mod.rs
src/librustc_borrowck/borrowck/move_data.rs
src/librustc_borrowck/lib.rs
src/librustc_driver/driver.rs
src/librustc_driver/lib.rs
src/librustc_driver/pretty.rs
src/librustc_driver/test.rs
src/librustc_lint/builtin.rs
src/librustc_lint/lib.rs
src/librustc_llvm/archive_ro.rs
src/librustc_llvm/lib.rs
src/librustc_privacy/lib.rs
src/librustc_resolve/lib.rs
src/librustc_trans/back/link.rs
src/librustc_trans/back/lto.rs
src/librustc_trans/back/write.rs
src/librustc_trans/lib.rs
src/librustc_trans/save/mod.rs
src/librustc_trans/save/recorder.rs
src/librustc_trans/trans/adt.rs
src/librustc_trans/trans/base.rs
src/librustc_trans/trans/cabi_aarch64.rs
src/librustc_trans/trans/closure.rs
src/librustc_trans/trans/consts.rs
src/librustc_trans/trans/context.rs
src/librustc_trans/trans/datum.rs
src/librustc_trans/trans/debuginfo.rs
src/librustc_trans/trans/expr.rs
src/librustc_trans/trans/foreign.rs
src/librustc_trans/trans/glue.rs
src/librustc_trans/trans/inline.rs
src/librustc_trans/trans/intrinsic.rs
src/librustc_trans/trans/meth.rs
src/librustc_typeck/astconv.rs
src/librustc_typeck/check/callee.rs
src/librustc_typeck/check/closure.rs
src/librustc_typeck/check/dropck.rs
src/librustc_typeck/check/implicator.rs
src/librustc_typeck/check/method/confirm.rs
src/librustc_typeck/check/method/probe.rs
src/librustc_typeck/check/mod.rs
src/librustc_typeck/check/regionck.rs
src/librustc_typeck/check/wf.rs
src/librustc_typeck/coherence/impls.rs [deleted file]
src/librustc_typeck/coherence/mod.rs
src/librustc_typeck/coherence/orphan.rs
src/librustc_typeck/coherence/overlap.rs
src/librustc_typeck/collect.rs
src/librustc_typeck/diagnostics.rs
src/librustc_typeck/lib.rs
src/librustc_typeck/variance.rs
src/librustdoc/clean/inline.rs
src/librustdoc/clean/mod.rs
src/librustdoc/externalfiles.rs
src/librustdoc/flock.rs
src/librustdoc/html/layout.rs
src/librustdoc/html/render.rs
src/librustdoc/html/static/main.css
src/librustdoc/html/static/main.js
src/librustdoc/html/static/playpen.js
src/librustdoc/lib.rs
src/librustdoc/markdown.rs
src/librustdoc/test.rs
src/libserialize/hex.rs
src/libserialize/json.rs
src/libserialize/lib.rs
src/libserialize/serialize.rs
src/libstd/ascii.rs
src/libstd/collections/hash/map.rs
src/libstd/collections/hash/table.rs
src/libstd/collections/mod.rs
src/libstd/env.rs
src/libstd/ffi/c_str.rs
src/libstd/ffi/mod.rs
src/libstd/ffi/os_str.rs
src/libstd/fs/mod.rs
src/libstd/fs/tempdir.rs
src/libstd/io/buffered.rs
src/libstd/io/cursor.rs
src/libstd/io/impls.rs
src/libstd/io/mod.rs
src/libstd/io/stdio.rs
src/libstd/io/util.rs
src/libstd/lib.rs
src/libstd/net/addr.rs
src/libstd/net/parser.rs
src/libstd/net/tcp.rs
src/libstd/num/f32.rs
src/libstd/num/f64.rs
src/libstd/num/mod.rs
src/libstd/num/strconv.rs
src/libstd/old_io/buffered.rs
src/libstd/old_io/comm_adapters.rs
src/libstd/old_io/extensions.rs
src/libstd/old_io/fs.rs
src/libstd/old_io/mod.rs
src/libstd/old_io/net/ip.rs
src/libstd/old_io/net/mod.rs
src/libstd/old_io/net/pipe.rs
src/libstd/old_io/net/tcp.rs
src/libstd/old_io/process.rs
src/libstd/old_io/stdio.rs
src/libstd/old_io/test.rs
src/libstd/old_io/timer.rs
src/libstd/old_io/util.rs
src/libstd/old_path/windows.rs
src/libstd/path.rs [changed mode: 0755->0644]
src/libstd/prelude/v1.rs
src/libstd/process.rs
src/libstd/rand/mod.rs
src/libstd/rand/os.rs
src/libstd/rand/reader.rs
src/libstd/rt/mod.rs
src/libstd/rt/unwind.rs
src/libstd/rt/util.rs
src/libstd/sync/condvar.rs
src/libstd/sync/future.rs
src/libstd/sync/mpsc/mod.rs
src/libstd/sync/mpsc/mpsc_queue.rs
src/libstd/sync/mpsc/select.rs
src/libstd/sync/mpsc/spsc_queue.rs
src/libstd/sync/mutex.rs
src/libstd/sync/rwlock.rs
src/libstd/sync/task_pool.rs
src/libstd/sys/common/net.rs
src/libstd/sys/common/thread_local.rs
src/libstd/sys/common/wtf8.rs
src/libstd/sys/unix/backtrace.rs
src/libstd/sys/unix/c.rs
src/libstd/sys/unix/ext.rs
src/libstd/sys/unix/fs.rs
src/libstd/sys/unix/os_str.rs
src/libstd/sys/unix/process.rs
src/libstd/sys/unix/tcp.rs
src/libstd/sys/windows/ext.rs
src/libstd/sys/windows/os.rs
src/libstd/sys/windows/os_str.rs
src/libstd/sys/windows/process.rs
src/libstd/sys/windows/tcp.rs
src/libstd/thread.rs
src/libstd/thread_local/mod.rs
src/libstd/thread_local/scoped.rs
src/libstd/thunk.rs
src/libstd/time/duration.rs
src/libstd/tuple.rs
src/libsyntax/abi.rs
src/libsyntax/ast.rs
src/libsyntax/ast_map/mod.rs
src/libsyntax/ast_util.rs
src/libsyntax/codemap.rs
src/libsyntax/diagnostic.rs
src/libsyntax/diagnostics/macros.rs
src/libsyntax/ext/asm.rs
src/libsyntax/ext/base.rs
src/libsyntax/ext/deriving/bounds.rs
src/libsyntax/ext/deriving/clone.rs
src/libsyntax/ext/deriving/cmp/eq.rs
src/libsyntax/ext/deriving/cmp/ord.rs
src/libsyntax/ext/deriving/cmp/totaleq.rs
src/libsyntax/ext/deriving/cmp/totalord.rs
src/libsyntax/ext/deriving/decodable.rs
src/libsyntax/ext/deriving/default.rs
src/libsyntax/ext/deriving/encodable.rs
src/libsyntax/ext/deriving/generic/mod.rs
src/libsyntax/ext/deriving/hash.rs
src/libsyntax/ext/deriving/mod.rs
src/libsyntax/ext/deriving/primitive.rs
src/libsyntax/ext/deriving/rand.rs
src/libsyntax/ext/deriving/show.rs
src/libsyntax/ext/expand.rs
src/libsyntax/ext/quote.rs
src/libsyntax/ext/source_util.rs
src/libsyntax/ext/tt/macro_parser.rs
src/libsyntax/ext/tt/macro_rules.rs
src/libsyntax/feature_gate.rs
src/libsyntax/fold.rs
src/libsyntax/lib.rs
src/libsyntax/owned_slice.rs
src/libsyntax/parse/attr.rs
src/libsyntax/parse/lexer/comments.rs
src/libsyntax/parse/lexer/mod.rs
src/libsyntax/parse/mod.rs
src/libsyntax/parse/parser.rs
src/libsyntax/parse/token.rs
src/libsyntax/print/pp.rs
src/libsyntax/print/pprust.rs
src/libsyntax/test.rs
src/libsyntax/util/interner.rs
src/libsyntax/util/small_vector.rs
src/libterm/lib.rs
src/libterm/terminfo/parm.rs
src/libterm/terminfo/parser/compiled.rs
src/libterm/terminfo/searcher.rs
src/libtest/lib.rs
src/libtest/stats.rs
src/libunicode/char.rs [new file with mode: 0644]
src/libunicode/lib.rs
src/libunicode/tables.rs
src/libunicode/u_char.rs [deleted file]
src/libunicode/u_str.rs
src/llvm
src/rustbook/book.rs
src/rustbook/build.rs
src/rustbook/error.rs
src/rustbook/help.rs
src/rustbook/main.rs
src/rustbook/serve.rs
src/rustbook/term.rs
src/rustbook/test.rs
src/rustllvm/llvm-auto-clean-trigger
src/snapshots.txt
src/test/auxiliary/cci_class_3.rs
src/test/auxiliary/cci_class_4.rs
src/test/auxiliary/cci_class_cast.rs
src/test/auxiliary/cci_impl_lib.rs
src/test/auxiliary/cci_iter_lib.rs
src/test/auxiliary/cci_no_inline_lib.rs
src/test/auxiliary/cross_crate_spans.rs [new file with mode: 0644]
src/test/auxiliary/custom_derive_plugin.rs [new file with mode: 0644]
src/test/auxiliary/internal_unstable.rs [new file with mode: 0644]
src/test/auxiliary/lint_for_crate.rs [new file with mode: 0644]
src/test/auxiliary/lint_output_format.rs [changed mode: 0755->0644]
src/test/auxiliary/macro_crate_test.rs
src/test/auxiliary/macro_reexport_1.rs
src/test/auxiliary/plugin_args.rs
src/test/auxiliary/procedural_mbe_matching.rs [new file with mode: 0644]
src/test/auxiliary/roman_numerals.rs
src/test/auxiliary/typeck-default-trait-impl-cross-crate-coherence-lib.rs [new file with mode: 0644]
src/test/auxiliary/unboxed-closures-cross-crate.rs
src/test/bench/noise.rs
src/test/bench/shootout-chameneos-redux.rs
src/test/bench/shootout-fannkuch-redux.rs
src/test/bench/shootout-fasta-redux.rs
src/test/bench/shootout-fasta.rs
src/test/bench/shootout-k-nucleotide.rs
src/test/bench/shootout-meteor.rs
src/test/bench/sudoku.rs
src/test/compile-fail-fulldeps/gated-quote.rs [new file with mode: 0644]
src/test/compile-fail-fulldeps/issue-15778-fail.rs [new file with mode: 0644]
src/test/compile-fail-fulldeps/issue-18986.rs
src/test/compile-fail/array-not-vector.rs
src/test/compile-fail/asm-in-bad-modifier.rs
src/test/compile-fail/asm-misplaced-option.rs
src/test/compile-fail/asm-out-assign-imm.rs
src/test/compile-fail/asm-out-no-modifier.rs
src/test/compile-fail/assign-to-method.rs
src/test/compile-fail/bad-bang-ann-3.rs
src/test/compile-fail/bad-bang-ann.rs
src/test/compile-fail/bad-const-type.rs
src/test/compile-fail/bad-method-typaram-kind.rs
src/test/compile-fail/binop-logic-int.rs
src/test/compile-fail/borrow-immutable-upvar-mutation.rs
src/test/compile-fail/borrow-tuple-fields.rs
src/test/compile-fail/borrowck-bad-nested-calls-free.rs
src/test/compile-fail/borrowck-bad-nested-calls-move.rs
src/test/compile-fail/borrowck-borrow-immut-deref-of-box-as-mut.rs
src/test/compile-fail/borrowck-borrowed-uniq-rvalue.rs
src/test/compile-fail/borrowck-box-insensitivity.rs
src/test/compile-fail/borrowck-call-is-borrow-issue-12224.rs
src/test/compile-fail/borrowck-closures-mut-and-imm.rs
src/test/compile-fail/borrowck-closures-two-mut.rs
src/test/compile-fail/borrowck-closures-use-after-free.rs
src/test/compile-fail/borrowck-for-loop-correct-cmt-for-pattern.rs
src/test/compile-fail/borrowck-issue-14498.rs
src/test/compile-fail/borrowck-issue-2657-1.rs
src/test/compile-fail/borrowck-issue-2657-2.rs
src/test/compile-fail/borrowck-lend-flow-if.rs
src/test/compile-fail/borrowck-lend-flow-loop.rs
src/test/compile-fail/borrowck-lend-flow.rs
src/test/compile-fail/borrowck-loan-blocks-move-cc.rs
src/test/compile-fail/borrowck-loan-blocks-mut-uniq.rs
src/test/compile-fail/borrowck-move-by-capture.rs
src/test/compile-fail/borrowck-move-error-with-note.rs
src/test/compile-fail/borrowck-move-from-subpath-of-borrowed-path.rs
src/test/compile-fail/borrowck-move-moved-value-into-closure.rs
src/test/compile-fail/borrowck-multiple-captures.rs
src/test/compile-fail/borrowck-no-cycle-in-exchange-heap.rs
src/test/compile-fail/borrowck-overloaded-index-2.rs
src/test/compile-fail/borrowck-report-with-custom-diagnostic.rs
src/test/compile-fail/borrowck-uniq-via-lend.rs
src/test/compile-fail/cfg-attr-unknown-attribute-macro-expansion.rs [new file with mode: 0644]
src/test/compile-fail/class-method-missing.rs
src/test/compile-fail/class-missing-self.rs
src/test/compile-fail/coercion-slice.rs
src/test/compile-fail/coherence-impls-builtin.rs [deleted file]
src/test/compile-fail/coherence-impls-copy.rs [new file with mode: 0644]
src/test/compile-fail/coherence-impls-send.rs [new file with mode: 0644]
src/test/compile-fail/coherence-impls-sized.rs [new file with mode: 0644]
src/test/compile-fail/coherence-orphan.rs
src/test/compile-fail/const-block-non-item-statement.rs
src/test/compile-fail/const-len-underflow-separate-spans.rs [new file with mode: 0644]
src/test/compile-fail/const-len-underflow-subspans.rs [new file with mode: 0644]
src/test/compile-fail/cross-borrow-trait.rs
src/test/compile-fail/cycle-projection-based-on-where-clause.rs
src/test/compile-fail/cycle-trait-default-type-trait.rs [new file with mode: 0644]
src/test/compile-fail/cycle-trait-supertrait-indirect.rs
src/test/compile-fail/deprecated-phase.rs
src/test/compile-fail/deriving-bounds.rs
src/test/compile-fail/deriving-meta-unknown-trait.rs
src/test/compile-fail/deriving-non-type.rs
src/test/compile-fail/destructor-restrictions.rs
src/test/compile-fail/dst-bad-assign-2.rs
src/test/compile-fail/dst-bad-assign.rs
src/test/compile-fail/duplicate-trait-bounds.rs [deleted file]
src/test/compile-fail/empty-extern-arg.rs
src/test/compile-fail/eval-enum.rs
src/test/compile-fail/feature-gate-allow-internal-unstable-nested-macro.rs [new file with mode: 0644]
src/test/compile-fail/feature-gate-allow-internal-unstable.rs [new file with mode: 0644]
src/test/compile-fail/feature-gate-intrinsics-and-lang-items.rs [deleted file]
src/test/compile-fail/feature-gate-intrinsics.rs [new file with mode: 0644]
src/test/compile-fail/feature-gate-lang-items.rs [new file with mode: 0644]
src/test/compile-fail/feature-gate-static-assert.rs [new file with mode: 0644]
src/test/compile-fail/feature-gated-feature-in-macro-arg.rs
src/test/compile-fail/gated-link-args.rs [new file with mode: 0644]
src/test/compile-fail/gated-link-llvm-intrinsics.rs [new file with mode: 0644]
src/test/compile-fail/gated-plugin_registrar.rs
src/test/compile-fail/gated-thread-local.rs [new file with mode: 0644]
src/test/compile-fail/gated-unsafe-destructor.rs [new file with mode: 0644]
src/test/compile-fail/huge-array-simple.rs
src/test/compile-fail/import-glob-circular.rs
src/test/compile-fail/index-bot.rs
src/test/compile-fail/infinite-instantiation.rs
src/test/compile-fail/infinite-vec-type-recursion.rs
src/test/compile-fail/internal-unstable-noallow.rs [new file with mode: 0644]
src/test/compile-fail/internal-unstable-thread-local.rs [new file with mode: 0644]
src/test/compile-fail/internal-unstable.rs [new file with mode: 0755]
src/test/compile-fail/issue-10291.rs
src/test/compile-fail/issue-10398.rs
src/test/compile-fail/issue-11192.rs
src/test/compile-fail/issue-11515.rs
src/test/compile-fail/issue-11714.rs
src/test/compile-fail/issue-11925.rs
src/test/compile-fail/issue-12127.rs
src/test/compile-fail/issue-13058.rs
src/test/compile-fail/issue-13466.rs
src/test/compile-fail/issue-14845.rs
src/test/compile-fail/issue-16747.rs
src/test/compile-fail/issue-17263.rs
src/test/compile-fail/issue-17283.rs
src/test/compile-fail/issue-17441.rs
src/test/compile-fail/issue-17651.rs
src/test/compile-fail/issue-17718-patterns.rs
src/test/compile-fail/issue-17913.rs
src/test/compile-fail/issue-17933.rs
src/test/compile-fail/issue-18107.rs
src/test/compile-fail/issue-18252.rs
src/test/compile-fail/issue-18389.rs
src/test/compile-fail/issue-18566.rs
src/test/compile-fail/issue-18783.rs
src/test/compile-fail/issue-18959.rs
src/test/compile-fail/issue-19244-1.rs
src/test/compile-fail/issue-19244-2.rs
src/test/compile-fail/issue-19991.rs
src/test/compile-fail/issue-20801.rs
src/test/compile-fail/issue-2150.rs
src/test/compile-fail/issue-22912.rs [new file with mode: 0644]
src/test/compile-fail/issue-23080-2.rs [new file with mode: 0644]
src/test/compile-fail/issue-23080.rs [new file with mode: 0644]
src/test/compile-fail/issue-3763.rs
src/test/compile-fail/issue-3953.rs [deleted file]
src/test/compile-fail/issue-4335.rs
src/test/compile-fail/issue-4517.rs
src/test/compile-fail/issue-5543.rs
src/test/compile-fail/issue-6804.rs
src/test/compile-fail/issue-7575.rs
src/test/compile-fail/issue-7867.rs
src/test/compile-fail/kindck-impl-type-params-2.rs
src/test/compile-fail/kindck-inherited-copy-bound.rs
src/test/compile-fail/kindck-nonsendable-1.rs
src/test/compile-fail/lifetime-inference-give-expl-lifetime-param-2.rs
src/test/compile-fail/linkage1.rs
src/test/compile-fail/lint-dead-code-4.rs
src/test/compile-fail/liveness-return-last-stmt-semi.rs
src/test/compile-fail/liveness-use-after-move.rs
src/test/compile-fail/macro-no-implicit-reexport.rs
src/test/compile-fail/macro-reexport-not-locally-visible.rs
src/test/compile-fail/malformed-derive-entry.rs [new file with mode: 0644]
src/test/compile-fail/malformed-plugin-1.rs
src/test/compile-fail/malformed-plugin-2.rs
src/test/compile-fail/malformed-plugin-3.rs
src/test/compile-fail/map-types.rs
src/test/compile-fail/method-self-arg-1.rs
src/test/compile-fail/move-in-guard-1.rs
src/test/compile-fail/move-in-guard-2.rs
src/test/compile-fail/move-out-of-tuple-field.rs
src/test/compile-fail/moves-based-on-type-no-recursive-stack-closure.rs
src/test/compile-fail/mut-cross-borrowing.rs
src/test/compile-fail/mut-pattern-mismatched.rs
src/test/compile-fail/mutable-class-fields-2.rs
src/test/compile-fail/mutable-class-fields.rs
src/test/compile-fail/non-constant-expr-for-fixed-len-vec.rs
src/test/compile-fail/non-exhaustive-pattern-witness.rs
src/test/compile-fail/nonbool_static_assert.rs
src/test/compile-fail/or-patter-mismatch.rs
src/test/compile-fail/phantom-oibit.rs [new file with mode: 0644]
src/test/compile-fail/plugin-extern-crate-attr-deprecated.rs
src/test/compile-fail/privacy5.rs
src/test/compile-fail/private-method.rs
src/test/compile-fail/private-struct-field-cross-crate.rs
src/test/compile-fail/range-1.rs
src/test/compile-fail/region-object-lifetime-in-coercion.rs
src/test/compile-fail/regions-addr-of-self.rs
src/test/compile-fail/regions-addr-of-upvar-self.rs
src/test/compile-fail/regions-close-associated-type-into-object.rs
src/test/compile-fail/regions-close-param-into-object.rs
src/test/compile-fail/regions-creating-enums.rs
src/test/compile-fail/regions-nested-fns.rs
src/test/compile-fail/regions-pattern-typing-issue-19997.rs
src/test/compile-fail/regions-proc-bound-capture.rs
src/test/compile-fail/regions-return-ref-to-upvar-issue-17403.rs
src/test/compile-fail/regions-steal-closure.rs
src/test/compile-fail/regions-trait-1.rs
src/test/compile-fail/reserved-attr-on-macro.rs [new file with mode: 0644]
src/test/compile-fail/send-is-not-static-ensures-scoping.rs [changed mode: 0755->0644]
src/test/compile-fail/single-derive-attr.rs [new file with mode: 0644]
src/test/compile-fail/static-assert.rs
src/test/compile-fail/static-assert2.rs
src/test/compile-fail/static-region-bound.rs
src/test/compile-fail/structure-constructor-type-mismatch.rs
src/test/compile-fail/tail-typeck.rs
src/test/compile-fail/trait-coercion-generic-bad.rs
src/test/compile-fail/trait-coercion-generic-regions.rs
src/test/compile-fail/traits-assoc-type-in-supertrait-bad.rs [new file with mode: 0644]
src/test/compile-fail/traits-issue-23003-overflow.rs [new file with mode: 0644]
src/test/compile-fail/traits-multidispatch-convert-ambig-dest.rs
src/test/compile-fail/traits-repeated-supertrait-ambig.rs [new file with mode: 0644]
src/test/compile-fail/tuple-index-out-of-bounds.rs
src/test/compile-fail/type-mismatch-multiple.rs
src/test/compile-fail/type-params-in-different-spaces-1.rs
src/test/compile-fail/typeck-default-trait-impl-cross-crate-coherence.rs [new file with mode: 0644]
src/test/compile-fail/typeck-default-trait-impl-outside-crate.rs
src/test/compile-fail/typeck_type_placeholder_item.rs
src/test/compile-fail/unboxed-closure-illegal-move.rs
src/test/compile-fail/unboxed-closure-immutable-capture.rs
src/test/compile-fail/unboxed-closure-region.rs
src/test/compile-fail/unboxed-closures-borrow-conflict.rs
src/test/compile-fail/unboxed-closures-mutate-upvar.rs
src/test/compile-fail/unboxed-closures-mutated-upvar-from-fn-closure.rs
src/test/compile-fail/unique-pinned-nocopy.rs
src/test/compile-fail/unique-unique-kind.rs
src/test/compile-fail/unique-vec-res.rs
src/test/compile-fail/unreachable-arm.rs
src/test/compile-fail/unsafe-fn-assign-deref-ptr.rs
src/test/compile-fail/unsized4.rs [deleted file]
src/test/compile-fail/use-after-move-implicity-coerced-object.rs
src/test/compile-fail/variance-issue-20533.rs
src/test/compile-fail/vtable-res-trait-param.rs
src/test/debuginfo/associated-types.rs
src/test/debuginfo/borrowed-struct.rs
src/test/debuginfo/boxed-struct.rs
src/test/debuginfo/closure-in-generic-function.rs
src/test/debuginfo/constant-debug-locs.rs [new file with mode: 0644]
src/test/debuginfo/cross-crate-spans.rs [new file with mode: 0644]
src/test/debuginfo/extern-c-fn.rs [new file with mode: 0644]
src/test/debuginfo/generic-method-on-generic-struct.rs
src/test/debuginfo/method-on-enum.rs
src/test/debuginfo/method-on-generic-struct.rs
src/test/debuginfo/method-on-struct.rs
src/test/debuginfo/method-on-trait.rs
src/test/debuginfo/method-on-tuple-struct.rs
src/test/debuginfo/recursive-struct.rs
src/test/debuginfo/self-in-default-method.rs
src/test/debuginfo/self-in-generic-default-method.rs
src/test/debuginfo/simd.rs
src/test/debuginfo/unique-enum.rs
src/test/debuginfo/var-captured-in-nested-closure.rs
src/test/debuginfo/var-captured-in-sendable-closure.rs
src/test/debuginfo/var-captured-in-stack-closure.rs
src/test/parse-fail/circular_modules_main.rs
src/test/parse-fail/class-implements-bad-trait.rs
src/test/parse-fail/issue-5544-b.rs
src/test/parse-fail/issue-5806.rs
src/test/parse-fail/lex-bad-char-literals.rs
src/test/parse-fail/lex-bad-numeric-literals.rs
src/test/parse-fail/regions-trait-2.rs
src/test/pretty/block-comment-wchar.pp
src/test/pretty/block-comment-wchar.rs
src/test/pretty/empty-lines.rs
src/test/pretty/issue-4264.pp
src/test/pretty/issue-4264.rs
src/test/run-fail/extern-panic.rs
src/test/run-fail/if-check-panic.rs
src/test/run-fail/overflowing-add.rs [new file with mode: 0644]
src/test/run-fail/overflowing-mul.rs [new file with mode: 0644]
src/test/run-fail/overflowing-sub.rs [new file with mode: 0644]
src/test/run-fail/panic-macro-any-wrapped.rs
src/test/run-fail/test-should-fail-bad-message.rs
src/test/run-fail/unique-panic.rs
src/test/run-fail/unwind-unique.rs
src/test/run-make/bare-outfile/Makefile [new file with mode: 0644]
src/test/run-make/bare-outfile/foo.rs [new file with mode: 0644]
src/test/run-make/debug-assertions/Makefile [new file with mode: 0644]
src/test/run-make/debug-assertions/debug.rs [new file with mode: 0644]
src/test/run-make/graphviz-flowgraph/f20.dot-expected.dot
src/test/run-make/graphviz-flowgraph/f20.rs
src/test/run-make/issue-19371/foo.rs
src/test/run-make/mismatching-target-triples/bar.rs [changed mode: 0755->0644]
src/test/run-make/mismatching-target-triples/foo.rs [changed mode: 0755->0644]
src/test/run-make/pretty-expanded-hygiene/input.pp.rs [changed mode: 0755->0644]
src/test/run-make/pretty-expanded-hygiene/input.rs [changed mode: 0755->0644]
src/test/run-make/save-analysis/foo.rs
src/test/run-make/simd-ffi/simd.rs [changed mode: 0755->0644]
src/test/run-make/symbols-are-reasonable/lib.rs
src/test/run-make/unicode-input/span_length.rs
src/test/run-pass-fulldeps/compiler-calls.rs
src/test/run-pass-fulldeps/derive-totalsum.rs [new file with mode: 0644]
src/test/run-pass-fulldeps/issue-15778-pass.rs [new file with mode: 0644]
src/test/run-pass-fulldeps/macro-crate.rs
src/test/run-pass-fulldeps/mbe_matching_test_macro.rs [new file with mode: 0644]
src/test/run-pass-fulldeps/qquote.rs
src/test/run-pass-fulldeps/quote-tokens.rs
src/test/run-pass-valgrind/dst-dtor-1.rs
src/test/run-pass-valgrind/dst-dtor-2.rs
src/test/run-pass/alias-uninit-value.rs
src/test/run-pass/assert-eq-macro-success.rs
src/test/run-pass/associated-types-binding-in-where-clause.rs
src/test/run-pass/associated-types-constant-type.rs
src/test/run-pass/associated-types-doubleendediterator-object.rs
src/test/run-pass/associated-types-eq-obj.rs
src/test/run-pass/associated-types-return.rs
src/test/run-pass/associated-types-struct-field-named.rs
src/test/run-pass/associated-types-struct-field-numbered.rs
src/test/run-pass/associated-types-sugar-path.rs
src/test/run-pass/auto-encode.rs
src/test/run-pass/autoderef-method-on-trait.rs
src/test/run-pass/autoderef-method-priority.rs
src/test/run-pass/autoderef-method-twice-but-not-thrice.rs
src/test/run-pass/autoderef-method-twice.rs
src/test/run-pass/autoderef-method.rs
src/test/run-pass/autoref-intermediate-types-issue-3585.rs
src/test/run-pass/backtrace-debuginfo.rs
src/test/run-pass/backtrace.rs
src/test/run-pass/big-literals.rs
src/test/run-pass/bitv-perf-test.rs
src/test/run-pass/block-arg-call-as.rs
src/test/run-pass/block-iter-1.rs
src/test/run-pass/block-iter-2.rs
src/test/run-pass/borrowck-closures-two-imm.rs
src/test/run-pass/borrowck-move-by-capture-ok.rs
src/test/run-pass/borrowck-mut-uniq.rs
src/test/run-pass/c-stack-returning-int64.rs
src/test/run-pass/capture-clauses-unboxed-closures.rs
src/test/run-pass/cast.rs
src/test/run-pass/cci_borrow.rs
src/test/run-pass/cci_impl_exe.rs
src/test/run-pass/cci_iter_exe.rs
src/test/run-pass/cci_no_inline_exe.rs
src/test/run-pass/class-cast-to-trait-cross-crate-2.rs
src/test/run-pass/class-cast-to-trait.rs
src/test/run-pass/class-dtor.rs
src/test/run-pass/class-exports.rs
src/test/run-pass/class-method-cross-crate.rs
src/test/run-pass/class-methods-cross-crate.rs
src/test/run-pass/class-methods.rs
src/test/run-pass/class-poly-methods.rs
src/test/run-pass/class-separate-impl.rs
src/test/run-pass/class-typarams.rs
src/test/run-pass/classes-simple-cross-crate.rs
src/test/run-pass/classes-simple-method.rs
src/test/run-pass/classes-simple.rs
src/test/run-pass/cleanup-rvalue-temp-during-incomplete-alloc.rs
src/test/run-pass/clone-with-exterior.rs
src/test/run-pass/coerce-expect-unsized.rs
src/test/run-pass/coerce-match.rs
src/test/run-pass/coerce-reborrow-imm-vec-rcvr.rs
src/test/run-pass/concat.rs
src/test/run-pass/conditional-debug-macro-off.rs
src/test/run-pass/const-block.rs
src/test/run-pass/const-bound.rs
src/test/run-pass/crate-method-reexport-grrrrrrr.rs
src/test/run-pass/deprecated-derive.rs [new file with mode: 0644]
src/test/run-pass/deref-lval.rs
src/test/run-pass/deriving-default-box.rs
src/test/run-pass/deriving-encodable-decodable-box.rs
src/test/run-pass/deriving-eq-ord-boxed-slice.rs
src/test/run-pass/double-ref.rs
src/test/run-pass/drop-trait-enum.rs
src/test/run-pass/dst-deref-mut.rs
src/test/run-pass/dst-deref.rs
src/test/run-pass/dst-struct.rs
src/test/run-pass/dst-trait.rs
src/test/run-pass/empty-allocation-non-null.rs
src/test/run-pass/empty-allocation-rvalue-non-null.rs
src/test/run-pass/explicit-self-generic.rs
src/test/run-pass/explicit-self.rs
src/test/run-pass/expr-block-unique.rs
src/test/run-pass/expr-if-unique.rs
src/test/run-pass/expr-match-unique.rs
src/test/run-pass/extern-pass-char.rs
src/test/run-pass/extern-pass-u32.rs
src/test/run-pass/extern-pass-u64.rs
src/test/run-pass/extern-stress.rs [deleted file]
src/test/run-pass/extern-yield.rs [deleted file]
src/test/run-pass/foreign-fn-linkname.rs
src/test/run-pass/foreign-mod-unused-const.rs
src/test/run-pass/foreign2.rs
src/test/run-pass/func-arg-incomplete-pattern.rs
src/test/run-pass/func-arg-ref-pattern.rs
src/test/run-pass/generic-alias-unique.rs
src/test/run-pass/generic-extern-mangle.rs
src/test/run-pass/hashmap-memory.rs
src/test/run-pass/hrtb-precedence-of-plus.rs
src/test/run-pass/i32-sub.rs
src/test/run-pass/i8-incr.rs
src/test/run-pass/if-check.rs
src/test/run-pass/ifmt.rs
src/test/run-pass/init-res-into-things.rs
src/test/run-pass/intrinsic-alignment.rs
src/test/run-pass/intrinsic-atomics.rs
src/test/run-pass/intrinsic-move-val.rs
src/test/run-pass/intrinsics-integer.rs
src/test/run-pass/intrinsics-math.rs
src/test/run-pass/issue-10802.rs
src/test/run-pass/issue-1112.rs
src/test/run-pass/issue-11205.rs
src/test/run-pass/issue-11677.rs
src/test/run-pass/issue-11736.rs
src/test/run-pass/issue-11958.rs
src/test/run-pass/issue-12744.rs
src/test/run-pass/issue-12909.rs
src/test/run-pass/issue-13808.rs
src/test/run-pass/issue-14399.rs
src/test/run-pass/issue-14589.rs
src/test/run-pass/issue-14919.rs
src/test/run-pass/issue-15571.rs
src/test/run-pass/issue-15673.rs
src/test/run-pass/issue-15734.rs
src/test/run-pass/issue-16668.rs
src/test/run-pass/issue-17662.rs
src/test/run-pass/issue-17734.rs
src/test/run-pass/issue-18425.rs
src/test/run-pass/issue-18539.rs
src/test/run-pass/issue-20055-box-trait.rs
src/test/run-pass/issue-20055-box-unsized-array.rs
src/test/run-pass/issue-20575.rs
src/test/run-pass/issue-20676.rs
src/test/run-pass/issue-21475.rs
src/test/run-pass/issue-2185.rs
src/test/run-pass/issue-22036.rs
src/test/run-pass/issue-2550.rs
src/test/run-pass/issue-2633-2.rs
src/test/run-pass/issue-2708.rs
src/test/run-pass/issue-2718.rs
src/test/run-pass/issue-2935.rs
src/test/run-pass/issue-2989.rs
src/test/run-pass/issue-3012-2.rs
src/test/run-pass/issue-3026.rs
src/test/run-pass/issue-3052.rs
src/test/run-pass/issue-3290.rs
src/test/run-pass/issue-3424.rs
src/test/run-pass/issue-3609.rs
src/test/run-pass/issue-3878.rs
src/test/run-pass/issue-4735.rs
src/test/run-pass/issue-4759-1.rs
src/test/run-pass/issue-5718.rs
src/test/run-pass/issue-6117.rs
src/test/run-pass/issue-6130.rs
src/test/run-pass/issue-6892.rs
src/test/run-pass/issue-7012.rs
src/test/run-pass/issue-8498.rs
src/test/run-pass/issue-8783.rs
src/test/run-pass/issue2170exe.rs
src/test/run-pass/iter-cloned-type-inference.rs [new file with mode: 0644]
src/test/run-pass/ivec-tag.rs
src/test/run-pass/last-use-in-cap-clause.rs
src/test/run-pass/last-use-is-capture.rs
src/test/run-pass/let-assignability.rs
src/test/run-pass/lint-cstack.rs [deleted file]
src/test/run-pass/logging-enabled-debug.rs
src/test/run-pass/logging-separate-lines.rs
src/test/run-pass/macro-interpolation.rs
src/test/run-pass/macro-pat.rs
src/test/run-pass/match-implicit-copy-unique.rs
src/test/run-pass/match-with-ret-arm.rs
src/test/run-pass/method-mut-self-modifies-mut-slice-lvalue.rs
src/test/run-pass/method-self-arg-aux1.rs
src/test/run-pass/method-self-arg-aux2.rs
src/test/run-pass/method-self-arg-trait.rs
src/test/run-pass/method-self-arg.rs
src/test/run-pass/method-two-trait-defer-resolution-2.rs
src/test/run-pass/move-1-unique.rs
src/test/run-pass/move-2-unique.rs
src/test/run-pass/move-2.rs
src/test/run-pass/move-3-unique.rs
src/test/run-pass/move-guard-const.rs
src/test/run-pass/newlambdas-ret-infer.rs
src/test/run-pass/newlambdas-ret-infer2.rs
src/test/run-pass/newtype-struct-with-dtor.rs
src/test/run-pass/nul-characters.rs
src/test/run-pass/nullable-pointer-iotareduction.rs
src/test/run-pass/object-method-numbering.rs
src/test/run-pass/objects-coerce-freeze-borrored.rs
src/test/run-pass/objects-owned-object-borrowed-method-headerless.rs
src/test/run-pass/or-pattern.rs
src/test/run-pass/overloaded-autoderef.rs
src/test/run-pass/overloaded-calls-param-vtables.rs
src/test/run-pass/overloaded-deref.rs
src/test/run-pass/overloaded-index-autoderef.rs
src/test/run-pass/owned-implies-static.rs
src/test/run-pass/packed-struct-vec.rs
src/test/run-pass/path.rs
src/test/run-pass/private-class-field.rs
src/test/run-pass/pure-sum.rs
src/test/run-pass/ranges-precedence.rs
src/test/run-pass/raw-str.rs
src/test/run-pass/rcvr-borrowed-to-region.rs
src/test/run-pass/realloc-16687.rs
src/test/run-pass/rec-align-u32.rs
src/test/run-pass/rec-align-u64.rs
src/test/run-pass/record-pat.rs
src/test/run-pass/regions-borrow-at.rs
src/test/run-pass/regions-borrow-uniq.rs
src/test/run-pass/regions-copy-closure.rs
src/test/run-pass/regions-escape-into-other-fn.rs
src/test/run-pass/regions-fn-subtyping.rs
src/test/run-pass/regions-infer-borrow-scope-within-loop-ok.rs
src/test/run-pass/regions-infer-borrow-scope.rs
src/test/run-pass/regions-params.rs
src/test/run-pass/regions-refcell.rs
src/test/run-pass/regions-relate-bound-regions-on-closures-to-inference-variables.rs
src/test/run-pass/regions-static-closure.rs
src/test/run-pass/regions-trait-object-1.rs
src/test/run-pass/rename-directory.rs
src/test/run-pass/ret-bang.rs
src/test/run-pass/running-with-no-runtime.rs
src/test/run-pass/self-in-mut-slot-default-method.rs
src/test/run-pass/self-re-assign.rs
src/test/run-pass/send-is-not-static-par-for.rs [changed mode: 0755->0644]
src/test/run-pass/sendfn-is-a-block.rs
src/test/run-pass/sendfn-spawn-with-fn-arg.rs
src/test/run-pass/shift-various-types.rs
src/test/run-pass/show-boxed-slice.rs
src/test/run-pass/single-derive-attr-with-gate.rs [new file with mode: 0644]
src/test/run-pass/small-enums-with-fields.rs
src/test/run-pass/static-assert.rs
src/test/run-pass/static-methods-in-traits.rs
src/test/run-pass/string-self-append.rs
src/test/run-pass/struct-order-of-eval-1.rs
src/test/run-pass/struct-order-of-eval-2.rs
src/test/run-pass/struct-order-of-eval-3.rs [new file with mode: 0644]
src/test/run-pass/struct-order-of-eval-4.rs [new file with mode: 0644]
src/test/run-pass/struct-return.rs
src/test/run-pass/syntax-extension-source-utils.rs
src/test/run-pass/tag-align-dyn-u64.rs
src/test/run-pass/tag-align-dyn-variants.rs
src/test/run-pass/tag-align-shape.rs
src/test/run-pass/tag-align-u64.rs
src/test/run-pass/task-comm-16.rs
src/test/run-pass/task-spawn-move-and-copy.rs
src/test/run-pass/tcp-stress.rs
src/test/run-pass/test-should-fail-good-message.rs
src/test/run-pass/trait-bounds-in-arc.rs
src/test/run-pass/trait-coercion-generic.rs
src/test/run-pass/trait-coercion.rs
src/test/run-pass/trait-default-method-bound-subst4.rs
src/test/run-pass/trait-object-generics.rs
src/test/run-pass/trait-object-with-lifetime-bound.rs
src/test/run-pass/traits-assoc-type-in-supertrait.rs [new file with mode: 0644]
src/test/run-pass/traits-conditional-dispatch.rs
src/test/run-pass/traits-issue-23003.rs [new file with mode: 0644]
src/test/run-pass/traits-repeated-supertrait.rs [new file with mode: 0644]
src/test/run-pass/type-param-constraints.rs
src/test/run-pass/type-params-in-for-each.rs
src/test/run-pass/typeck_type_placeholder_1.rs
src/test/run-pass/u32-decr.rs
src/test/run-pass/u8-incr-decr.rs
src/test/run-pass/u8-incr.rs
src/test/run-pass/ufcs-explicit-self.rs
src/test/run-pass/ufcs-trait-object.rs
src/test/run-pass/unboxed-closures-call-sugar-object-autoderef.rs
src/test/run-pass/unboxed-closures-call-sugar-object.rs
src/test/run-pass/unboxed-closures-monomorphization.rs
src/test/run-pass/unboxed-closures-prelude.rs
src/test/run-pass/unboxed-closures-unique-type-id.rs
src/test/run-pass/uniq-self-in-mut-slot.rs
src/test/run-pass/unique-assign-copy.rs
src/test/run-pass/unique-assign-drop.rs
src/test/run-pass/unique-assign-generic.rs
src/test/run-pass/unique-assign.rs
src/test/run-pass/unique-autoderef-field.rs
src/test/run-pass/unique-autoderef-index.rs
src/test/run-pass/unique-cmp.rs
src/test/run-pass/unique-containing-tag.rs
src/test/run-pass/unique-create.rs
src/test/run-pass/unique-decl-init-copy.rs
src/test/run-pass/unique-decl-init.rs
src/test/run-pass/unique-decl-move.rs
src/test/run-pass/unique-deref.rs
src/test/run-pass/unique-drop-complex.rs
src/test/run-pass/unique-in-vec-copy.rs
src/test/run-pass/unique-in-vec.rs
src/test/run-pass/unique-init.rs
src/test/run-pass/unique-kinds.rs
src/test/run-pass/unique-log.rs
src/test/run-pass/unique-match-discrim.rs
src/test/run-pass/unique-move-drop.rs
src/test/run-pass/unique-move-temp.rs
src/test/run-pass/unique-move.rs
src/test/run-pass/unique-mutable.rs
src/test/run-pass/unique-pat-2.rs
src/test/run-pass/unique-rec.rs
src/test/run-pass/unique-send-2.rs
src/test/run-pass/unique-send.rs
src/test/run-pass/unique-swap.rs
src/test/run-pass/unsized.rs
src/test/run-pass/unsized2.rs
src/test/run-pass/unsized3.rs
src/test/run-pass/unused-move-capture.rs
src/test/run-pass/unused-move.rs
src/test/run-pass/unwind-unique.rs
src/test/run-pass/utf8.rs
src/test/run-pass/utf8_chars.rs
src/test/run-pass/variadic-ffi.rs
src/test/run-pass/vec-fixed-length.rs
src/test/run-pass/vector-sort-panic-safe.rs
src/test/run-pass/weird-exprs.rs
src/test/run-pass/where-for-self.rs
src/test/run-pass/x86stdcall.rs
src/test/run-pass/x86stdcall2.rs

index c88c237cbee896985663697ed030b018393d8e89..93f0daa7141f575fd5563643a1514b47fc1a0607 100644 (file)
--- a/README.md
+++ b/README.md
@@ -115,7 +115,7 @@ The Rust community congregates in a few places:
 
 ## Contributing
 
-To contribute to Rust, please see [CONTRIBUTING.md](CONTRIBUTING.md).
+To contribute to Rust, please see [CONTRIBUTING](CONTRIBUTING.md).
 
 Rust has an [IRC] culture and most real-time collaboration happens in a
 variety of channels on Mozilla's IRC network, irc.mozilla.org. The
@@ -131,4 +131,4 @@ Rust is primarily distributed under the terms of both the MIT license
 and the Apache License (Version 2.0), with portions covered by various
 BSD-like licenses.
 
-See LICENSE-APACHE, LICENSE-MIT, and COPYRIGHT for details.
+See [LICENSE-APACHE](LICENSE-APACHE), [LICENSE-MIT](LICENSE-MIT), and [COPYRIGHT](COPYRIGHT) for details.
index e5333b45525fc3eb0636ad585bacbdba0985f5d1..b0d0c3f29b84a3e6f1f623c54a983b231accd662 100755 (executable)
--- a/configure
+++ b/configure
@@ -430,6 +430,10 @@ case $CFG_OSTYPE in
         CFG_CPUTYPE=x86_64
         ;;
 
+#   Win 8 # uname -s on 64-bit cygwin does not contain WOW64, so simply use uname -m to detect arch (works in my install)
+    CYGWIN_NT-6.3)
+       CFG_OSTYPE=pc-windows-gnu
+       ;;
 # We do not detect other OS such as XP/2003 using 64 bit using uname.
 # If we want to in the future, we will need to use Cygwin - Chuck's csih helper in /usr/lib/csih/winProductName.exe or alternative.
     *)
@@ -697,15 +701,17 @@ probe CFG_ADB        adb
 
 if [ ! -z "$CFG_PANDOC" ]
 then
-    PV_MAJOR_MINOR=$(pandoc --version | grep '^pandoc\(.exe\)\? ' |
-        # extract the first 2 version fields, ignore everything else
-        sed 's/pandoc\(.exe\)\? \([0-9]*\)\.\([0-9]*\).*/\2 \3/')
+    # Extract "MAJOR MINOR" from Pandoc's version number
+    PV_MAJOR_MINOR=$(pandoc --version | grep '^pandoc' |
+        sed -E 's/pandoc(.exe)? ([0-9]+)\.([0-9]+).*/\2 \3/')
 
     MIN_PV_MAJOR="1"
     MIN_PV_MINOR="9"
+
     # these patterns are shell globs, *not* regexps
     PV_MAJOR=${PV_MAJOR_MINOR% *}
     PV_MINOR=${PV_MAJOR_MINOR#* }
+
     if [ "$PV_MAJOR" -lt "$MIN_PV_MAJOR" ] || [ "$PV_MINOR" -lt "$MIN_PV_MINOR" ]
     then
         step_msg "pandoc $PV_MAJOR.$PV_MINOR is too old. Need at least $MIN_PV_MAJOR.$MIN_PV_MINOR. Disabling"
index 49056afa045abb46f7e970696fd03f6ec1ef0b24..f37e66001909305143f627359a9f392adbbfeb6d 100644 (file)
@@ -7,224 +7,267 @@ rustc \- The Rust compiler
 
 .SH DESCRIPTION
 This program is a compiler for the Rust language, available at
-<\fBhttps://www.rust-lang.org\fR>.
+.UR https://www.rust\-lang.org
+.UE .
 
 .SH OPTIONS
 
 .TP
 \fB\-h\fR, \fB\-\-help\fR
-Display the help message
+Display the help message.
 .TP
-\fB\-\-cfg\fR SPEC
-Configure the compilation environment
+\fB\-\-cfg\fR \fISPEC\fR
+Configure the compilation environment.
 .TP
-\fB\-L\fR [KIND=]PATH
-Add a directory to the library search path. The optional KIND can be one of:
-    dependency = only lookup transitive dependencies here
-    crate = only lookup local `extern crate` directives here
-    native = only lookup native libraries here
-    framework = only look for OSX frameworks here
-    all = look for anything here (the default)
+\fB\-L\fR [\fIKIND\fR=]\fIPATH\fR
+Add a directory to the library search path.
+The optional \fIKIND\fR can be one of:
+.RS
 .TP
-\fB\-l\fR [KIND=]NAME
-Link the generated crate(s) to the specified native library NAME. The optional
-KIND can be one of, static, dylib, or framework. If omitted, dylib is assumed.
+\fBdependency\fR
+only lookup transitive dependencies here
 .TP
-\fB\-\-crate-type\fR [bin|lib|rlib|dylib|staticlib]
-Comma separated list of types of crates for the compiler to emit
+.B crate
+only lookup local `extern crate` directives here
 .TP
-\fB\-\-crate-name NAME\fR
-Specify the name of the crate being built
+.B native
+only lookup native libraries here
 .TP
-\fB\-\-emit\fR [asm|llvm-bc|llvm-ir|obj|link|dep-info]
-Configure the output that rustc will produce
+.B framework
+only look for OSX frameworks here
 .TP
-\fB\-\-print\fR [crate-name|file-names|sysroot]
-Comma separated list of compiler information to print on stdout
+.B all
+look for anything here (the default)
+.RE
+.TP
+\fB\-l\fR [\fIKIND\fR=]\fINAME\fR
+Link the generated crate(s) to the specified native library \fINAME\fR.
+The optional \fIKIND\fR can be one of \fIstatic\fR, \fIdylib\fR, or
+\fIframework\fR.
+If omitted, \fIdylib\fR is assumed.
+.TP
+\fB\-\-crate\-type\fR [bin|lib|rlib|dylib|staticlib]
+Comma separated list of types of crates for the compiler to emit.
+.TP
+\fB\-\-crate\-name\fR \fINAME\fR
+Specify the name of the crate being built.
+.TP
+\fB\-\-emit\fR [asm|llvm\-bc|llvm\-ir|obj|link|dep\-info]
+Configure the output that \fBrustc\fR will produce.
+.TP
+\fB\-\-print\fR [crate\-name|file\-names|sysroot]
+Comma separated list of compiler information to print on stdout.
 .TP
 \fB\-g\fR
-Equivalent to \fI\-C\fR debuginfo=2
+Equivalent to \fI\-C\ debuginfo=2\fR.
 .TP
 \fB\-O\fR
-Equivalent to \fI\-C\fR opt-level=2
+Equivalent to \fI\-C\ opt\-level=2\fR.
 .TP
-\fB\-o\fR FILENAME
-Write output to <filename>. Ignored if multiple \fI\-\-emit\fR outputs are
-specified.
+\fB\-o\fR \fIFILENAME\fR
+Write output to \fIFILENAME\fR.
+Ignored if multiple \fI\-\-emit\fR outputs are specified.
 .TP
-\fB\-\-out\-dir\fR DIR
-Write output to compiler-chosen filename in <dir>. Ignored if \fI\-o\fR is
-specified. Defaults to the current directory.
+\fB\-\-out\-dir\fR \fIDIR\fR
+Write output to compiler\[hy]chosen filename in \fIDIR\fR.
+Ignored if \fI\-o\fR is specified.
+Defaults to the current directory.
 .TP
-\fB\-\-explain\fR OPT
-Provide a detailed explanation of an error message
+\fB\-\-explain\fR \fIOPT\fR
+Provide a detailed explanation of an error message.
 .TP
 \fB\-\-test\fR
-Build a test harness
+Build a test harness.
 .TP
-\fB\-\-target\fR TRIPLE
-Target triple cpu-manufacturer-kernel[-os] to compile for (see chapter 3.4 of
-http://www.sourceware.org/autobook/ for details)
+\fB\-\-target\fR \fITRIPLE\fR
+Target triple \fIcpu\fR\-\fImanufacturer\fR\-\fIkernel\fR[\-\fIos\fR]
+to compile for (see chapter 3.4 of
+.UR http://www.sourceware.org/autobook/
+.UE
+for details).
 .TP
-\fB\-W\fR help
-Print 'lint' options and default settings
+\fB\-W help\fR
+Print 'lint' options and default settings.
 .TP
-\fB\-W\fR OPT, \fB\-\-warn\fR OPT
-Set lint warnings
+\fB\-W\fR \fIOPT\fR, \fB\-\-warn\fR \fIOPT\fR
+Set lint warnings.
 .TP
-\fB\-A\fR OPT, \fB\-\-allow\fR OPT
-Set lint allowed
+\fB\-A\fR \fIOPT\fR, \fB\-\-allow\fR \fIOPT\fR
+Set lint allowed.
 .TP
-\fB\-D\fR OPT, \fB\-\-deny\fR OPT
-Set lint denied
+\fB\-D\fR \fIOPT\fR, \fB\-\-deny\fR \fIOPT\fR
+Set lint denied.
 .TP
-\fB\-F\fR OPT, \fB\-\-forbid\fR OPT
-Set lint forbidden
+\fB\-F\fR \fIOPT\fR, \fB\-\-forbid\fR \fIOPT\fR
+Set lint forbidden.
 .TP
-\fB\-C\fR FLAG[=VAL], \fB\-\-codegen\fR FLAG[=VAL]
-Set a codegen-related flag to the value specified. Use "-C help" to print
-available flags. See CODEGEN OPTIONS below
+\fB\-C\fR \fIFLAG\fR[=\fIVAL\fR], \fB\-\-codegen\fR \fIFLAG\fR[=\fIVAL\fR]
+Set a codegen\[hy]related flag to the value specified.
+Use \fI\-C help\fR to print available flags.
+See CODEGEN OPTIONS below.
 .TP
 \fB\-V\fR, \fB\-\-version\fR
-Print version info and exit
+Print version info and exit.
 .TP
 \fB\-v\fR, \fB\-\-verbose\fR
-Use verbose output
+Use verbose output.
 .TP
-\fB\-\-extern\fR NAME=PATH
-Specify where an external rust library is located
+\fB\-\-extern\fR \fINAME\fR=\fIPATH\fR
+Specify where an external rust library is located.
 .TP
-\fB\-\-sysroot\fR PATH
-Override the system root
+\fB\-\-sysroot\fR \fIPATH\fR
+Override the system root.
 .TP
-\fB\-Z\fR FLAG
-Set internal debugging options. Use "-Z help" to print available options.
+\fB\-Z\fR \fIFLAG\fR
+Set internal debugging options.
+Use \fI\-Z help\fR to print available options.
 .TP
 \fB\-\-color\fR auto|always|never
 Configure coloring of output:
-    auto = colorize, if output goes to a tty (default);
-    always = always colorize output;
-    never = never colorize output
+.RS
+.TP
+.B auto
+colorize, if output goes to a tty (default);
+.TP
+.B always
+always colorize output;
+.TP
+.B never
+never colorize output.
+.RE
 
 .SH CODEGEN OPTIONS
 
 .TP
-\fBar\fR=/path/to/ar
+\fBar\fR=\fI/path/to/ar\fR
 Path to the archive utility to use when assembling archives.
 .TP
-\fBlinker\fR=/path/to/cc
+\fBlinker\fR=\fI/path/to/cc\fR
 Path to the linker utility to use when linking libraries, executables, and
 objects.
 .TP
-\fBlink-args\fR='-flag1 -flag2'
-A space-separated list of extra arguments to pass to the linker when the linker
+\fBlink\-args\fR='\fI\-flag1 \-flag2\fR'
+A space\[hy]separated list of extra arguments to pass to the linker when the linker
 is invoked.
 .TP
 \fBlto\fR
-Perform LLVM link-time optimizations.
+Perform LLVM link\[hy]time optimizations.
 .TP
-\fBtarget-cpu\fR=help
-Selects a target processor. If the value is 'help', then a list of available
-CPUs is printed.
+\fBtarget\-cpu\fR=\fIhelp\fR
+Selects a target processor.
+If the value is 'help', then a list of available CPUs is printed.
 .TP
-\fBtarget-feature\fR='+feature1,-feature2'
-A comma-separated list of features to enable or disable for the target. A
-preceding '+' enables a feature while a preceding '-' disables it. Available
-features can be discovered through target-cpu=help.
+\fBtarget\-feature\fR='\fI+feature1\fR,\fI\-feature2\fR'
+A comma\[hy]separated list of features to enable or disable for the target.
+A preceding '+' enables a feature while a preceding '\-' disables it.
+Available features can be discovered through \fItarget\-cpu=help\fR.
 .TP
-\fBpasses\fR=list
-A space-separated list of extra LLVM passes to run. A value of 'list' will
-cause rustc to print all known passes and exit. The passes specified are
-appended at the end of the normal pass manager.
+\fBpasses\fR=\fIval\fR
+A space\[hy]separated list of extra LLVM passes to run.
+A value of 'list' will cause \fBrustc\fR to print all known passes and
+exit.
+The passes specified are appended at the end of the normal pass manager.
 .TP
-\fBllvm-args\fR='-arg1 -arg2'
-A space-separated list of arguments to pass through to LLVM.
+\fBllvm\-args\fR='\fI\-arg1\fR \fI\-arg2\fR'
+A space\[hy]separated list of arguments to pass through to LLVM.
 .TP
-\fBsave-temps\fR
-If specified, the compiler will save more files (.bc, .o, .no-opt.bc) generated
+\fBsave\-temps\fR
+If specified, the compiler will save more files (.bc, .o, .no\-opt.bc) generated
 throughout compilation in the output directory.
 .TP
 \fBrpath\fR
 If specified, then the rpath value for dynamic libraries will be set in
 either dynamic library or executable outputs.
 .TP
-\fBno-prepopulate-passes\fR
-Suppresses pre-population of the LLVM pass manager that is run over the module.
+\fBno\-prepopulate\-passes\fR
+Suppresses pre\[hy]population of the LLVM pass manager that is run over the module.
 .TP
-\fBno-vectorize-loops\fR
+\fBno\-vectorize\-loops\fR
 Suppresses running the loop vectorization LLVM pass, regardless of optimization
 level.
 .TP
-\fBno-vectorize-slp\fR
+\fBno\-vectorize\-slp\fR
 Suppresses running the LLVM SLP vectorization pass, regardless of optimization
 level.
 .TP
-\fBsoft-float\fR
+\fBsoft\-float\fR
 Generates software floating point library calls instead of hardware
 instructions.
 .TP
-\fBprefer-dynamic\fR
+\fBprefer\-dynamic\fR
 Prefers dynamic linking to static linking.
 .TP
-\fBno-integrated-as\fR
+\fBno\-integrated\-as\fR
 Force usage of an external assembler rather than LLVM's integrated one.
 .TP
-\fBno-redzone\fR
+\fBno\-redzone\fR
 Disable the use of the redzone.
 .TP
-\fBrelocation-model\fR=[pic,static,dynamic-no-pic]
-The relocation model to use. (Default: pic)
+\fBrelocation\-model\fR=[pic,static,dynamic\-no\-pic]
+The relocation model to use.
+(Default: \fIpic\fR)
 .TP
-\fBcode-model\fR=[small,kernel,medium,large]
+\fBcode\-model\fR=[small,kernel,medium,large]
 Choose the code model to use.
 .TP
-\fBmetadata\fR=val
+\fBmetadata\fR=\fIval\fR
 Metadata to mangle symbol names with.
 .TP
-\fBextra-filename\fR=val
+\fBextra\-filename\fR=\fIval\fR
 Extra data to put in each output filename.
 .TP
-\fBcodegen-units\fR=val
-Divide crate into N units to optimize in parallel.
+\fBcodegen\-units\fR=\fIn\fR
+Divide crate into \fIn\fR units to optimize in parallel.
 .TP
-\fBremark\fR=val
+\fBremark\fR=\fIval\fR
 Print remarks for these optimization passes (space separated, or "all").
 .TP
-\fBno-stack-check\fR
-Disable checks for stack exhaustion (a memory-safety hazard!).
+\fBno\-stack\-check\fR
+Disable checks for stack exhaustion (a memory\[hy]safety hazard!).
 .TP
-\fBdebuginfo\fR=val
+\fBdebuginfo\fR=\fIval\fR
 Debug info emission level:
-    0 = no debug info;
-    1 = line-tables only (for stacktraces and breakpoints);
-    2 = full debug info with variable and type information.
+.RS
+.TP
+.B 0
+no debug info;
+.TP
+.B 1
+line\[hy]tables only (for stacktraces and breakpoints);
+.TP
+.B 2
+full debug info with variable and type information.
+.RE
 .TP
-\fBopt-level\fR=val
-Optimize with possible levels 0-3
+\fBopt\-level\fR=\fIVAL\fR
+Optimize with possible levels 0\[en]3
 
 .SH "EXAMPLES"
 To build an executable from a source file with a main function:
-    $ rustc -o hello hello.rs
+    $ rustc \-o hello hello.rs
 
 To build a library from a source file:
-    $ rustc --crate-type=lib hello-lib.rs
+    $ rustc \-\-crate\-type=lib hello\-lib.rs
 
 To build either with a crate (.rs) file:
     $ rustc hello.rs
 
 To build an executable with debug info:
-    $ rustc -g -o hello hello.rs
+    $ rustc \-g \-o hello hello.rs
 
 .SH "SEE ALSO"
 
-rustdoc
+.BR rustdoc (1)
 
 .SH "BUGS"
-See <\fBhttps://github.com/rust-lang/rust/issues\fR> for issues.
+See
+.UR https://github.com/rust\-lang/rust/issues
+.UE
+for issues.
 
 .SH "AUTHOR"
-See \fBAUTHORS.txt\fR in the Rust source distribution.
+See \fIAUTHORS.txt\fR in the Rust source distribution.
 
 .SH "COPYRIGHT"
-This work is dual-licensed under Apache 2.0 and MIT terms.  See \fBCOPYRIGHT\fR
-file in the rust source distribution.
+This work is dual\[hy]licensed under Apache\ 2.0 and MIT terms.
+See \fICOPYRIGHT\fR file in the rust source distribution.
index 830884b19bde204400dc43c82c372a34932305cb..1738354fb43d50b6d01376755e688d54925f1680 100644 (file)
@@ -8,76 +8,79 @@ rustdoc \- generate documentation from Rust source code
 .SH DESCRIPTION
 This tool generates API reference documentation by extracting comments from
 source code written in the Rust language, available at
-<\fBhttps://www.rust-lang.org\fR>. It accepts several input formats and provides
-several output formats for the generated documentation.
+.UR https://www.rust\-lang.org
+.UE .
+It accepts several input formats and provides several output formats
+for the generated documentation.
 
 .SH OPTIONS
 
 .TP
--r --input-format <val>
+\fB\-r\fR, \fB\-\-input\-format\fR \fIFORMAT\fR
 html or json (default: inferred)
 .TP
--w --output-format <val>
+\fB\-w\fR, \fB\-\-output\-format\fR \fIFORMAT\fR
 html or json (default: html)
 .TP
--o --output <val>
-where to place the output (default: doc/ for html, doc.json for json)
+\fB\-o\fR, \fB\-\-output\fR \fIOUTPUT\fR
+where to place the output (default: \fIdoc/\fR for html,
+\fIdoc.json\fR for json)
 .TP
---passes <val>
-space-separated list of passes to run (default: '')
+\fB\-\-passes\fR \fILIST\fR
+space\[hy]separated list of passes to run (default: '')
 .TP
---no-defaults
+\fB\-\-no\-defaults\fR
 don't run the default passes
 .TP
---plugins <val>
+\fB\-\-plugins\fR \fILIST\fR
 space-separated list of plugins to run (default: '')
 .TP
---plugin-path <val>
-directory to load plugins from (default: /tmp/rustdoc_ng/plugins)
+\fB\-\-plugin\-path\fR \fIDIR\fR
+directory to load plugins from (default: \fI/tmp/rustdoc_ng/plugins\fR)
 .TP
---target <val>
+\fB\-\-target\fR \fITRIPLE\fR
 target triple to document
 .TP
---crate-name <val>
+\fB\-\-crate\-name\fR \fINAME\fR
 specify the name of this crate
 .TP
--L --library-path <val>
+\fB\-L\fR, \fB\-\-library\-path\fR \fIDIR\fR
 directory to add to crate search path
 .TP
---cfg <val>
-pass a --cfg to rustc
+\fB\-\-cfg\fR \fISPEC\fR
+pass a \fI\-\-cfg\fR to rustc
 .TP
---extern <val>
-pass an --extern to rustc
+\fB\-\-extern\fR \fIVAL\fR
+pass an \fI\-\-extern\fR to rustc
 .TP
---test
+\fB\-\-test\fR
 run code examples as tests
 .TP
---test-args <val>
+\fB\-\-test\-args\fR \fIARGS\fR
 pass arguments to the test runner
 .TP
---html-in-header <val>
+\fB\-\-html\-in\-header\fR \fIFILE\fR
 file to add to <head>
 .TP
---html-before-content <val>
+\fB\-\-html\-before\-content\fR \fIFILE\fR
 file to add in <body>, before content
 .TP
---html-after-content <val>
+\fB\-\-html\-after\-content\fR \fIFILE\fR
 file to add in <body>, after content
 .TP
---markdown-css <val>
+\fB\-\-markdown\-css\fR \fIFILE\fR
 CSS files to include via <link> in a rendered Markdown file
 .TP
---markdown-playground-url <val>
+\fB\-\-markdown\-playground\-url\fR \fIURL\fR
 URL to send code snippets to
 .TP
---markdown-no-toc
+\fB\-\-markdown\-no\-toc\fR
 don't include table of contents
 .TP
--h, --help
+\fB\-h\fR, \fB\-\-help\fR
 Print help
 .TP
--V, --version
+\fB\-V\fR, \fB\-\-version\fR
 Print rustdoc's version
 
 .SH "OUTPUT FORMATS"
@@ -85,14 +88,15 @@ Print rustdoc's version
 The rustdoc tool can generate output in either an HTML or JSON format.
 
 If using an HTML format, then the specified output destination will be the root
-directory of an HTML structure for all the documentation. Pages will be placed
-into this directory, and source files will also possibly be rendered into it as
-well.
+directory of an HTML structure for all the documentation.
+Pages will be placed into this directory, and source files will also
+possibly be rendered into it as well.
 
 If using a JSON format, then the specified output destination will have the
-rustdoc output serialized as JSON into it. This output format exists to
-pre-compile documentation for crates, and for usage in non-rustdoc tools. The
-JSON output is the following hash:
+rustdoc output serialized as JSON into it.
+This output format exists to pre\[hy]compile documentation for crates,
+and for usage in non\[hy]rustdoc tools.
+The JSON output is the following hash:
 
     {
         "schema": VERSION,
@@ -100,11 +104,12 @@ JSON output is the following hash:
         "plugins": ...,
     }
 
-The schema version indicates what the structure of crate/plugins will look
-like. Within a schema version the structure will remain the same. The `crate`
-field will contain all relevant documentation for the source being documented,
-and the `plugins` field will contain the output of the plugins run over the
-crate.
+The schema version indicates what the structure of crate/plugins will
+look like.
+Within a schema version the structure will remain the same.
+The \fIcrate\fR field will contain all relevant documentation for the
+source being documented, and the \fIplugins\fR field will contain the
+output of the plugins run over the crate.
 
 .SH "EXAMPLES"
 
@@ -112,25 +117,28 @@ To generate documentation for the source in the current directory:
     $ rustdoc hello.rs
 
 List all available passes that rustdoc has, along with default passes:
-    $ rustdoc --passes list
+    $ rustdoc \-\-passes list
 
 To precompile the documentation for a crate, and then use it to render html at
 a later date:
-    $ rustdoc -w json hello.rs
+    $ rustdoc \-w json hello.rs
     $ rustdoc doc.json
 
 The generated HTML can be viewed with any standard web browser.
 
 .SH "SEE ALSO"
 
-rustc
+.BR rustc (1)
 
 .SH "BUGS"
-See <\fBhttps://github.com/rust-lang/rust/issues\fR> for issues.
+See
+.UR https://github.com/rust\-lang/rust/issues
+.UE
+for issues.
 
 .SH "AUTHOR"
-See \fBAUTHORS.txt\fR in the Rust source distribution.
+See \fIAUTHORS.txt\fR in the Rust source distribution.
 
 .SH "COPYRIGHT"
-This work is dual-licensed under Apache 2.0 and MIT terms.  See \fBCOPYRIGHT\fR
-file in the rust source distribution.
+This work is dual\[hy]licensed under Apache\ 2.0 and MIT terms.
+See \fICOPYRIGHT\fR file in the rust source distribution.
index 899cc42d066e4a2032a37a5646925fecb7e913d2..e6a2174f84a82dab0104b0520535561d298aa692 100644 (file)
@@ -56,29 +56,32 @@ define DEF_INSTALL_DEBUGGER_SCRIPTS_HOST
 tmp/install-debugger-scripts$(1)_H_$(2)-gdb.done: \
   $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_GDB_ABS) \
   $$(DEBUGGER_BIN_SCRIPTS_GDB_ABS)
+       $(Q)touch $$@.start_time
        $(Q)mkdir -p $$(HBIN$(1)_H_$(2))
        $(Q)mkdir -p $$(HLIB$(1)_H_$(2))/rustlib/etc
        $(Q)install $$(DEBUGGER_BIN_SCRIPTS_GDB_ABS) $$(HBIN$(1)_H_$(2))
        $(Q)install $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_GDB_ABS) $$(HLIB$(1)_H_$(2))/rustlib/etc
-       $(Q)touch $$@
+       $(Q)touch -r $$@.start_time $$@ && rm $$@.start_time
 
 tmp/install-debugger-scripts$(1)_H_$(2)-lldb.done: \
   $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_LLDB_ABS) \
   $$(DEBUGGER_BIN_SCRIPTS_LLDB_ABS)
+       $(Q)touch $$@.start_time
        $(Q)mkdir -p $$(HBIN$(1)_H_$(2))
        $(Q)mkdir -p $$(HLIB$(1)_H_$(2))/rustlib/etc
        $(Q)install $$(DEBUGGER_BIN_SCRIPTS_LLDB_ABS) $$(HBIN$(1)_H_$(2))
        $(Q)install $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_LLDB_ABS) $$(HLIB$(1)_H_$(2))/rustlib/etc
-       $(Q)touch $$@
+       $(Q)touch -r $$@.start_time $$@ && rm $$@.start_time
 
 tmp/install-debugger-scripts$(1)_H_$(2)-all.done: \
   $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_ALL_ABS) \
   $$(DEBUGGER_BIN_SCRIPTS_ALL_ABS)
+       $(Q)touch $$@.start_time
        $(Q)mkdir -p $$(HBIN$(1)_H_$(2))
        $(Q)mkdir -p $$(HLIB$(1)_H_$(2))/rustlib/etc
        $(Q)install $$(DEBUGGER_BIN_SCRIPTS_ALL_ABS) $$(HBIN$(1)_H_$(2))
        $(Q)install $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_ALL_ABS) $$(HLIB$(1)_H_$(2))/rustlib/etc
-       $(Q)touch $$@
+       $(Q)touch -r $$@.start_time $$@ && rm $$@.start_time
 
 tmp/install-debugger-scripts$(1)_H_$(2)-none.done:
        $(Q)touch $$@
@@ -98,29 +101,32 @@ define DEF_INSTALL_DEBUGGER_SCRIPTS_TARGET
 tmp/install-debugger-scripts$(1)_T_$(2)_H_$(3)-gdb.done: \
   $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_GDB_ABS) \
   $$(DEBUGGER_BIN_SCRIPTS_GDB_ABS)
+       $(Q)touch $$@.start_time
        $(Q)mkdir -p $$(TBIN$(1)_T_$(2)_H_$(3))
        $(Q)mkdir -p $$(TLIB$(1)_T_$(2)_H_$(3))/rustlib/etc
        $(Q)install $(DEBUGGER_BIN_SCRIPTS_GDB_ABS) $$(TBIN$(1)_T_$(2)_H_$(3))
        $(Q)install $(DEBUGGER_RUSTLIB_ETC_SCRIPTS_GDB_ABS) $$(TLIB$(1)_T_$(2)_H_$(3))/rustlib/etc
-       $(Q)touch $$@
+       $(Q)touch -r $$@.start_time $$@ && rm $$@.start_time
 
 tmp/install-debugger-scripts$(1)_T_$(2)_H_$(3)-lldb.done: \
   $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_LLDB_ABS) \
   $$(DEBUGGER_BIN_SCRIPTS_LLDB_ABS)
+       $(Q)touch $$@.start_time
        $(Q)mkdir -p $$(TBIN$(1)_T_$(2)_H_$(3))
        $(Q)mkdir -p $$(TLIB$(1)_T_$(2)_H_$(3))/rustlib/etc
        $(Q)install $(DEBUGGER_BIN_SCRIPTS_LLDB_ABS) $$(TBIN$(1)_T_$(2)_H_$(3))
        $(Q)install $(DEBUGGER_RUSTLIB_ETC_SCRIPTS_LLDB_ABS) $$(TLIB$(1)_T_$(2)_H_$(3))/rustlib/etc
-       $(Q)touch $$@
+       $(Q)touch -r $$@.start_time $$@ && rm $$@.start_time
 
 tmp/install-debugger-scripts$(1)_T_$(2)_H_$(3)-all.done: \
   $$(DEBUGGER_RUSTLIB_ETC_SCRIPTS_ALL_ABS) \
   $$(DEBUGGER_BIN_SCRIPTS_ALL_ABS)
+       $(Q)touch $$@.start_time
        $(Q)mkdir -p $$(TBIN$(1)_T_$(2)_H_$(3))
        $(Q)mkdir -p $$(TLIB$(1)_T_$(2)_H_$(3))/rustlib/etc
        $(Q)install $(DEBUGGER_BIN_SCRIPTS_ALL_ABS) $$(TBIN$(1)_T_$(2)_H_$(3))
        $(Q)install $(DEBUGGER_RUSTLIB_ETC_SCRIPTS_ALL_ABS) $$(TLIB$(1)_T_$(2)_H_$(3))/rustlib/etc
-       $(Q)touch $$@
+       $(Q)touch -r $$@.start_time $$@ && rm $$@.start_time
 
 tmp/install-debugger-scripts$(1)_T_$(2)_H_$(3)-none.done:
        $(Q)touch $$@
index 743032f676d217d4201246b9cf8d5984ff8608d0..f7ab86d3a29b92d2dde26091d38dc578758ec25a 100644 (file)
@@ -273,11 +273,13 @@ compiler-docs: $(COMPILER_DOC_TARGETS)
 trpl: doc/book/index.html
 
 doc/book/index.html: $(RUSTBOOK_EXE) $(wildcard $(S)/src/doc/trpl/*.md) | doc/
+       @$(call E, rustbook: $@)
        $(Q)rm -rf doc/book
        $(Q)$(RUSTBOOK) build $(S)src/doc/trpl doc/book
 
 style: doc/style/index.html
 
 doc/style/index.html: $(RUSTBOOK_EXE) $(wildcard $(S)/src/doc/style/*.md) | doc/
+       @$(call E, rustbook: $@)
        $(Q)rm -rf doc/style
        $(Q)$(RUSTBOOK) build $(S)src/doc/style doc/style
index ba2e073803935b89632a9e476a40a4293fd45cfb..b07c2a1d62fdb8c441c4a6f0062fcd0e6b10189b 100644 (file)
@@ -38,9 +38,10 @@ endif
 # the stamp in the source dir.
 $$(LLVM_STAMP_$(1)): $(S)src/rustllvm/llvm-auto-clean-trigger
        @$$(call E, make: cleaning llvm)
+       $(Q)touch $$@.start_time
        $(Q)$(MAKE) clean-llvm$(1)
        @$$(call E, make: done cleaning llvm)
-       touch $$@
+       touch -r $$@.start_time $$@ && rm $$@.start_time
 
 ifeq ($$(CFG_ENABLE_LLVM_STATIC_STDCPP),1)
 LLVM_STDCPP_LOCATION_$(1) = $$(shell $$(CC_$(1)) $$(CFG_GCCISH_CFLAGS_$(1)) \
index 9752ee233b6e3ab0035f30af74c0cf047362046f..c00494be47cb768b367ff736dd00437a0fdb17b1 100644 (file)
@@ -18,7 +18,7 @@ CFG_RELEASE_NUM=1.0.0
 # An optional number to put after the label, e.g. '.2' -> '-beta.2'
 # NB Make sure it starts with a dot to conform to semver pre-release
 # versions (section 9)
-CFG_PRERELEASE_VERSION=.2
+CFG_PRERELEASE_VERSION=
 
 CFG_FILENAME_EXTRA=4e7c5e5c
 
@@ -30,8 +30,8 @@ CFG_PACKAGE_VERS=$(CFG_RELEASE_NUM)
 CFG_DISABLE_UNSTABLE_FEATURES=1
 endif
 ifeq ($(CFG_RELEASE_CHANNEL),beta)
-CFG_RELEASE=$(CFG_RELEASE_NUM)-alpha$(CFG_PRERELEASE_VERSION)
-CFG_PACKAGE_VERS=$(CFG_RELEASE_NUM)-alpha$(CFG_PRERELEASE_VERSION)
+CFG_RELEASE=$(CFG_RELEASE_NUM)-beta(CFG_PRERELEASE_VERSION)
+CFG_PACKAGE_VERS=$(CFG_RELEASE_NUM)-beta(CFG_PRERELEASE_VERSION)
 CFG_DISABLE_UNSTABLE_FEATURES=1
 endif
 ifeq ($(CFG_RELEASE_CHANNEL),nightly)
index 1f67d9ed8da2934a6f3c68cdf2fc6e3823d255b7..2435edfb9dc361373fcb065dcae8014d27023c0d 100644 (file)
@@ -75,6 +75,7 @@ $$(TLIB$(1)_T_$(2)_H_$(3))/stamp.$(4): \
                $$(TSREQ$(1)_T_$(2)_H_$(3)) \
                | $$(TLIB$(1)_T_$(2)_H_$(3))/
        @$$(call E, rustc: $$(@D)/lib$(4))
+       @touch $$@.start_time
        $$(call REMOVE_ALL_OLD_GLOB_MATCHES, \
            $$(dir $$@)$$(call CFG_LIB_GLOB_$(2),$(4)))
        $$(call REMOVE_ALL_OLD_GLOB_MATCHES, \
@@ -89,7 +90,7 @@ $$(TLIB$(1)_T_$(2)_H_$(3))/stamp.$(4): \
                --out-dir $$(@D) \
                -C extra-filename=-$$(CFG_FILENAME_EXTRA) \
                $$<
-       @touch $$@
+       @touch -r $$@.start_time $$@ && rm $$@.start_time
        $$(call LIST_ALL_OLD_GLOB_MATCHES, \
            $$(dir $$@)$$(call CFG_LIB_GLOB_$(2),$(4)))
        $$(call LIST_ALL_OLD_GLOB_MATCHES, \
index ca2d1a45d571f3a0317ebfe6268a6dbb971a115c..ef38abcab651877dfdd0a6a9c9358d4176cadce6 100644 (file)
@@ -389,10 +389,11 @@ check-stage$(1)-T-$(2)-H-$(3)-$(4)-exec: $$(call TEST_OK_FILE,$(1),$(2),$(3),$(4
 $$(call TEST_OK_FILE,$(1),$(2),$(3),$(4)): \
                $(3)/stage$(1)/test/$(4)test-$(2)$$(X_$(2))
        @$$(call E, run: $$<)
+       $$(Q)touch $$@.start_time
        $$(Q)$$(call CFG_RUN_TEST_$(2),$$<,$(1),$(2),$(3)) $$(TESTARGS) \
            --logfile $$(call TEST_LOG_FILE,$(1),$(2),$(3),$(4)) \
            $$(call CRATE_TEST_EXTRA_ARGS,$(1),$(2),$(3),$(4)) \
-           && touch $$@
+           && touch -r $$@.start_time $$@ && rm $$@.start_time
 endef
 
 define DEF_TEST_CRATE_RULES_android
@@ -401,6 +402,7 @@ check-stage$(1)-T-$(2)-H-$(3)-$(4)-exec: $$(call TEST_OK_FILE,$(1),$(2),$(3),$(4
 $$(call TEST_OK_FILE,$(1),$(2),$(3),$(4)): \
                $(3)/stage$(1)/test/$(4)test-$(2)$$(X_$(2))
        @$$(call E, run: $$< via adb)
+       $$(Q)touch $$@.start_time
        $$(Q)$(CFG_ADB) push $$< $(CFG_ADB_TEST_DIR)
        $$(Q)$(CFG_ADB) shell '(cd $(CFG_ADB_TEST_DIR); LD_LIBRARY_PATH=./$(2) \
                ./$$(notdir $$<) \
@@ -414,7 +416,7 @@ $$(call TEST_OK_FILE,$(1),$(2),$(3),$(4)): \
        @if grep -q "result: ok" tmp/check-stage$(1)-T-$(2)-H-$(3)-$(4).tmp; \
        then \
                rm tmp/check-stage$(1)-T-$(2)-H-$(3)-$(4).tmp; \
-               touch $$@; \
+               touch -r $$@.start_time $$@ && rm $$@.start_time; \
        else \
                rm tmp/check-stage$(1)-T-$(2)-H-$(3)-$(4).tmp; \
                exit 101; \
@@ -588,7 +590,7 @@ TEST_SREQ$(1)_T_$(2)_H_$(3) = \
 
 # The tests select when to use debug configuration on their own;
 # remove directive, if present, from CFG_RUSTC_FLAGS (issue #7898).
-CTEST_RUSTC_FLAGS := $$(subst --cfg ndebug,,$$(CFG_RUSTC_FLAGS))
+CTEST_RUSTC_FLAGS := $$(subst -C debug-assertions,,$$(CFG_RUSTC_FLAGS))
 
 # The tests cannot be optimized while the rest of the compiler is optimized, so
 # filter out the optimization (if any) from rustc and then figure out if we need
@@ -690,10 +692,11 @@ $$(call TEST_OK_FILE,$(1),$(2),$(3),$(4)): \
                $$(TEST_SREQ$(1)_T_$(2)_H_$(3)) \
                 $$(CTEST_DEPS_$(4)_$(1)-T-$(2)-H-$(3))
        @$$(call E, run $(4) [$(2)]: $$<)
+       $$(Q)touch $$@.start_time
        $$(Q)$$(call CFG_RUN_CTEST_$(2),$(1),$$<,$(3)) \
                $$(CTEST_ARGS$(1)-T-$(2)-H-$(3)-$(4)) \
                --logfile $$(call TEST_LOG_FILE,$(1),$(2),$(3),$(4)) \
-                && touch $$@
+                && touch -r $$@.start_time $$@ && rm $$@.start_time
 
 else
 
@@ -750,10 +753,11 @@ $$(call TEST_OK_FILE,$(1),$(2),$(3),$(4)): \
                $$(PRETTY_DEPS_$(4)) \
                $$(PRETTY_DEPS$(1)_H_$(3)_$(4))
        @$$(call E, run pretty-rpass [$(2)]: $$<)
+       $$(Q)touch $$@.start_time
        $$(Q)$$(call CFG_RUN_CTEST_$(2),$(1),$$<,$(3)) \
                $$(PRETTY_ARGS$(1)-T-$(2)-H-$(3)-$(4)) \
                --logfile $$(call TEST_LOG_FILE,$(1),$(2),$(3),$(4)) \
-                && touch $$@
+                && touch -r $$@.start_time $$@ && rm $$@.start_time
 
 endef
 
@@ -799,8 +803,10 @@ endif
 ifeq ($(2),$$(CFG_BUILD))
 $$(call TEST_OK_FILE,$(1),$(2),$(3),doc-$(4)): $$(DOCTESTDEP_$(1)_$(2)_$(3)_$(4))
        @$$(call E, run doc-$(4) [$(2)])
+       $$(Q)touch $$@.start_time
        $$(Q)$$(RUSTDOC_$(1)_T_$(2)_H_$(3)) --cfg dox --test $$< \
-               --test-args "$$(TESTARGS)" && touch $$@
+               --test-args "$$(TESTARGS)" && \
+               touch -r $$@.start_time $$@ && rm $$@.start_time
 else
 $$(call TEST_OK_FILE,$(1),$(2),$(3),doc-$(4)):
        touch $$@
@@ -835,9 +841,11 @@ check-stage$(1)-T-$(2)-H-$(3)-doc-crate-$(4)-exec: \
 ifeq ($(2),$$(CFG_BUILD))
 $$(call TEST_OK_FILE,$(1),$(2),$(3),doc-crate-$(4)): $$(CRATEDOCTESTDEP_$(1)_$(2)_$(3)_$(4))
        @$$(call E, run doc-crate-$(4) [$(2)])
+       $$(Q)touch $$@.start_time
        $$(Q)CFG_LLVM_LINKAGE_FILE=$$(LLVM_LINKAGE_PATH_$(3)) \
            $$(RUSTDOC_$(1)_T_$(2)_H_$(3)) --test --cfg dox \
-               $$(CRATEFILE_$(4)) --test-args "$$(TESTARGS)" && touch $$@
+               $$(CRATEFILE_$(4)) --test-args "$$(TESTARGS)" && \
+               touch -r $$@.start_time $$@ && rm $$@.start_time
 else
 $$(call TEST_OK_FILE,$(1),$(2),$(3),doc-crate-$(4)):
        touch $$@
@@ -984,6 +992,7 @@ $(3)/test/run-make/%-$(1)-T-$(2)-H-$(3).ok: \
                $$(CSREQ$(1)_T_$(2)_H_$(3))
        @rm -rf $(3)/test/run-make/$$*
        @mkdir -p $(3)/test/run-make/$$*
+       $$(Q)touch $$@.start_time
        $$(Q)$$(CFG_PYTHON) $(S)src/etc/maketest.py $$(dir $$<) \
         $$(MAKE) \
            $$(HBIN$(1)_H_$(3))/rustc$$(X_$(3)) \
@@ -996,7 +1005,7 @@ $(3)/test/run-make/%-$(1)-T-$(2)-H-$(3).ok: \
            "$$(LD_LIBRARY_PATH_ENV_TARGETDIR$(1)_T_$(2)_H_$(3))" \
            $(1) \
            $$(S)
-       @touch $$@
+       @touch -r $$@.start_time $$@ && rm $$@.start_time
 else
 # FIXME #11094 - The above rule doesn't work right for multiple targets
 check-stage$(1)-T-$(2)-H-$(3)-rmake-exec:
index 2c046d252799ee02338b399fb4e38a1b1cae75e4..fe556cecef6981eef5b856bb40ccc48d3250c272 100644 (file)
@@ -11,6 +11,7 @@
 
 use std::fmt;
 use std::str::FromStr;
+use std::path::PathBuf;
 
 #[derive(Clone, Copy, PartialEq, Debug)]
 pub enum Mode {
@@ -68,13 +69,13 @@ pub struct Config {
     pub run_lib_path: String,
 
     // The rustc executable
-    pub rustc_path: Path,
+    pub rustc_path: PathBuf,
 
     // The clang executable
-    pub clang_path: Option<Path>,
+    pub clang_path: Option<PathBuf>,
 
     // The llvm binaries path
-    pub llvm_bin_path: Option<Path>,
+    pub llvm_bin_path: Option<PathBuf>,
 
     // The valgrind path
     pub valgrind_path: Option<String>,
@@ -84,13 +85,13 @@ pub struct Config {
     pub force_valgrind: bool,
 
     // The directory containing the tests to run
-    pub src_base: Path,
+    pub src_base: PathBuf,
 
     // The directory where programs should be built
-    pub build_base: Path,
+    pub build_base: PathBuf,
 
     // Directory for auxiliary libraries
-    pub aux_base: Path,
+    pub aux_base: PathBuf,
 
     // The name of the stage being built (stage1, etc)
     pub stage_id: String,
@@ -105,7 +106,7 @@ pub struct Config {
     pub filter: Option<String>,
 
     // Write out a parseable log of tests that were run
-    pub logfile: Option<Path>,
+    pub logfile: Option<PathBuf>,
 
     // A command line to prefix program execution with,
     // for running under valgrind
@@ -133,7 +134,7 @@ pub struct Config {
     pub lldb_version: Option<String>,
 
     // Path to the android tools
-    pub android_cross_path: Path,
+    pub android_cross_path: PathBuf,
 
     // Extra parameter to run adb on arm-linux-androideabi
     pub adb_path: String,
index 4993dd140d335daac402fd10c2bff54192bd3373..e32dacd2e6aaa5ff1d2c8aa31a5e95b536e7af5d 100644 (file)
 #![feature(unboxed_closures)]
 #![feature(std_misc)]
 #![feature(test)]
-#![feature(unicode)]
 #![feature(core)]
+#![feature(path)]
+#![feature(io)]
+#![feature(net)]
+#![feature(path_ext)]
 
 #![deny(warnings)]
 
@@ -31,8 +34,9 @@
 extern crate log;
 
 use std::env;
+use std::fs;
 use std::old_io;
-use std::old_io::fs;
+use std::path::{Path, PathBuf};
 use std::thunk::Thunk;
 use getopts::{optopt, optflag, reqopt};
 use common::Config;
@@ -114,9 +118,9 @@ pub fn parse_config(args: Vec<String> ) -> Config {
         panic!()
     }
 
-    fn opt_path(m: &getopts::Matches, nm: &str) -> Path {
+    fn opt_path(m: &getopts::Matches, nm: &str) -> PathBuf {
         match m.opt_str(nm) {
-            Some(s) => Path::new(s),
+            Some(s) => PathBuf::new(&s),
             None => panic!("no option (=path) found for {}", nm),
         }
     }
@@ -131,10 +135,10 @@ fn opt_path(m: &getopts::Matches, nm: &str) -> Path {
         compile_lib_path: matches.opt_str("compile-lib-path").unwrap(),
         run_lib_path: matches.opt_str("run-lib-path").unwrap(),
         rustc_path: opt_path(matches, "rustc-path"),
-        clang_path: matches.opt_str("clang-path").map(|s| Path::new(s)),
+        clang_path: matches.opt_str("clang-path").map(|s| PathBuf::new(&s)),
         valgrind_path: matches.opt_str("valgrind-path"),
         force_valgrind: matches.opt_present("force-valgrind"),
-        llvm_bin_path: matches.opt_str("llvm-bin-path").map(|s| Path::new(s)),
+        llvm_bin_path: matches.opt_str("llvm-bin-path").map(|s| PathBuf::new(&s)),
         src_base: opt_path(matches, "src-base"),
         build_base: opt_path(matches, "build-base"),
         aux_base: opt_path(matches, "aux-base"),
@@ -142,7 +146,7 @@ fn opt_path(m: &getopts::Matches, nm: &str) -> Path {
         mode: matches.opt_str("mode").unwrap().parse().ok().expect("invalid mode"),
         run_ignored: matches.opt_present("ignored"),
         filter: filter,
-        logfile: matches.opt_str("logfile").map(|s| Path::new(s)),
+        logfile: matches.opt_str("logfile").map(|s| PathBuf::new(&s)),
         runtool: matches.opt_str("runtool"),
         host_rustcflags: matches.opt_str("host-rustcflags"),
         target_rustcflags: matches.opt_str("target-rustcflags"),
@@ -276,9 +280,9 @@ pub fn make_tests(config: &Config) -> Vec<test::TestDescAndFn> {
     debug!("making tests from {:?}",
            config.src_base.display());
     let mut tests = Vec::new();
-    let dirs = fs::readdir(&config.src_base).unwrap();
-    for file in &dirs {
-        let file = file.clone();
+    let dirs = fs::read_dir(&config.src_base).unwrap();
+    for file in dirs {
+        let file = file.unwrap().path();
         debug!("inspecting file {:?}", file.display());
         if is_test(config, &file) {
             let t = make_test(config, &file, || {
@@ -301,7 +305,7 @@ pub fn is_test(config: &Config, testfile: &Path) -> bool {
           _ => vec!(".rc".to_string(), ".rs".to_string())
         };
     let invalid_prefixes = vec!(".".to_string(), "#".to_string(), "~".to_string());
-    let name = testfile.filename_str().unwrap();
+    let name = testfile.file_name().unwrap().to_str().unwrap();
 
     let mut valid = false;
 
@@ -327,7 +331,7 @@ pub fn make_test<F>(config: &Config, testfile: &Path, f: F) -> test::TestDescAnd
         desc: test::TestDesc {
             name: make_test_name(config, testfile),
             ignore: header::is_test_ignored(config, testfile),
-            should_fail: test::ShouldFail::No,
+            should_panic: test::ShouldPanic::No,
         },
         testfn: f(),
     }
@@ -337,9 +341,9 @@ pub fn make_test_name(config: &Config, testfile: &Path) -> test::TestName {
 
     // Try to elide redundant long paths
     fn shorten(path: &Path) -> String {
-        let filename = path.filename_str();
-        let p = path.dir_path();
-        let dir = p.filename_str();
+        let filename = path.file_name().unwrap().to_str();
+        let p = path.parent().unwrap();
+        let dir = p.file_name().unwrap().to_str();
         format!("{}/{}", dir.unwrap_or(""), filename.unwrap_or(""))
     }
 
@@ -348,19 +352,17 @@ fn shorten(path: &Path) -> String {
 
 pub fn make_test_closure(config: &Config, testfile: &Path) -> test::TestFn {
     let config = (*config).clone();
-    // FIXME (#9639): This needs to handle non-utf8 paths
-    let testfile = testfile.as_str().unwrap().to_string();
+    let testfile = testfile.to_path_buf();
     test::DynTestFn(Thunk::new(move || {
-        runtest::run(config, testfile)
+        runtest::run(config, &testfile)
     }))
 }
 
 pub fn make_metrics_test_closure(config: &Config, testfile: &Path) -> test::TestFn {
     let config = (*config).clone();
-    // FIXME (#9639): This needs to handle non-utf8 paths
-    let testfile = testfile.as_str().unwrap().to_string();
+    let testfile = testfile.to_path_buf();
     test::DynMetricFn(box move |mm: &mut test::MetricMap| {
-        runtest::run_metrics(config, testfile, mm)
+        runtest::run_metrics(config, &testfile, mm)
     })
 }
 
index 7411a9b48d417e70936dcacfad51c6b10822a5ee..2b0e7985229e2bd85e81ba97b5a0b8c05b52dc35 100644 (file)
@@ -9,7 +9,10 @@
 // except according to those terms.
 use self::WhichLine::*;
 
-use std::old_io::{BufferedReader, File};
+use std::fs::File;
+use std::io::BufReader;
+use std::io::prelude::*;
+use std::path::Path;
 
 pub struct ExpectedError {
     pub line: uint,
@@ -29,7 +32,7 @@ enum WhichLine { ThisLine, FollowPrevious(uint), AdjustBackward(uint) }
 ///          //~| ERROR message two for that same line.
 // Load any test directives embedded in the file
 pub fn load_errors(testfile: &Path) -> Vec<ExpectedError> {
-    let mut rdr = BufferedReader::new(File::open(testfile).unwrap());
+    let rdr = BufReader::new(File::open(testfile).unwrap());
 
     // `last_nonfollow_error` tracks the most recently seen
     // line with an error template that did not use the
@@ -68,7 +71,7 @@ fn parse_expected(last_nonfollow_error: Option<uint>,
     let letters = line[kind_start..].chars();
     let kind = letters.skip_while(|c| c.is_whitespace())
                       .take_while(|c| !c.is_whitespace())
-                      .map(|c| c.to_lowercase())
+                      .flat_map(|c| c.to_lowercase())
                       .collect::<String>();
     let letters = line[kind_start..].chars();
     let msg = letters.skip_while(|c| c.is_whitespace())
index e5570fe0b8fb0c84cd0dd0121e9f445f0c84f702..21cebc61b3a9d3d4dcc821e15de197b896bdd769 100644 (file)
@@ -9,6 +9,10 @@
 // except according to those terms.
 
 use std::env;
+use std::fs::File;
+use std::io::BufReader;
+use std::io::prelude::*;
+use std::path::{Path, PathBuf};
 
 use common::Config;
 use common;
@@ -23,7 +27,7 @@ pub struct TestProps {
     pub run_flags: Option<String>,
     // If present, the name of a file that this test should match when
     // pretty-printed
-    pub pp_exact: Option<Path>,
+    pub pp_exact: Option<PathBuf>,
     // Modules from aux directory that should be compiled
     pub aux_builds: Vec<String> ,
     // Environment settings to use during execution
@@ -62,7 +66,7 @@ pub fn load_props(testfile: &Path) -> TestProps {
     let mut pretty_mode = None;
     let mut pretty_compare_only = false;
     let mut forbid_output = Vec::new();
-    iter_header(testfile, |ln| {
+    iter_header(testfile, &mut |ln| {
         match parse_error_pattern(ln) {
           Some(ep) => error_patterns.push(ep),
           None => ()
@@ -219,7 +223,7 @@ fn ignore_lldb(config: &Config, line: &str) -> bool {
         }
     }
 
-    let val = iter_header(testfile, |ln| {
+    let val = iter_header(testfile, &mut |ln| {
         !parse_name_directive(ln, "ignore-test") &&
         !parse_name_directive(ln, &ignore_target(config)) &&
         !parse_name_directive(ln, &ignore_stage(config)) &&
@@ -232,12 +236,8 @@ fn ignore_lldb(config: &Config, line: &str) -> bool {
     !val
 }
 
-fn iter_header<F>(testfile: &Path, mut it: F) -> bool where
-    F: FnMut(&str) -> bool,
-{
-    use std::old_io::{BufferedReader, File};
-
-    let mut rdr = BufferedReader::new(File::open(testfile).unwrap());
+fn iter_header(testfile: &Path, it: &mut FnMut(&str) -> bool) -> bool {
+    let rdr = BufReader::new(File::open(testfile).unwrap());
     for ln in rdr.lines() {
         // Assume that any directives will be found before the first
         // module or function. This doesn't seem to be an optimization
@@ -322,12 +322,12 @@ fn parse_exec_env(line: &str) -> Option<(String, String)> {
     })
 }
 
-fn parse_pp_exact(line: &str, testfile: &Path) -> Option<Path> {
+fn parse_pp_exact(line: &str, testfile: &Path) -> Option<PathBuf> {
     match parse_name_value_directive(line, "pp-exact") {
-      Some(s) => Some(Path::new(s)),
+      Some(s) => Some(PathBuf::new(&s)),
       None => {
         if parse_name_directive(line, "pp-exact") {
-            testfile.filename().map(|s| Path::new(s))
+            testfile.file_name().map(|s| PathBuf::new(s))
         } else {
             None
         }
index 148a43e6c783196555b044efb3e4ec8e1791d4d6..b684dbcfaceb98b4c465295faf6086fede5b33c0 100644 (file)
@@ -8,7 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-use std::old_io::process::{ProcessExit, Command, Process, ProcessOutput};
+use std::process::{ExitStatus, Command, Child, Output, Stdio};
+use std::io::prelude::*;
 use std::dynamic_lib::DynamicLibrary;
 
 fn add_target_env(cmd: &mut Command, lib_path: &str, aux_path: Option<&str>) {
@@ -25,10 +26,10 @@ fn add_target_env(cmd: &mut Command, lib_path: &str, aux_path: Option<&str>) {
     let var = DynamicLibrary::envvar();
     let newpath = DynamicLibrary::create_path(&path);
     let newpath = String::from_utf8(newpath).unwrap();
-    cmd.env(var.to_string(), newpath);
+    cmd.env(var, &newpath);
 }
 
-pub struct Result {pub status: ProcessExit, pub out: String, pub err: String}
+pub struct Result {pub status: ExitStatus, pub out: String, pub err: String}
 
 pub fn run(lib_path: &str,
            prog: &str,
@@ -38,10 +39,13 @@ pub fn run(lib_path: &str,
            input: Option<String>) -> Option<Result> {
 
     let mut cmd = Command::new(prog);
-    cmd.args(args);
+    cmd.args(args)
+       .stdin(Stdio::piped())
+       .stdout(Stdio::piped())
+       .stderr(Stdio::piped());
     add_target_env(&mut cmd, lib_path, aux_path);
     for (key, val) in env {
-        cmd.env(key, val);
+        cmd.env(&key, &val);
     }
 
     match cmd.spawn() {
@@ -49,13 +53,13 @@ pub fn run(lib_path: &str,
             if let Some(input) = input {
                 process.stdin.as_mut().unwrap().write_all(input.as_bytes()).unwrap();
             }
-            let ProcessOutput { status, output, error } =
+            let Output { status, stdout, stderr } =
                 process.wait_with_output().unwrap();
 
             Some(Result {
                 status: status,
-                out: String::from_utf8(output).unwrap(),
-                err: String::from_utf8(error).unwrap()
+                out: String::from_utf8(stdout).unwrap(),
+                err: String::from_utf8(stderr).unwrap()
             })
         },
         Err(..) => None
@@ -67,13 +71,16 @@ pub fn run_background(lib_path: &str,
            aux_path: Option<&str>,
            args: &[String],
            env: Vec<(String, String)> ,
-           input: Option<String>) -> Option<Process> {
+           input: Option<String>) -> Option<Child> {
 
     let mut cmd = Command::new(prog);
-    cmd.args(args);
+    cmd.args(args)
+       .stdin(Stdio::piped())
+       .stdout(Stdio::piped())
+       .stderr(Stdio::piped());
     add_target_env(&mut cmd, lib_path, aux_path);
     for (key, val) in env {
-        cmd.env(key, val);
+        cmd.env(&key, &val);
     }
 
     match cmd.spawn() {
index 85bbd2cb42e6983ce121cefe047f9ce431dae786..04714b50fc027b78215777f4f388b3eec326e9bc 100644 (file)
 use self::TargetLocation::*;
 
 use common::Config;
-use common::{CompileFail, ParseFail, Pretty, RunFail, RunPass, RunPassValgrind, DebugInfoGdb};
-use common::{Codegen, DebugInfoLldb};
+use common::{CompileFail, ParseFail, Pretty, RunFail, RunPass, RunPassValgrind};
+use common::{Codegen, DebugInfoLldb, DebugInfoGdb};
 use errors;
 use header::TestProps;
 use header;
 use procsrv;
 use util::logv;
-#[cfg(target_os = "windows")]
-use util;
-
-#[cfg(target_os = "windows")]
-use std::ascii::AsciiExt;
-use std::old_io::File;
-use std::old_io::fs::PathExtensions;
-use std::old_io::fs;
-use std::old_io::net::tcp;
-use std::old_io::process::ProcessExit;
-use std::old_io::process;
-use std::old_io::timer;
-use std::old_io;
+
 use std::env;
+use std::fmt;
+use std::fs::{self, File};
+use std::io::BufReader;
+use std::io::prelude::*;
 use std::iter::repeat;
+use std::net::TcpStream;
+use std::old_io::timer;
+use std::path::{Path, PathBuf};
+use std::process::{Command, Output, ExitStatus};
 use std::str;
-use std::string::String;
-use std::thread;
 use std::time::Duration;
 use test::MetricMap;
 
-pub fn run(config: Config, testfile: String) {
+pub fn run(config: Config, testfile: &Path) {
     match &*config.target {
 
         "arm-linux-androideabi" | "aarch64-linux-android" => {
@@ -55,12 +49,11 @@ pub fn run(config: Config, testfile: String) {
     run_metrics(config, testfile, &mut _mm);
 }
 
-pub fn run_metrics(config: Config, testfile: String, mm: &mut MetricMap) {
+pub fn run_metrics(config: Config, testfile: &Path, mm: &mut MetricMap) {
     if config.verbose {
         // We're going to be dumping a lot of info. Start on a new line.
         print!("\n\n");
     }
-    let testfile = Path::new(testfile);
     debug!("running {:?}", testfile.display());
     let props = header::load_props(&testfile);
     debug!("loaded props");
@@ -127,8 +120,8 @@ fn run_rfail_test(config: &Config, props: &TestProps, testfile: &Path) {
     };
 
     // The value our Makefile configures valgrind to return on failure
-    static VALGRIND_ERR: int = 100;
-    if proc_res.status.matches_exit_status(VALGRIND_ERR) {
+    const VALGRIND_ERR: i32 = 100;
+    if proc_res.status.code() == Some(VALGRIND_ERR) {
         fatal_proc_rec("run-fail test isn't valgrind-clean!", &proc_res);
     }
 
@@ -139,10 +132,10 @@ fn run_rfail_test(config: &Config, props: &TestProps, testfile: &Path) {
 
 fn check_correct_failure_status(proc_res: &ProcRes) {
     // The value the rust runtime returns on failure
-    static RUST_ERR: int = 101;
-    if !proc_res.status.matches_exit_status(RUST_ERR) {
+    const RUST_ERR: i32 = 101;
+    if proc_res.status.code() != Some(RUST_ERR) {
         fatal_proc_rec(
-            &format!("failure produced the wrong error: {:?}",
+            &format!("failure produced the wrong error: {}",
                      proc_res.status),
             proc_res);
     }
@@ -201,8 +194,8 @@ fn run_pretty_test(config: &Config, props: &TestProps, testfile: &Path) {
     let rounds =
         match props.pp_exact { Some(_) => 1, None => 2 };
 
-    let src = File::open(testfile).read_to_end().unwrap();
-    let src = String::from_utf8(src.clone()).unwrap();
+    let mut src = String::new();
+    File::open(testfile).unwrap().read_to_string(&mut src).unwrap();
     let mut srcs = vec!(src);
 
     let mut round = 0;
@@ -226,9 +219,10 @@ fn run_pretty_test(config: &Config, props: &TestProps, testfile: &Path) {
 
     let mut expected = match props.pp_exact {
         Some(ref file) => {
-            let filepath = testfile.dir_path().join(file);
-            let s = File::open(&filepath).read_to_end().unwrap();
-            String::from_utf8(s).unwrap()
+            let filepath = testfile.parent().unwrap().join(file);
+            let mut s = String::new();
+            File::open(&filepath).unwrap().read_to_string(&mut s).unwrap();
+            s
         }
         None => { srcs[srcs.len() - 2].clone() }
     };
@@ -283,7 +277,7 @@ fn print_source(config: &Config,
                                      pretty_type.to_string()),
                         props.exec_env.clone(),
                         &config.compile_lib_path,
-                        Some(aux_dir.as_str().unwrap()),
+                        Some(aux_dir.to_str().unwrap()),
                         Some(src))
     }
 
@@ -299,11 +293,11 @@ fn make_pp_args(config: &Config,
                             pretty_type,
                             format!("--target={}", config.target),
                             "-L".to_string(),
-                            aux_dir.as_str().unwrap().to_string());
+                            aux_dir.to_str().unwrap().to_string());
         args.extend(split_maybe_args(&config.target_rustcflags).into_iter());
         args.extend(split_maybe_args(&props.compile_flags).into_iter());
         return ProcArgs {
-            prog: config.rustc_path.as_str().unwrap().to_string(),
+            prog: config.rustc_path.to_str().unwrap().to_string(),
             args: args,
         };
     }
@@ -345,14 +339,14 @@ fn make_typecheck_args(config: &Config, props: &TestProps, testfile: &Path) -> P
                             "--crate-type=lib".to_string(),
                             format!("--target={}", target),
                             "-L".to_string(),
-                            config.build_base.as_str().unwrap().to_string(),
+                            config.build_base.to_str().unwrap().to_string(),
                             "-L".to_string(),
-                            aux_dir.as_str().unwrap().to_string());
+                            aux_dir.to_str().unwrap().to_string());
         args.extend(split_maybe_args(&config.target_rustcflags).into_iter());
         args.extend(split_maybe_args(&props.compile_flags).into_iter());
         // FIXME (#9639): This needs to handle non-utf8 paths
         return ProcArgs {
-            prog: config.rustc_path.as_str().unwrap().to_string(),
+            prog: config.rustc_path.to_str().unwrap().to_string(),
             args: args,
         };
     }
@@ -390,18 +384,19 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
             // write debugger script
             let mut script_str = String::with_capacity(2048);
             script_str.push_str("set charset UTF-8\n");
-            script_str.push_str(&format!("file {}\n", exe_file.as_str().unwrap()));
+            script_str.push_str(&format!("file {}\n", exe_file.to_str().unwrap()));
             script_str.push_str("target remote :5039\n");
             script_str.push_str(&format!("set solib-search-path \
                                          ./{}/stage2/lib/rustlib/{}/lib/\n",
                                          config.host, config.target));
             for line in breakpoint_lines.iter() {
                 script_str.push_str(&format!("break {:?}:{}\n",
-                                             testfile.filename_display(),
+                                             testfile.file_name().unwrap()
+                                                     .to_string_lossy(),
                                              *line)[..]);
             }
             script_str.push_str(&cmds);
-            script_str.push_str("quit\n");
+            script_str.push_str("\nquit\n");
 
             debug!("script_str = {}", script_str);
             dump_output_file(config,
@@ -415,7 +410,7 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
                          None,
                          &[
                             "push".to_string(),
-                            exe_file.as_str().unwrap().to_string(),
+                            exe_file.to_str().unwrap().to_string(),
                             config.adb_test_dir.clone()
                          ],
                          vec!(("".to_string(), "".to_string())),
@@ -440,9 +435,8 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
                                   if config.target.contains("aarch64")
                                   {"64"} else {""},
                                   config.adb_test_dir.clone(),
-                                  str::from_utf8(
-                                      exe_file.filename()
-                                      .unwrap()).unwrap());
+                                  exe_file.file_name().unwrap().to_str()
+                                          .unwrap());
 
             let mut process = procsrv::run_background("",
                                                       &config.adb_path
@@ -459,16 +453,12 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
             loop {
                 //waiting 1 second for gdbserver start
                 timer::sleep(Duration::milliseconds(1000));
-                let result = thread::spawn(move || {
-                    tcp::TcpStream::connect("127.0.0.1:5039").unwrap();
-                }).join();
-                if result.is_err() {
-                    continue;
+                if TcpStream::connect("127.0.0.1:5039").is_ok() {
+                    break
                 }
-                break;
             }
 
-            let tool_path = match config.android_cross_path.as_str() {
+            let tool_path = match config.android_cross_path.to_str() {
                 Some(x) => x.to_string(),
                 None => fatal("cannot find android cross path")
             };
@@ -479,7 +469,7 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
                 vec!("-quiet".to_string(),
                      "-batch".to_string(),
                      "-nx".to_string(),
-                     format!("-command={}", debugger_script.as_str().unwrap()));
+                     format!("-command={}", debugger_script.to_str().unwrap()));
 
             let mut gdb_path = tool_path;
             gdb_path.push_str(&format!("/bin/{}-gdb", config.target));
@@ -503,12 +493,12 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
             };
 
             debugger_run_result = ProcRes {
-                status: status,
+                status: Status::Normal(status),
                 stdout: out,
                 stderr: err,
                 cmdline: cmdline
             };
-            if process.signal_kill().is_err() {
+            if process.kill().is_err() {
                 println!("Adb process is already finished.");
             }
         }
@@ -518,7 +508,7 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
                 .expect("Could not find Rust source root");
             let rust_pp_module_rel_path = Path::new("./src/etc");
             let rust_pp_module_abs_path = rust_src_root.join(rust_pp_module_rel_path)
-                                                       .as_str()
+                                                       .to_str()
                                                        .unwrap()
                                                        .to_string();
             // write debugger script
@@ -538,7 +528,7 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
                         // GDB's script auto loading safe path
                         script_str.push_str(
                             &format!("add-auto-load-safe-path {}\n",
-                                     rust_pp_module_abs_path.replace("\\", "\\\\"))
+                                     rust_pp_module_abs_path.replace(r"\", r"\\"))
                                 );
                     }
                 }
@@ -553,21 +543,24 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
             script_str.push_str("set print pretty off\n");
 
             // Add the pretty printer directory to GDB's source-file search path
-            script_str.push_str(&format!("directory {}\n", rust_pp_module_abs_path)[..]);
+            script_str.push_str(&format!("directory {}\n",
+                                         rust_pp_module_abs_path));
 
             // Load the target executable
             script_str.push_str(&format!("file {}\n",
-                                         exe_file.as_str().unwrap().replace("\\", "\\\\"))[..]);
+                                         exe_file.to_str().unwrap()
+                                                 .replace(r"\", r"\\")));
 
             // Add line breakpoints
             for line in &breakpoint_lines {
                 script_str.push_str(&format!("break '{}':{}\n",
-                                             testfile.filename_display(),
-                                             *line)[..]);
+                                             testfile.file_name().unwrap()
+                                                     .to_string_lossy(),
+                                             *line));
             }
 
             script_str.push_str(&cmds);
-            script_str.push_str("quit\n");
+            script_str.push_str("\nquit\n");
 
             debug!("script_str = {}", script_str);
             dump_output_file(config,
@@ -576,13 +569,8 @@ fn run_debuginfo_gdb_test(config: &Config, props: &TestProps, testfile: &Path) {
                              "debugger.script");
 
             // run debugger script with gdb
-            #[cfg(windows)]
-            fn debugger() -> String {
-                "gdb.exe".to_string()
-            }
-            #[cfg(unix)]
-            fn debugger() -> String {
-                "gdb".to_string()
+            fn debugger() -> &'static str {
+                if cfg!(windows) {"gdb.exe"} else {"gdb"}
             }
 
             let debugger_script = make_out_name(config, testfile, "debugger.script");
@@ -592,10 +580,10 @@ fn debugger() -> String {
                 vec!("-quiet".to_string(),
                      "-batch".to_string(),
                      "-nx".to_string(),
-                     format!("-command={}", debugger_script.as_str().unwrap()));
+                     format!("-command={}", debugger_script.to_str().unwrap()));
 
             let proc_args = ProcArgs {
-                prog: debugger(),
+                prog: debugger().to_string(),
                 args: debugger_opts,
             };
 
@@ -618,7 +606,7 @@ fn debugger() -> String {
     check_debugger_output(&debugger_run_result, &check_lines);
 }
 
-fn find_rust_src_root(config: &Config) -> Option<Path> {
+fn find_rust_src_root(config: &Config) -> Option<PathBuf> {
     let mut path = config.src_base.clone();
     let path_postfix = Path::new("src/etc/lldb_batchmode.py");
 
@@ -632,8 +620,6 @@ fn find_rust_src_root(config: &Config) -> Option<Path> {
 }
 
 fn run_debuginfo_lldb_test(config: &Config, props: &TestProps, testfile: &Path) {
-    use std::old_io::process::{Command, ProcessOutput};
-
     if config.lldb_python_dir.is_none() {
         fatal("Can't run LLDB test because LLDB's python path is not set.");
     }
@@ -685,11 +671,12 @@ fn run_debuginfo_lldb_test(config: &Config, props: &TestProps, testfile: &Path)
         .expect("Could not find Rust source root");
     let rust_pp_module_rel_path = Path::new("./src/etc/lldb_rust_formatters.py");
     let rust_pp_module_abs_path = rust_src_root.join(rust_pp_module_rel_path)
-                                               .as_str()
+                                               .to_str()
                                                .unwrap()
                                                .to_string();
 
-    script_str.push_str(&format!("command script import {}\n", &rust_pp_module_abs_path[..])[..]);
+    script_str.push_str(&format!("command script import {}\n",
+                                 &rust_pp_module_abs_path[..])[..]);
     script_str.push_str("type summary add --no-value ");
     script_str.push_str("--python-function lldb_rust_formatters.print_val ");
     script_str.push_str("-x \".*\" --category Rust\n");
@@ -707,7 +694,7 @@ fn run_debuginfo_lldb_test(config: &Config, props: &TestProps, testfile: &Path)
     }
 
     // Finally, quit the debugger
-    script_str.push_str("quit\n");
+    script_str.push_str("\nquit\n");
 
     // Write the script into a file
     debug!("script_str = {}", script_str);
@@ -735,22 +722,19 @@ fn run_lldb(config: &Config,
                 rust_src_root: &Path)
                 -> ProcRes {
         // Prepare the lldb_batchmode which executes the debugger script
-        let lldb_script_path = rust_src_root.join(Path::new("./src/etc/lldb_batchmode.py"));
+        let lldb_script_path = rust_src_root.join("src/etc/lldb_batchmode.py");
 
         let mut cmd = Command::new("python");
-        cmd.arg(lldb_script_path)
+        cmd.arg(&lldb_script_path)
            .arg(test_executable)
            .arg(debugger_script)
-           .env_set_all(&[("PYTHONPATH", config.lldb_python_dir.clone().unwrap())]);
-
-        let (status, out, err) = match cmd.spawn() {
-            Ok(process) => {
-                let ProcessOutput { status, output, error } =
-                    process.wait_with_output().unwrap();
+           .env("PYTHONPATH", config.lldb_python_dir.as_ref().unwrap());
 
+        let (status, out, err) = match cmd.output() {
+            Ok(Output { status, stdout, stderr }) => {
                 (status,
-                 String::from_utf8(output).unwrap(),
-                 String::from_utf8(error).unwrap())
+                 String::from_utf8(stdout).unwrap(),
+                 String::from_utf8(stderr).unwrap())
             },
             Err(e) => {
                 fatal(&format!("Failed to setup Python process for \
@@ -760,7 +744,7 @@ fn run_lldb(config: &Config,
 
         dump_output(config, test_executable, &out, &err);
         return ProcRes {
-            status: status,
+            status: Status::Normal(status),
             stdout: out,
             stderr: err,
             cmdline: format!("{:?}", cmd)
@@ -776,8 +760,6 @@ struct DebuggerCommands {
 
 fn parse_debugger_commands(file_path: &Path, debugger_prefix: &str)
                            -> DebuggerCommands {
-    use std::old_io::{BufferedReader, File};
-
     let command_directive = format!("{}-command", debugger_prefix);
     let check_directive = format!("{}-check", debugger_prefix);
 
@@ -785,7 +767,7 @@ fn parse_debugger_commands(file_path: &Path, debugger_prefix: &str)
     let mut commands = vec!();
     let mut check_lines = vec!();
     let mut counter = 1;
-    let mut reader = BufferedReader::new(File::open(file_path).unwrap());
+    let reader = BufReader::new(File::open(file_path).unwrap());
     for line in reader.lines() {
         match line {
             Ok(line) => {
@@ -963,16 +945,17 @@ fn check_expected_errors(expected_errors: Vec<errors::ExpectedError> ,
 
     let prefixes = expected_errors.iter().map(|ee| {
         format!("{}:{}:", testfile.display(), ee.line)
-    }).collect::<Vec<String> >();
-
-    #[cfg(windows)]
-    fn prefix_matches( line : &str, prefix : &str ) -> bool {
-        line.to_ascii_lowercase().starts_with(&prefix.to_ascii_lowercase())
-    }
-
-    #[cfg(unix)]
-    fn prefix_matches( line : &str, prefix : &str ) -> bool {
-        line.starts_with( prefix )
+    }).collect::<Vec<String>>();
+
+    fn prefix_matches(line: &str, prefix: &str) -> bool {
+        use std::ascii::AsciiExt;
+        // On windows just translate all '\' path separators to '/'
+        let line = line.replace(r"\", "/");
+        if cfg!(windows) {
+            line.to_ascii_lowercase().starts_with(&prefix.to_ascii_lowercase())
+        } else {
+            line.starts_with(prefix)
+        }
     }
 
     // A multi-line error will have followup lines which will always
@@ -1113,12 +1096,42 @@ struct ProcArgs {
 }
 
 struct ProcRes {
-    status: ProcessExit,
+    status: Status,
     stdout: String,
     stderr: String,
     cmdline: String,
 }
 
+enum Status {
+    Parsed(i32),
+    Normal(ExitStatus),
+}
+
+impl Status {
+    fn code(&self) -> Option<i32> {
+        match *self {
+            Status::Parsed(i) => Some(i),
+            Status::Normal(ref e) => e.code(),
+        }
+    }
+
+    fn success(&self) -> bool {
+        match *self {
+            Status::Parsed(i) => i == 0,
+            Status::Normal(ref e) => e.success(),
+        }
+    }
+}
+
+impl fmt::Display for Status {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        match *self {
+            Status::Parsed(i) => write!(f, "exit code: {}", i),
+            Status::Normal(ref e) => e.fmt(f),
+        }
+    }
+}
+
 fn compile_test(config: &Config, props: &TestProps,
                 testfile: &Path) -> ProcRes {
     compile_test_(config, props, testfile, &[])
@@ -1133,7 +1146,7 @@ fn compile_test_(config: &Config, props: &TestProps,
     let aux_dir = aux_output_dir_name(config, testfile);
     // FIXME (#9639): This needs to handle non-utf8 paths
     let mut link_args = vec!("-L".to_string(),
-                             aux_dir.as_str().unwrap().to_string());
+                             aux_dir.to_str().unwrap().to_string());
     link_args.extend(extra_args.iter().cloned());
     let args = make_compile_args(config,
                                  props,
@@ -1160,7 +1173,7 @@ fn exec_compiled_test(config: &Config, props: &TestProps,
                             make_run_args(config, props, testfile),
                             env,
                             &config.run_lib_path,
-                            Some(aux_dir.as_str().unwrap()),
+                            Some(aux_dir.to_str().unwrap()),
                             None)
         }
     }
@@ -1179,7 +1192,7 @@ fn compose_and_run_compiler(
 
     let aux_dir = aux_output_dir_name(config, testfile);
     // FIXME (#9639): This needs to handle non-utf8 paths
-    let extra_link_args = vec!("-L".to_string(), aux_dir.as_str().unwrap().to_string());
+    let extra_link_args = vec!("-L".to_string(), aux_dir.to_str().unwrap().to_string());
 
     for rel_ab in &props.aux_builds {
         let abs_ab = config.aux_base.join(rel_ab);
@@ -1196,7 +1209,8 @@ fn compose_and_run_compiler(
                               crate_type,
                               |a,b| {
                                   let f = make_lib_name(a, b, testfile);
-                                  TargetLocation::ThisDirectory(f.dir_path())
+                                  let parent = f.parent().unwrap();
+                                  TargetLocation::ThisDirectory(parent.to_path_buf())
                               },
                               &abs_ab);
         let auxres = compose_and_run(config,
@@ -1204,7 +1218,7 @@ fn compose_and_run_compiler(
                                      aux_args,
                                      Vec::new(),
                                      &config.compile_lib_path,
-                                     Some(aux_dir.as_str().unwrap()),
+                                     Some(aux_dir.to_str().unwrap()),
                                      None);
         if !auxres.status.success() {
             fatal_proc_rec(
@@ -1226,13 +1240,13 @@ fn compose_and_run_compiler(
                     args,
                     Vec::new(),
                     &config.compile_lib_path,
-                    Some(aux_dir.as_str().unwrap()),
+                    Some(aux_dir.to_str().unwrap()),
                     input)
 }
 
 fn ensure_dir(path: &Path) {
     if path.is_dir() { return; }
-    fs::mkdir(path, old_io::USER_RWX).unwrap();
+    fs::create_dir(path).unwrap();
 }
 
 fn compose_and_run(config: &Config, testfile: &Path,
@@ -1246,8 +1260,8 @@ fn compose_and_run(config: &Config, testfile: &Path,
 }
 
 enum TargetLocation {
-    ThisFile(Path),
-    ThisDirectory(Path),
+    ThisFile(PathBuf),
+    ThisDirectory(PathBuf),
 }
 
 fn make_compile_args<F>(config: &Config,
@@ -1265,9 +1279,9 @@ fn make_compile_args<F>(config: &Config,
         &*config.target
     };
     // FIXME (#9639): This needs to handle non-utf8 paths
-    let mut args = vec!(testfile.as_str().unwrap().to_string(),
+    let mut args = vec!(testfile.to_str().unwrap().to_string(),
                         "-L".to_string(),
-                        config.build_base.as_str().unwrap().to_string(),
+                        config.build_base.to_str().unwrap().to_string(),
                         format!("--target={}", target));
     args.push_all(&extras);
     if !props.no_prefer_dynamic {
@@ -1284,7 +1298,7 @@ fn make_compile_args<F>(config: &Config,
             path
         }
     };
-    args.push(path.as_str().unwrap().to_string());
+    args.push(path.to_str().unwrap().to_string());
     if props.force_host {
         args.extend(split_maybe_args(&config.host_rustcflags).into_iter());
     } else {
@@ -1292,24 +1306,24 @@ fn make_compile_args<F>(config: &Config,
     }
     args.extend(split_maybe_args(&props.compile_flags).into_iter());
     return ProcArgs {
-        prog: config.rustc_path.as_str().unwrap().to_string(),
+        prog: config.rustc_path.to_str().unwrap().to_string(),
         args: args,
     };
 }
 
-fn make_lib_name(config: &Config, auxfile: &Path, testfile: &Path) -> Path {
+fn make_lib_name(config: &Config, auxfile: &Path, testfile: &Path) -> PathBuf {
     // what we return here is not particularly important, as it
     // happens; rustc ignores everything except for the directory.
     let auxname = output_testname(auxfile);
     aux_output_dir_name(config, testfile).join(&auxname)
 }
 
-fn make_exe_name(config: &Config, testfile: &Path) -> Path {
+fn make_exe_name(config: &Config, testfile: &Path) -> PathBuf {
     let mut f = output_base_name(config, testfile);
     if !env::consts::EXE_SUFFIX.is_empty() {
-        let mut fname = f.filename().unwrap().to_vec();
-        fname.extend(env::consts::EXE_SUFFIX.bytes());
-        f.set_filename(fname);
+        let mut fname = f.file_name().unwrap().to_os_string();
+        fname.push(env::consts::EXE_SUFFIX);
+        f.set_file_name(&fname);
     }
     f
 }
@@ -1322,7 +1336,7 @@ fn make_run_args(config: &Config, props: &TestProps, testfile: &Path) ->
     let exe_file = make_exe_name(config, testfile);
 
     // FIXME (#9639): This needs to handle non-utf8 paths
-    args.push(exe_file.as_str().unwrap().to_string());
+    args.push(exe_file.to_str().unwrap().to_string());
 
     // Add the arguments in the run_flags directive
     args.extend(split_maybe_args(&props.run_flags).into_iter());
@@ -1375,29 +1389,28 @@ fn program_output(config: &Config, testfile: &Path, lib_path: &str, prog: String
                      input).expect(&format!("failed to exec `{}`", prog));
     dump_output(config, testfile, &out, &err);
     return ProcRes {
-        status: status,
+        status: Status::Normal(status),
         stdout: out,
         stderr: err,
         cmdline: cmdline,
     };
 }
 
-// Linux and mac don't require adjusting the library search path
-#[cfg(unix)]
-fn make_cmdline(_libpath: &str, prog: &str, args: &[String]) -> String {
-    format!("{} {}", prog, args.connect(" "))
-}
-
-#[cfg(windows)]
 fn make_cmdline(libpath: &str, prog: &str, args: &[String]) -> String {
+    use util;
 
-    // Build the LD_LIBRARY_PATH variable as it would be seen on the command line
-    // for diagnostic purposes
-    fn lib_path_cmd_prefix(path: &str) -> String {
-        format!("{}=\"{}\"", util::lib_path_env_var(), util::make_new_path(path))
-    }
+    // Linux and mac don't require adjusting the library search path
+    if cfg!(unix) {
+        format!("{} {}", prog, args.connect(" "))
+    } else {
+        // Build the LD_LIBRARY_PATH variable as it would be seen on the command line
+        // for diagnostic purposes
+        fn lib_path_cmd_prefix(path: &str) -> String {
+            format!("{}=\"{}\"", util::lib_path_env_var(), util::make_new_path(path))
+        }
 
-    format!("{} {} {}", lib_path_cmd_prefix(libpath), prog, args.connect(" "))
+        format!("{} {} {}", lib_path_cmd_prefix(libpath), prog, args.connect(" "))
+    }
 }
 
 fn dump_output(config: &Config, testfile: &Path, out: &str, err: &str) {
@@ -1409,25 +1422,25 @@ fn dump_output(config: &Config, testfile: &Path, out: &str, err: &str) {
 fn dump_output_file(config: &Config, testfile: &Path,
                     out: &str, extension: &str) {
     let outfile = make_out_name(config, testfile, extension);
-    File::create(&outfile).write_all(out.as_bytes()).unwrap();
+    File::create(&outfile).unwrap().write_all(out.as_bytes()).unwrap();
 }
 
-fn make_out_name(config: &Config, testfile: &Path, extension: &str) -> Path {
+fn make_out_name(config: &Config, testfile: &Path, extension: &str) -> PathBuf {
     output_base_name(config, testfile).with_extension(extension)
 }
 
-fn aux_output_dir_name(config: &Config, testfile: &Path) -> Path {
+fn aux_output_dir_name(config: &Config, testfile: &Path) -> PathBuf {
     let f = output_base_name(config, testfile);
-    let mut fname = f.filename().unwrap().to_vec();
-    fname.extend("libaux".bytes());
-    f.with_filename(fname)
+    let mut fname = f.file_name().unwrap().to_os_string();
+    fname.push("libaux");
+    f.with_file_name(&fname)
 }
 
-fn output_testname(testfile: &Path) -> Path {
-    Path::new(testfile.filestem().unwrap())
+fn output_testname(testfile: &Path) -> PathBuf {
+    PathBuf::new(testfile.file_stem().unwrap())
 }
 
-fn output_base_name(config: &Config, testfile: &Path) -> Path {
+fn output_base_name(config: &Config, testfile: &Path) -> PathBuf {
     config.build_base
         .join(&output_testname(testfile))
         .with_extension(&config.stage_id)
@@ -1542,11 +1555,11 @@ fn _arm_exec_compiled_test(config: &Config,
                      Some("".to_string()))
         .expect(&format!("failed to exec `{}`", config.adb_path));
 
-    let mut exitcode: int = 0;
+    let mut exitcode: i32 = 0;
     for c in exitcode_out.chars() {
         if !c.is_numeric() { break; }
         exitcode = exitcode * 10 + match c {
-            '0' ... '9' => c as int - ('0' as int),
+            '0' ... '9' => c as i32 - ('0' as i32),
             _ => 101,
         }
     }
@@ -1587,7 +1600,7 @@ fn _arm_exec_compiled_test(config: &Config,
                 &stderr_out);
 
     ProcRes {
-        status: process::ProcessExit::ExitStatus(exitcode),
+        status: Status::Parsed(exitcode),
         stdout: stdout_out,
         stderr: stderr_out,
         cmdline: cmdline
@@ -1597,16 +1610,17 @@ fn _arm_exec_compiled_test(config: &Config,
 fn _arm_push_aux_shared_library(config: &Config, testfile: &Path) {
     let tdir = aux_output_dir_name(config, testfile);
 
-    let dirs = fs::readdir(&tdir).unwrap();
-    for file in &dirs {
-        if file.extension_str() == Some("so") {
+    let dirs = fs::read_dir(&tdir).unwrap();
+    for file in dirs {
+        let file = file.unwrap().path();
+        if file.extension().and_then(|s| s.to_str()) == Some("so") {
             // FIXME (#9639): This needs to handle non-utf8 paths
             let copy_result = procsrv::run("",
                                            &config.adb_path,
                                            None,
                                            &[
                                             "push".to_string(),
-                                            file.as_str()
+                                            file.to_str()
                                                 .unwrap()
                                                 .to_string(),
                                             config.adb_test_dir.to_string(),
@@ -1627,14 +1641,14 @@ fn _arm_push_aux_shared_library(config: &Config, testfile: &Path) {
 
 // codegen tests (vs. clang)
 
-fn append_suffix_to_stem(p: &Path, suffix: &str) -> Path {
+fn append_suffix_to_stem(p: &Path, suffix: &str) -> PathBuf {
     if suffix.len() == 0 {
-        (*p).clone()
+        p.to_path_buf()
     } else {
-        let mut stem = p.filestem().unwrap().to_vec();
-        stem.extend("-".bytes());
-        stem.extend(suffix.bytes());
-        p.with_filename(stem)
+        let mut stem = p.file_stem().unwrap().to_os_string();
+        stem.push("-");
+        stem.push(suffix);
+        p.with_file_name(&stem)
     }
 }
 
@@ -1643,7 +1657,7 @@ fn compile_test_and_save_bitcode(config: &Config, props: &TestProps,
     let aux_dir = aux_output_dir_name(config, testfile);
     // FIXME (#9639): This needs to handle non-utf8 paths
     let mut link_args = vec!("-L".to_string(),
-                             aux_dir.as_str().unwrap().to_string());
+                             aux_dir.to_str().unwrap().to_string());
     let llvm_args = vec!("--emit=llvm-bc,obj".to_string(),
                          "--crate-type=lib".to_string());
     link_args.extend(llvm_args.into_iter());
@@ -1651,7 +1665,8 @@ fn compile_test_and_save_bitcode(config: &Config, props: &TestProps,
                                  props,
                                  link_args,
                                  |a, b| TargetLocation::ThisDirectory(
-                                     output_base_name(a, b).dir_path()),
+                                     output_base_name(a, b).parent()
+                                        .unwrap().to_path_buf()),
                                  testfile);
     compose_and_run_compiler(config, props, testfile, args, None)
 }
@@ -1663,12 +1678,12 @@ fn compile_cc_with_clang_and_save_bitcode(config: &Config, _props: &TestProps,
     let testcc = testfile.with_extension("cc");
     let proc_args = ProcArgs {
         // FIXME (#9639): This needs to handle non-utf8 paths
-        prog: config.clang_path.as_ref().unwrap().as_str().unwrap().to_string(),
+        prog: config.clang_path.as_ref().unwrap().to_str().unwrap().to_string(),
         args: vec!("-c".to_string(),
                    "-emit-llvm".to_string(),
                    "-o".to_string(),
-                   bitcodefile.as_str().unwrap().to_string(),
-                   testcc.as_str().unwrap().to_string())
+                   bitcodefile.to_str().unwrap().to_string(),
+                   testcc.to_str().unwrap().to_string())
     };
     compose_and_run(config, testfile, proc_args, Vec::new(), "", None, None)
 }
@@ -1682,10 +1697,10 @@ fn extract_function_from_bitcode(config: &Config, _props: &TestProps,
     let prog = config.llvm_bin_path.as_ref().unwrap().join("llvm-extract");
     let proc_args = ProcArgs {
         // FIXME (#9639): This needs to handle non-utf8 paths
-        prog: prog.as_str().unwrap().to_string(),
+        prog: prog.to_str().unwrap().to_string(),
         args: vec!(format!("-func={}", fname),
-                   format!("-o={}", extracted_bc.as_str().unwrap()),
-                   bitcodefile.as_str().unwrap().to_string())
+                   format!("-o={}", extracted_bc.to_str().unwrap()),
+                   bitcodefile.to_str().unwrap().to_string())
     };
     compose_and_run(config, testfile, proc_args, Vec::new(), "", None, None)
 }
@@ -1699,16 +1714,17 @@ fn disassemble_extract(config: &Config, _props: &TestProps,
     let prog = config.llvm_bin_path.as_ref().unwrap().join("llvm-dis");
     let proc_args = ProcArgs {
         // FIXME (#9639): This needs to handle non-utf8 paths
-        prog: prog.as_str().unwrap().to_string(),
-        args: vec!(format!("-o={}", extracted_ll.as_str().unwrap()),
-                   extracted_bc.as_str().unwrap().to_string())
+        prog: prog.to_str().unwrap().to_string(),
+        args: vec!(format!("-o={}", extracted_ll.to_str().unwrap()),
+                   extracted_bc.to_str().unwrap().to_string())
     };
     compose_and_run(config, testfile, proc_args, Vec::new(), "", None, None)
 }
 
 
 fn count_extracted_lines(p: &Path) -> uint {
-    let x = File::open(&p.with_extension("ll")).read_to_end().unwrap();
+    let mut x = Vec::new();
+    File::open(&p.with_extension("ll")).unwrap().read_to_end(&mut x).unwrap();
     let x = str::from_utf8(&x).unwrap();
     x.lines().count()
 }
index 778629dd2028f53ed838dd533198e2705045c358..16e2806f72cecd2bdeef69af472fda23e4798311 100644 (file)
@@ -8,13 +8,11 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-use common::Config;
-
-#[cfg(target_os = "windows")]
 use std::env;
+use common::Config;
 
 /// Conversion table from triple OS name to Rust SYSNAME
-static OS_TABLE: &'static [(&'static str, &'static str)] = &[
+const OS_TABLE: &'static [(&'static str, &'static str)] = &[
     ("mingw32", "windows"),
     ("win32", "windows"),
     ("windows", "windows"),
@@ -36,24 +34,20 @@ pub fn get_os(triple: &str) -> &'static str {
     panic!("Cannot determine OS from triple");
 }
 
-#[cfg(target_os = "windows")]
 pub fn make_new_path(path: &str) -> String {
-
+    assert!(cfg!(windows));
     // Windows just uses PATH as the library search path, so we have to
     // maintain the current value while adding our own
     match env::var(lib_path_env_var()) {
-      Ok(curr) => {
-        format!("{}{}{}", path, path_div(), curr)
-      }
-      Err(..) => path.to_string()
+        Ok(curr) => {
+            format!("{}{}{}", path, path_div(), curr)
+        }
+        Err(..) => path.to_string()
     }
 }
 
-#[cfg(target_os = "windows")]
 pub fn lib_path_env_var() -> &'static str { "PATH" }
-
-#[cfg(target_os = "windows")]
-pub fn path_div() -> &'static str { ";" }
+fn path_div() -> &'static str { ";" }
 
 pub fn logv(config: &Config, s: String) {
     debug!("{}", s);
index e57953db3a256fd2463ad6a04d3015dccd830c96..3edbcbe62c51172ea225fa122e62add202f9657b 100644 (file)
@@ -174,3 +174,10 @@ bindings.
 See also [a long thread][alt] on renaming `let mut` to `var`.
 
 [alt]: https://mail.mozilla.org/pipermail/rust-dev/2014-January/008319.html
+
+## Why no `--x` or `x++`?
+
+Preincrement and postincrement, while convenient, are also fairly complex. They
+require knowledge of evaluation order, and often lead to subtle bugs and
+undefined behavior in C and C++. `x = x + 1` or `x += 1` is only slightly
+longer, but unambiguous.
index d7a29ea530952a4f28a934c0834fce2558f7e845..68ca1cb72170ad1b7507da0bb78fc0b30ee7925a 100644 (file)
@@ -514,7 +514,7 @@ field_expr : expr '.' ident ;
 ### Array expressions
 
 ```antlr
-array_expr : '[' "mut" ? vec_elems? ']' ;
+array_expr : '[' "mut" ? array_elems? ']' ;
 
 array_elems : [expr [',' expr]*] | [expr ',' ".." expr] ;
 ```
index 197559bef0408564d13f90ee1e6cc008d09d5b24..21217bf54d7693e50a4777601536f2fca935edc0 100644 (file)
@@ -1,4 +1,4 @@
 % The (old) Rust Threads and Communication Guide
 
 This content has moved into
-[the Rust Programming Language book](book/tasks.html).
+[the Rust Programming Language book](book/concurrency.html).
index 07a90959deb693b30fbf629a50d950c9c52cc03c..9e575abeee2173d415e7064599c89f30c86614d6 100644 (file)
@@ -389,11 +389,11 @@ safe concurrent programs.
 Here's an example of a concurrent Rust program:
 
 ```{rust}
-use std::thread::Thread;
+use std::thread;
 
 fn main() {
     let guards: Vec<_> = (0..10).map(|_| {
-        Thread::scoped(|| {
+        thread::scoped(|| {
             println!("Hello, world!");
         })
     }).collect();
@@ -421,15 +421,16 @@ problem.
 Let's see an example. This Rust code will not compile:
 
 ```{rust,ignore}
-use std::thread::Thread;
+use std::thread;
 
 fn main() {
     let mut numbers = vec![1, 2, 3];
 
     let guards: Vec<_> = (0..3).map(|i| {
-        Thread::scoped(move || {
-            for j in 0..3 { numbers[j] += 1 }
-        });
+        thread::scoped(move || {
+            numbers[i] += 1;
+            println!("numbers[{}] is {}", i, numbers[i]);
+        })
     }).collect();
 }
 ```
@@ -437,10 +438,12 @@ fn main() {
 It gives us this error:
 
 ```text
-7:29: 9:10 error: cannot move out of captured outer variable in an `FnMut` closure
-7         Thread::scoped(move || {
-8             for j in 0..3 { numbers[j] += 1 }
-9         });
+7:25: 10:6 error: cannot move out of captured outer variable in an `FnMut` closure
+7     thread::scoped(move || {
+8       numbers[i] += 1;
+9       println!("numbers[{}] is {}", i, numbers[i]);
+10     })
+error: aborting due to previous error
 ```
 
 It mentions that "captured outer variable in an `FnMut` closure".
@@ -468,7 +471,7 @@ mutation doesn't cause a data race.
 Here's what using an Arc with a Mutex looks like:
 
 ```{rust}
-use std::thread::Thread;
+use std::thread;
 use std::sync::{Arc,Mutex};
 
 fn main() {
@@ -476,11 +479,11 @@ fn main() {
 
     let guards: Vec<_> = (0..3).map(|i| {
         let number = numbers.clone();
-        Thread::scoped(move || {
+        thread::scoped(move || {
             let mut array = number.lock().unwrap();
             array[i] += 1;
             println!("numbers[{}] is {}", i, array[i]);
-        });
+        })
     }).collect();
 }
 ```
@@ -510,10 +513,10 @@ numbers[1] is 3
 numbers[0] is 2
 ```
 
-Each time, we can get a slithtly different output because the threads
-are not quaranteed to run in any set order. If you get the same order
-every time it is because each of these threads are very small and
-complete too fast for their indeterminate behavior to surface.
+Each time, we can get a slightly different output because the threads are not
+guaranteed to run in any set order. If you get the same order every time it is
+because each of these threads are very small and complete too fast for their
+indeterminate behavior to surface.
 
 The important part here is that the Rust compiler was able to use ownership to
 give us assurance _at compile time_ that we weren't doing something incorrect
@@ -532,15 +535,15 @@ As an example, Rust's ownership system is _entirely_ at compile time. The
 safety check that makes this an error about moved values:
 
 ```{rust,ignore}
-use std::thread::Thread;
+use std::thread;
 
 fn main() {
     let numbers = vec![1, 2, 3];
 
     let guards: Vec<_> = (0..3).map(|i| {
-        Thread::scoped(move || {
+        thread::scoped(move || {
             println!("{}", numbers[i]);
-        });
+        })
     }).collect();
 }
 ```
index 2f047d2c173f82a5d23b93f4cc2c11624f219644..4f5f2a631adef5ba8e27c8858f72e861b2572f05 100644 (file)
@@ -229,14 +229,14 @@ cases mentioned in [Number literals](#number-literals) below.
 
 ##### Characters and strings
 
-|   | Example | Number of `#` pairs allowed | Available characters | Escapes | Equivalent to |
-|---|---------|-----------------------------|----------------------|---------|---------------|
-| [Character](#character-literals) | `'H'` | `N/A` | All unicode | `\'` & [Byte escapes](#byte-escapes) & [Unicode escapes](#unicode-escapes) | `N/A` |
-| [String](#string-literals) | `"hello"` | `N/A` | All unicode | `\"` & [Byte escapes](#byte-escapes) & [Unicode escapes](#unicode-escapes) | `N/A` |
-| [Raw](#raw-string-literals) | `r##"hello"##`  | `0...` | All unicode | `N/A` | `N/A` |
-| [Byte](#byte-literals) | `b'H'` | `N/A` | All ASCII | `\'` & [Byte escapes](#byte-escapes) | `u8` |
-| [Byte string](#byte-string-literals) | `b"hello"` | `N/A`  | All ASCII | `\"` & [Byte escapes](#byte-escapes) | `&'static [u8]` |
-| [Raw byte string](#raw-byte-string-literals) | `br##"hello"##` | `0...` | All ASCII | `N/A` | `&'static [u8]` (unsure...not stated) |
+|                                              | Example       | # sets | Characters  | Escapes             |
+|----------------------------------------------|---------------|--------|-------------|---------------------|
+| [Character](#character-literals)             | 'H'           | N/A    | All Unicode | \' & [Byte](#byte-escapes) & [Unicode](#unicode-escapes) |
+| [String](#string-literals)                   | "hello"       | N/A    | All Unicode | \" & [Byte](#byte-escapes) & [Unicode](#unicode-escapes) |
+| [Raw](#raw-string-literals)                  | r#"hello"#    | 0...   | All Unicode | N/A                                                      |
+| [Byte](#byte-literals)                       | b'H'          | N/A    | All ASCII   | \' & [Byte](#byte-escapes)                               |
+| [Byte string](#byte-string-literals)         | b"hello"      | N/A    | All ASCII   | \" & [Byte](#byte-escapes)                               |
+| [Raw byte string](#raw-byte-string-literals) | br#"hello"#   | 0...   | All ASCII   | N/A                                                      |
 
 ##### Byte escapes
 
@@ -764,7 +764,15 @@ usually in [procedural macros](book/plugins.html#syntax-extensions):
 * `quote_pat!`
 * `quote_stmt!`
 * `quote_tokens!`
+* `quote_matcher!`
 * `quote_ty!`
+* `quote_attr!`
+
+Keep in mind that when `$name : ident` appears in the input to
+`quote_tokens!`, the result contains unquoted `name` followed by two tokens.
+However, input of the same form passed to `quote_matcher!` becomes a
+quasiquoted MBE-matcher of a nonterminal. No unquotation happens. Otherwise
+the result of `quote_matcher!` is identical to that of `quote_tokens!`.
 
 Documentation is very limited at the moment.
 
@@ -2421,6 +2429,10 @@ The currently implemented features of the reference compiler are:
                        so that new attributes can be added in a bacwards compatible
                        manner (RFC 572).
 
+* `custom_derive` - Allows the use of `#[derive(Foo,Bar)]` as sugar for
+                    `#[derive_Foo] #[derive_Bar]`, which can be user-defined syntax
+                    extensions.
+
 * `intrinsics` - Allows use of the "rust-intrinsics" ABI. Compiler intrinsics
                  are inherently unstable and no promise about them is made.
 
@@ -2495,6 +2507,12 @@ The currently implemented features of the reference compiler are:
 
 * `staged_api` - Allows usage of stability markers and `#![staged_api]` in a crate
 
+* `static_assert` - The `#[static_assert]` functionality is experimental and
+                    unstable. The attribute can be attached to a `static` of
+                    type `bool` and the compiler will error if the `bool` is
+                    `false` at compile time. This version of this functionality
+                    is unintuitive and suboptimal.
+
 * `start` - Allows use of the `#[start]` attribute, which changes the entry point
             into a Rust program. This capabiilty, especially the signature for the
             annotated function, is subject to change.
@@ -2541,6 +2559,14 @@ The currently implemented features of the reference compiler are:
                             types, e.g. as the return type of a public function.
                             This capability may be removed in the future.
 
+* `allow_internal_unstable` - Allows `macro_rules!` macros to be tagged with the
+                              `#[allow_internal_unstable]` attribute, designed
+                              to allow `std` macros to call
+                              `#[unstable]`/feature-gated functionality
+                              internally without imposing on callers
+                              (i.e. making them behave like function calls in
+                              terms of encapsulation).
+
 If a feature is promoted to a language feature, then all existing programs will
 start to receive compilation warnings about #[feature] directives which enabled
 the new feature (because the directive is no longer necessary). However, if a
@@ -2821,7 +2847,7 @@ automatically dereferenced to make the field access possible.
 ### Array expressions
 
 ```{.ebnf .gram}
-array_expr : '[' "mut" ? vec_elems? ']' ;
+array_expr : '[' "mut" ? array_elems? ']' ;
 
 array_elems : [expr [',' expr]*] | [expr ';' expr] ;
 ```
@@ -2981,10 +3007,6 @@ A type cast expression is denoted with the binary operator `as`.
 Executing an `as` expression casts the value on the left-hand side to the type
 on the right-hand side.
 
-A numeric value can be cast to any numeric type. A raw pointer value can be
-cast to or from any integral type or raw pointer type. Any other cast is
-unsupported and will fail to compile.
-
 An example of an `as` expression:
 
 ```
index 33f1e82b187e7ddb6ee68fa2465e131e16a0435e..d2fcf27e93cdf540627bf9e2c2e1255183493882 100644 (file)
@@ -22,9 +22,9 @@ fn write_info(info: &Info) -> Result<(), IoError> {
     let mut file = File::open_mode(&Path::new("my_best_friends.txt"),
                                    Open, Write);
     // Early return on error
-    try!(file.write_line(format!("name: {}", info.name).as_slice()));
-    try!(file.write_line(format!("age: {}", info.age).as_slice()));
-    try!(file.write_line(format!("rating: {}", info.rating).as_slice()));
+    try!(file.write_line(&format!("name: {}", info.name)));
+    try!(file.write_line(&format!("age: {}", info.age)));
+    try!(file.write_line(&format!("rating: {}", info.rating)));
     return Ok(());
 }
 ```
@@ -44,15 +44,15 @@ fn write_info(info: &Info) -> Result<(), IoError> {
     let mut file = File::open_mode(&Path::new("my_best_friends.txt"),
                                    Open, Write);
     // Early return on error
-    match file.write_line(format!("name: {}", info.name).as_slice()) {
+    match file.write_line(&format!("name: {}", info.name)) {
         Ok(_) => (),
         Err(e) => return Err(e)
     }
-    match file.write_line(format!("age: {}", info.age).as_slice()) {
+    match file.write_line(&format!("age: {}", info.age)) {
         Ok(_) => (),
         Err(e) => return Err(e)
     }
-    return file.write_line(format!("rating: {}", info.rating).as_slice());
+    return file.write_line(&format!("rating: {}", info.rating));
 }
 ```
 
index d57aff7f4f411fbc9974666127a02150b324301d..c65389287fbb8a19e4202689b8ea9d0d242dab7a 100644 (file)
     * [Standard Input](standard-input.md)
     * [Guessing Game](guessing-game.md)
 * [II: Intermediate Rust](intermediate.md)
-    * [More Strings](more-strings.md)
     * [Crates and Modules](crates-and-modules.md)
     * [Testing](testing.md)
     * [Pointers](pointers.md)
     * [Ownership](ownership.md)
+    * [More Strings](more-strings.md)
     * [Patterns](patterns.md)
     * [Method Syntax](method-syntax.md)
     * [Closures](closures.md)
index d4e2ad5cd5f66fa7973a0214b130afa660a411aa..f1b5ecf4ff031b4535a5fc685312a6003455aa91 100644 (file)
@@ -60,6 +60,12 @@ let v = vec![1, 2, 3]; // v: Vec<i32>
 brackets `[]` with `vec!`. Rust allows you to use either in either situation,
 this is just convention.)
 
+There's an alternate form of `vec!` for repeating an initial value:
+
+```
+let v = vec![0; 10]; // ten zeroes
+```
+
 You can get the length of, iterate over, and subscript vectors just like
 arrays. In addition, (mutable) vectors can grow automatically:
 
index 85d67262c4066d9bf78b9d7185b0020fefa23877..e09922fd390a9b037cedaab162908449a42d2eb2 100644 (file)
@@ -6,8 +6,8 @@ strings, but next, let's talk about some more complicated ways of storing data.
 
 ## Tuples
 
-The first compound data type we're going to talk about are called *tuples*.
-Tuples are an ordered list of a fixed size. Like this:
+The first compound data type we're going to talk about is called the *tuple*.
+A tuple is an ordered list of fixed size. Like this:
 
 ```rust
 let x = (1, "hello");
@@ -229,7 +229,7 @@ enum Character {
 ```
 
 An `enum` variant can be defined as most normal types. Below are some example
-types have been listed which also would be allowed in an `enum`.
+types which also would be allowed in an `enum`.
 
 ```rust
 struct Empty;
index 842957bd601c61cd59fc479fce93e4d17659dd1b..9b6d6ca67f6c840c2328e986ed03ed9696e724a9 100644 (file)
@@ -223,15 +223,8 @@ method which has this signature:
 fn lock(&self) -> LockResult<MutexGuard<T>>
 ```
 
-If we [look at the code for MutexGuard](https://github.com/rust-lang/rust/blob/ca4b9674c26c1de07a2042cb68e6a062d7184cef/src/libstd/sync/mutex.rs#L172), we'll see
-this:
-
-```ignore
-__marker: marker::NoSend,
-```
-
-Because our guard is `NoSend`, it's not `Send`. Which means we can't actually
-transfer the guard across thread boundaries, which gives us our error.
+Because `Send` is not implemented for `MutexGuard<T>`, we can't transfer the
+guard across thread boundaries, which gives us our error.
 
 We can use `Arc<T>` to fix this. Here's the working version:
 
index f3c0195855c3436baecae176038888e748f96b96..8eaad5067f09e7dc84fc653d4be4c0ed6e791fde 100644 (file)
@@ -555,6 +555,13 @@ Here we have a `pub use` for each function we want to bring into the
 `japanese` scope. We could alternatively use the wildcard syntax to include
 everything from `greetings` into the current scope: `pub use self::greetings::*`. 
 
+What about the `self`? Well, by default, `use` declarations are absolute paths,
+starting from your crate root. `self` makes that path relative to your current
+place in the hierarchy instead. There's one more special form of `use`: you can
+`use super::` to reach one level up the tree from your current location. Some
+people like to think of `self` as `.` and `super` as `..`, from many shells'
+display for the current directory and the parent directory.
+
 Also, note that we `pub use`d before we declared our `mod`s. Rust requires that
 `use` declarations go first.
 
index ded30063ebaf08fbf6a539374a1a978d70699172..0553fe3280c68fd08b0123649912ced97cbde9b9 100644 (file)
 % Documentation
 
-`rustdoc` is the built-in tool for generating documentation. It integrates
-with the compiler to provide accurate hyperlinking between usage of types and
-their documentation. Furthermore, by not using a separate parser, it will
-never reject your valid Rust code.
+Documentation is an important part of any software project, and it's
+first-class in Rust. Let's talk about the tooling Rust gives you to
+document your project.
 
-# Creating Documentation
+## About `rustdoc`
 
-Documenting Rust APIs is quite simple. To document a given item, we have "doc
-comments":
+The Rust distribution includes a tool, `rustdoc`, that generates documentation.
+`rustdoc` is also used by Cargo through `cargo doc`.
 
-~~~
-# #![allow(unused_attribute)]
-// the "link" crate attribute is currently required for rustdoc, but normally
-// isn't needed.
-#![crate_id = "universe"]
-#![crate_type= "lib"]
-
-//! Tools for dealing with universes (this is a doc comment, and is shown on
-//! the crate index page. The ! makes it apply to the parent of the comment,
-//! rather than what follows).
-
-# mod workaround_the_outer_function_rustdoc_inserts {
-/// Widgets are very common (this is a doc comment, and will show up on
-/// Widget's documentation).
-pub struct Widget {
-       /// All widgets have a purpose (this is a doc comment, and will show up
-       /// the field's documentation).
-       purpose: String,
-       /// Humans are not allowed to understand some widgets
-       understandable: bool
-}
+Documentation can be generated in two ways: from source code, and from
+standalone Markdown files.
 
-pub fn recalibrate() {
-       //! Recalibrate a pesky universe (this is also a doc comment, like above,
-       //! the documentation will be applied to the *parent* item, so
-       //! `recalibrate`).
-       /* ... */
-}
-# }
-~~~
+## Documenting source code
 
-Documentation can also be controlled via the `doc` attribute on items. This is
-implicitly done by the compiler when using the above form of doc comments
-(converting the slash-based comments to `#[doc]` attributes).
+The primary way of documenting a Rust project is through annotating the source
+code. You can use documentation comments for this purpose:
 
-~~~
-#[doc = "
-Calculates the factorial of a number.
+```rust,ignore
+/// Constructs a new `Rc<T>`.
+///
+/// # Examples
+///
+/// ```
+/// use std::rc::Rc;
+///
+/// let five = Rc::new(5);
+/// ```
+pub fn new(value: T) -> Rc<T> {
+    // implementation goes here
+}
+```
 
-Given the input integer `n`, this function will calculate `n!` and return it.
-"]
-pub fn factorial(n: int) -> int { if n < 2 {1} else {n * factorial(n - 1)} }
-# fn main() {}
-~~~
+This code generates documentation that looks [like this][rc-new]. I've left the
+implementation out, with a regular comment in its place. That's the first thing
+to notice about this annotation: it uses `///`, instead of `//`. The triple slash
+indicates a documentation comment.
 
-The `doc` attribute can also be used to control how rustdoc emits documentation
-in some cases.
+Documentation comments are written in Markdown.
+
+Rust keeps track of these comments, and uses them when generating
+documentation. This is important when documenting things like enums:
 
 ```
-// Rustdoc will inline documentation of a `pub use` into this crate when the
-// `pub use` reaches across crates, but this behavior can also be disabled.
-#[doc(no_inline)]
-pub use std::option::Option;
-# fn main() {}
+/// The `Option` type. See [the module level documentation](../) for more.
+enum Option<T> {
+    /// No value
+    None,
+    /// Some value `T`
+    Some(T),
+}
 ```
 
-Doc comments are markdown, and are currently parsed with the
-[hoedown][hoedown] library. rustdoc does not yet do any fanciness such as
-referencing other items inline, like javadoc's `@see`. One exception to this
-is that the first paragraph will be used as the "summary" of an item in the
-generated documentation:
+The above works, but this does not:
 
-~~~
-/// A whizbang. Does stuff. (this line is the summary)
-///
-/// Whizbangs are ...
-struct Whizbang;
-~~~
-
-To generate the docs, run `rustdoc universe.rs`. By default, it generates a
-directory called `doc`, with the documentation for `universe` being in
-`doc/universe/index.html`. If you are using other crates with `extern crate`,
-rustdoc will even link to them when you use their types, as long as their
-documentation has already been generated by a previous run of rustdoc, or the
-crate advertises that its documentation is hosted at a given URL.
+```rust,ignore
+/// The `Option` type. See [the module level documentation](../) for more.
+enum Option<T> {
+    None, /// No value
+    Some(T), /// Some value `T`
+}
+```
 
-The generated output can be controlled with the `doc` crate attribute, which
-is how the above advertisement works. An example from the `libstd`
-documentation:
+You'll get an error:
 
-~~~
-#[doc(html_logo_url = "http://www.rust-lang.org/logos/rust-logo-128x128-blk-v2.png",
-      html_favicon_url = "http://www.rust-lang.org/favicon.ico",
-      html_root_url = "http://doc.rust-lang.org/")];
-~~~
+```text
+hello.rs:4:1: 4:2 error: expected ident, found `}`
+hello.rs:4 }
+           ^
+```
 
-The `html_root_url` is the prefix that rustdoc will apply to any references to
-that crate's types etc.
+This [unfortunate error](https://github.com/rust-lang/rust/issues/22547) is
+correct: documentation comments apply to the thing after them, and there's no
+thing after that last comment.
 
-rustdoc can also generate JSON, for consumption by other tools, with
-`rustdoc --output-format json`, and also consume already-generated JSON with
-`rustdoc --input-format json`.
+[rc-new]: http://doc.rust-lang.org/nightly/std/rc/struct.Rc.html#method.new
 
-rustdoc also supports personalizing the output from crates' documentation,
-similar to markdown options.
+### Writing documentation comments
 
-- `--html-in-header FILE`: includes the contents of `FILE` at the
-  end of the `<head>...</head>` section.
-- `--html-before-content FILE`: includes the contents of `FILE`
-  directly after `<body>`, before the rendered content (including the
-  search bar).
-- `--html-after-content FILE`: includes the contents of `FILE`
-  after all the rendered content.
+Anyway, let's cover each part of this comment in detail:
 
-# Using the Documentation
+```
+/// Constructs a new `Rc<T>`.
+# fn foo() {}
+```
 
-The web pages generated by rustdoc present the same logical hierarchy that one
-writes a library with. Every kind of item (function, struct, etc) has its own
-color, and one can always click on a colored type to jump to its
-documentation. There is a search bar at the top, which is powered by some
-JavaScript and a statically-generated search index. No special web server is
-required for the search.
+The first line of a documentation comment should be a short summary of its
+functionality. One sentence. Just the basics. High level.
 
-[hoedown]: https://github.com/hoedown/hoedown
+```
+///
+/// Other details about constructing `Rc<T>`s, maybe describing complicated
+/// semantics, maybe additional options, all kinds of stuff.
+///
+# fn foo() {}
+```
 
-# Testing the Documentation
+Our original example had just a summary line, but if we had more things to say,
+we could have added more explanation in a new paragraph.
 
-`rustdoc` has support for testing code examples which appear in the
-documentation. This is helpful for keeping code examples up to date with the
-source code.
+#### Special sections
 
-To test documentation, the `--test` argument is passed to rustdoc:
+```
+/// # Examples
+# fn foo() {}
+```
 
-~~~ {.sh}
-rustdoc --test crate.rs
-~~~
+Next, are special sections. These are indicated with a header, `#`. There
+are three kinds of headers that are commonly used. They aren't special syntax,
+just convention, for now.
 
-## Defining tests
+```
+/// # Panics
+# fn foo() {}
+```
 
-Rust documentation currently uses the markdown format, and rustdoc treats all
-code blocks as testable-by-default unless they carry a language tag of another
-language. In order to not run a test over a block of code, the `ignore` string
-can be added to the three-backtick form of markdown code block.
+Unrecoverable misuses of a function (i.e. programming errors) in Rust are
+usually indicated by panics, which kill the whole current thread at the very
+least. If your function has a non-trivial contract like this, that is
+detected/enforced by panics, documenting it is very important.
 
-~~~md
 ```
-// This is a testable code block
+/// # Failures
+# fn foo() {}
 ```
 
-```rust{.example}
-// This is rust and also testable
-```
+If your function or method returns a `Result<T, E>`, then describing the
+conditions under which it returns `Err(E)` is a nice thing to do. This is
+slightly less important than `Panics`, because failure is encoded into the type
+system, but it's still a good thing to do.
 
-```ignore
-// This is not a testable code block
+```
+/// # Safety
+# fn foo() {}
 ```
 
-    // This is a testable code block (4-space indent)
+If your function is `unsafe`, you should explain which invariants the caller is
+responsible for upholding.
 
-```sh
-# this is shell code and not tested
 ```
-~~~
+/// # Examples
+///
+/// ```
+/// use std::rc::Rc;
+///
+/// let five = Rc::new(5);
+/// ```
+# fn foo() {}
+```
 
-You can specify that the test's execution should fail with the `should_fail`
-directive.
+Third, `Examples`. Include one or more examples of using your function or
+method, and your users will love you for it. These examples go inside of
+code block annotations, which we'll talk about in a moment, and can have
+more than one section:
 
-~~~md
-```should_fail
-// This code block is expected to generate a panic when run
 ```
-~~~
+/// # Examples
+///
+/// Simple `&str` patterns:
+///
+/// ```
+/// let v: Vec<&str> = "Mary had a little lamb".split(' ').collect();
+/// assert_eq!(v, vec!["Mary", "had", "a", "little", "lamb"]);
+/// ```
+///
+/// More complex patterns with a lambda:
+///
+/// ```
+/// let v: Vec<&str> = "abc1def2ghi".split(|c: char| c.is_numeric()).collect();
+/// assert_eq!(v, vec!["abc", "def", "ghi"]);
+/// ```
+# fn foo() {}
+```
 
-You can specify that the code block should be compiled but not run with the
-`no_run` directive.
+Let's discuss the details of these code blocks.
 
-~~~md
-```no_run
-// This code will be compiled but not executed
-```
-~~~
+#### Code block annotations
 
-Lastly, you can specify that a code block be compiled as if `--test`
-were passed to the compiler using the `test_harness` directive.
+To write some Rust code in a comment, use the triple graves:
 
-~~~md
-```test_harness
-#[test]
-fn foo() {
-    panic!("oops! (will run & register as a failed test)")
-}
 ```
-~~~
+/// ```
+/// println!("Hello, world");
+/// ```
+# fn foo() {}
+```
 
-Rustdoc also supplies some extra sugar for helping with some tedious
-documentation examples. If a line is prefixed with `# `, then the line
-will not show up in the HTML documentation, but it will be used when
-testing the code block (NB. the space after the `#` is required, so
-that one can still write things like `#[derive(Eq)]`).
+If you want something that's not Rust code, you can add an annotation:
 
-~~~md
 ```
-# /!\ The three following lines are comments, which are usually stripped off by
-# the doc-generating tool.  In order to display them anyway in this particular
-# case, the character following the leading '#' is not a usual space like in
-# these first five lines but a non breakable one.
-# // showing 'fib' in this documentation would just be tedious and detracts from
-# // what's actually being documented.
-# fn fib(n: int) { n + 2 }
-
-spawn(move || { fib(200); })
+/// ```c
+/// printf("Hello, world\n");
+/// ```
+# fn foo() {}
 ```
-~~~
 
-The documentation online would look like `spawn(move || { fib(200); })`, but when
-testing this code, the `fib` function will be included (so it can compile).
+This will highlight according to whatever language you're showing off.
+If you're just showing plain text, choose `text`.
+
+It's important to choose the correct annotation here, because `rustdoc` uses it
+in an interesting way: It can be used to actually test your examples, so that
+they don't get out of date. If you have some C code but `rustdoc` thinks it's
+Rust because you left off the annotation, `rustdoc` will complain when trying to
+generate the documentation.
 
-Rustdoc will automatically add a `main()` wrapper around your code, and in the right
-place. For example:
+## Documentation as tests
+
+Let's discuss our sample example documentation:
+
+```
+/// ```
+/// println!("Hello, world");
+/// ```
+# fn foo() {}
+```
+
+You'll notice that you don't need a `fn main()` or anything here. `rustdoc` will
+automatically add a main() wrapper around your code, and in the right place.
+For example:
 
 ```
 /// ```
@@ -240,80 +239,286 @@ fn main() {
 
 Here's the full algorithm:
 
-1. Given a code block, if it does not contain `fn main`, it is wrapped in `fn main() { your_code }`
+1. Given a code block, if it does not contain `fn main()`, it is wrapped in
+   `fn main() { your_code }`
 2. Given that result, if it contains no `extern crate` directives but it also
    contains the name of the crate being tested, then `extern crate <name>` is
    injected at the top.
-3. Some common `allow` attributes are added for documentation examples at the top.
+3. Some common allow attributes are added for documentation examples at the top.
+
+Sometimes, this isn't enough, though. For example, all of these code samples
+with `///` we've been talking about? The raw text:
+
+```text
+/// Some documentation.
+# fn foo() {}
+```
+
+looks different than the output:
+
+```
+/// Some documentation.
+# fn foo() {}
+```
+
+Yes, that's right: you can add lines that start with `# `, and they will
+be hidden from the output, but will be used when compiling your code. You
+can use this to your advantage. In this case, documentation comments need
+to apply to some kind of function, so if I want to show you just a
+documentation comment, I need to add a little function definition below
+it. At the same time, it's just there to satisfy the compiler, so hiding
+it makes the example more clear. You can use this technique to explain
+longer examples in detail, while still preserving the testability of your
+documentation. For example, this code:
+
+```
+let x = 5;
+let y = 6;
+println!("{}", x + y);
+```
+
+Here's an explanation, rendered:
+
+First, we set `x` to five:
+
+```
+let x = 5;
+# let y = 6;
+# println!("{}", x + y);
+```
+
+Next, we set `y` to six:
+
+```
+# let x = 5;
+let y = 6;
+# println!("{}", x + y);
+```
+
+Finally, we print the sum of `x` and `y`:
+
+```
+# let x = 5;
+# let y = 6;
+println!("{}", x + y);
+```
+
+Here's the same explanation, in raw text:
+
+> First, we set `x` to five:
+> 
+> ```text
+> let x = 5;
+> # let y = 6;
+> # println!("{}", x + y);
+> ```
+> 
+> Next, we set `y` to six:
+> 
+> ```text
+> # let x = 5;
+> let y = 6;
+> # println!("{}", x + y);
+> ```
+> 
+> Finally, we print the sum of `x` and `y`:
+> 
+> ```text
+> # let x = 5;
+> # let y = 6;
+> println!("{}", x + y);
+> ```
+
+By repeating all parts of the example, you can ensure that your example still
+compiles, while only showing the parts that are relevant to that part of your
+explanation.
+
+To run the tests, either
+
+```bash
+$ rustdoc --test path/to/my/crate/root.rs
+# or
+$ cargo test
+```
+
+That's right, `cargo test` tests embedded documentation too.
+
+There are a few more annotations that are useful to help `rustdoc` do the right
+thing when testing your code:
+
+```
+/// ```ignore
+/// fn foo() {
+/// ```
+# fn foo() {}
+```
+
+The `ignore` directive tells Rust to ignore your code. This is almost never
+what you want, as it's the most generic. Instead, consider annotating it
+with `text` if it's not code, or using `#`s to get a working example that
+only shows the part you care about.
+
+```
+/// ```should_panic
+/// assert!(false);
+/// ```
+# fn foo() {}
+```
+
+`should_panic` tells `rustdoc` that the code should compile correctly, but
+not actually pass as a test.
+
+```
+/// ```no_run
+/// loop {
+///     println!("Hello, world");
+/// }
+/// ```
+# fn foo() {}
+```
+
+The `no_run` attribute will compile your code, but not run it. This is
+important for examples such as "Here's how to start up a network service,"
+which you would want to make sure compile, but might run in an infinite loop!
+
+### Documenting modules
+
+Rust has another kind of doc comment, `//!`. This comment doesn't document the next item, but the enclosing item. In other words:
+
+```
+mod foo {
+    //! This is documentation for the `foo` module.
+    //!
+    //! # Examples
+
+    // ...
+}
+```
+
+This is where you'll see `//!` used most often: for module documentation. If
+you have a module in `foo.rs`, you'll often open its code and see this:
+
+```
+//! A module for using `foo`s.
+//!
+//! The `foo` module contains a lot of useful functionality blah blah blah
+```
+
+### Documentation comment style
+
+Check out [RFC 505][rfc505] for full conventions around the style and format of
+documentation.
+
+[rfc505]: https://github.com/rust-lang/rfcs/blob/master/text/0505-api-comment-conventions.md
+
+## Other documentation
+
+All of this behavior works in non-Rust source files too. Because comments
+are written in Markdown, they're often `.md` files.
+
+When you write documentation in Markdown files, you don't need to prefix
+the documentation with comments. For example:
 
-## Running tests (advanced)
+```
+/// # Examples
+///
+/// ```
+/// use std::rc::Rc;
+///
+/// let five = Rc::new(5);
+/// ```
+# fn foo() {}
+```
 
-Running tests often requires some special configuration to filter tests, find
-libraries, or try running ignored examples. The testing framework that rustdoc
-uses is built on crate `test`, which is also used when you compile crates with
-rustc's `--test` flag. Extra arguments can be passed to rustdoc's test harness
-with the `--test-args` flag.
+is just
 
-~~~console
-# Only run tests containing 'foo' in their name
-$ rustdoc --test lib.rs --test-args 'foo'
+~~~markdown
+# Examples
 
-# See what's possible when running tests
-$ rustdoc --test lib.rs --test-args '--help'
+```
+use std::rc::Rc;
+
+let five = Rc::new(5);
+```
 ~~~
 
-When testing a library, code examples will often show how functions are used,
-and this code often requires `use`-ing paths from the crate. To accommodate this,
-rustdoc will implicitly add `extern crate <crate>;` where `<crate>` is the name of
-the crate being tested to the top of each code example. This means that rustdoc
-must be able to find a compiled version of the library crate being tested. Extra
-search paths may be added via the `-L` flag to `rustdoc`.
+when it's in a Markdown file. There is one wrinkle though: Markdown files need
+to have a title like this:
 
-# Standalone Markdown files
+```markdown
+% The title
 
-As well as Rust crates, rustdoc supports rendering pure Markdown files
-into HTML and testing the code snippets from them. A Markdown file is
-detected by a `.md` or `.markdown` extension.
+This is the example documentation.
+```
+
+This `%` line needs to be the very first line of the file.
+
+## `doc` attributes
+
+At a deeper level, documentation comments are sugar for documentation attributes:
+
+```
+/// this
+# fn foo() {}
+
+#[doc="this"]
+# fn bar() {}
+```
 
-There are 4 options to modify the output that Rustdoc creates.
+are the same, as are these:
 
-- `--markdown-css PATH`: adds a `<link rel="stylesheet">` tag pointing to `PATH`.
-- `--html-in-header FILE`: includes the contents of `FILE` at the
-  end of the `<head>...</head>` section.
-- `--html-before-content FILE`: includes the contents of `FILE`
-  directly after `<body>`, before the rendered content (including the
-  title).
-- `--html-after-content FILE`: includes the contents of `FILE`
-  directly before `</body>`, after all the rendered content.
+```
+//! this
 
-All of these can be specified multiple times, and they are output in
-the order in which they are specified. The first line of the file being rendered must
-be the title, prefixed with `%` (e.g. this page has `% Rust
-Documentation` on the first line).
+#![doc="/// this"]
+```
 
-Like with a Rust crate, the `--test` argument will run the code
-examples to check they compile, and obeys any `--test-args` flags. The
-tests are named after the last `#` heading.
+You won't often see this attribute used for writing documentation, but it
+can be useful when changing some options, or when writing a macro.
 
-# Re-exports
+### Re-exports
 
-Rustdoc will show the documentation for a publc re-export in both places:
+`rustdoc` will show the documentation for a publc re-export in both places:
 
-```{rust,ignore}
+```ignore
 extern crate foo;
 
 pub use foo::bar;
 ```
 
-This will create documentation for `bar` both inside the documentation for
-the crate `foo`, as well as the documentation for your crate. It will use
-the same documentation in both places.
+This will create documentation for bar both inside the documentation for the
+crate `foo`, as well as the documentation for your crate. It will use the same
+documentation in both places.
 
 This behavior can be supressed with `no_inline`:
 
-```{rust,ignore}
+```ignore
 extern crate foo;
 
 #[doc(no_inline)]
 pub use foo::bar;
 ```
+
+### Controlling HTML
+
+You can control a few aspects of the HTML that `rustdoc` generates through the
+`#![doc]` version of the attribute:
+
+```
+#![doc(html_logo_url = "http://www.rust-lang.org/logos/rust-logo-128x128-blk-v2.png",
+       html_favicon_url = "http://www.rust-lang.org/favicon.ico",
+       html_root_url = "http://doc.rust-lang.org/")];
+```
+
+This sets a few different options, with a logo, favicon, and a root URL.
+
+## Generation options
+
+`rustdoc` also contains a few other options on the command line, for further customiziation:
+
+- `--html-in-header FILE`: includes the contents of FILE at the end of the
+  `<head>...</head>` section.
+- `--html-before-content FILE`: includes the contents of FILE directly after
+  `<body>`, before the rendered content (including the search bar).
+- `--html-after-content FILE`: includes the contents of FILE after all the rendered content.
+
index a40374fe30fadde9235a6607f6f010307eaf0649..4e7222269a8ff1954f4fcffccd2271e0762816c0 100644 (file)
@@ -422,11 +422,11 @@ In this case, we say `x` is a `u32` explicitly, so Rust is able to properly
 tell `random()` what to generate. In a similar fashion, both of these work:
 
 ```{rust,ignore}
-let input_num = "5".parse::<u32>(); // input_num: Option<u32>
-let input_num: Result<u32, _> = "5".parse(); // input_num: Result<u32, <u32 as FromStr>::Err>
+let input_num_option = "5".parse::<u32>().ok(); // input_num: Option<u32>
+let input_num_result: Result<u32, _> = "5".parse(); // input_num: Result<u32, <u32 as FromStr>::Err>
 ```
 
-Here we're converting the `Result` returned by `parse` to an `Option` by using
+Above, we're converting the `Result` returned by `parse` to an `Option` by using
 the `ok` method as well.  Anyway, with us now converting our input to a number,
 our code looks like this:
 
@@ -470,14 +470,14 @@ Let's try it out!
 ```bash
 $ cargo build
    Compiling guessing_game v0.0.1 (file:///home/you/projects/guessing_game)
-src/main.rs:22:15: 22:24 error: mismatched types: expected `u32` but found `core::option::Option<u32>` (expected u32 but found enum core::option::Option)
-src/main.rs:22     match cmp(input_num, secret_number) {
+src/main.rs:21:15: 21:24 error: mismatched types: expected `u32`, found `core::result::Result<u32, core::num::ParseIntError>` (expected u32, found enum `core::result::Result`) [E0308]
+src/main.rs:21     match cmp(input_num, secret_number) {
                              ^~~~~~~~~
 error: aborting due to previous error
 ```
 
-Oh yeah! Our `input_num` has the type `Option<u32>`, rather than `u32`. We
-need to unwrap the Option. If you remember from before, `match` is a great way
+Oh yeah! Our `input_num` has the type `Result<u32, <some error>>`, rather than `u32`. We
+need to unwrap the Result. If you remember from before, `match` is a great way
 to do that. Try this code:
 
 ```{rust,no_run}
@@ -500,7 +500,7 @@ fn main() {
     let input_num: Result<u32, _> = input.parse();
 
     let num = match input_num {
-        Ok(num) => num,
+        Ok(n) => n,
         Err(_) => {
             println!("Please input a number!");
             return;
@@ -524,7 +524,7 @@ fn cmp(a: u32, b: u32) -> Ordering {
 }
 ```
 
-We use a `match` to either give us the `u32` inside of the `Option`, or else
+We use a `match` to either give us the `u32` inside of the `Result`, or else
 print an error message and return. Let's give this a shot:
 
 ```bash
index 64d540582a3998bd7acd97c745379be9d2ba21ba..0625d649e3086b6de909a0c06632f41c0fe02775 100644 (file)
@@ -50,7 +50,29 @@ You can think of this first parameter as being the `x` in `x.foo()`. The three
 variants correspond to the three kinds of thing `x` could be: `self` if it's
 just a value on the stack, `&self` if it's a reference, and `&mut self` if it's
 a mutable reference. We should default to using `&self`, as it's the most
-common.
+common. Here's an example of all three variants:
+
+```rust
+struct Circle {
+    x: f64,
+    y: f64,
+    radius: f64,
+}
+
+impl Circle {
+    fn reference(&self) {
+       println!("taking self by reference!"); 
+    }
+
+    fn mutable_reference(&mut self) {
+       println!("taking self by mutable reference!"); 
+    }
+
+    fn takes_ownership(self) {
+       println!("taking ownership of self!"); 
+    }
+}
+```
 
 Finally, as you may remember, the value of the area of a circle is `π*r²`.
 Because we took the `&self` parameter to `area`, we can use it just like any
index a2a558094e1963c8f4b0c46423f3f69ef0eea45e..6567cd448f998611ee7bdaecc9a8067fddec7921 100644 (file)
@@ -278,7 +278,18 @@ This will print:
 
 Many more bytes than graphemes!
 
-# Other Documentation
+# `Deref` coercions
 
-* [the `&str` API documentation](../std/str/index.html)
-* [the `String` API documentation](../std/string/index.html)
+References to `String`s will automatically coerce into `&str`s. Like this:
+
+```
+fn hello(s: &str) {
+   println!("Hello, {}!", s);
+}
+
+let slice = "Steve";
+let string = "Steve".to_string();
+
+hello(slice);
+hello(&string);
+```
index a093b97eefbc4b34cbbd31e3eefee5c547ef0eae..33f0893466da604ad7472600230c3a5d4a390778 100644 (file)
@@ -63,7 +63,7 @@ that implements Roman numeral integer literals.
 
 ```ignore
 #![crate_type="dylib"]
-#![feature(plugin_registrar)]
+#![feature(plugin_registrar, rustc_private)]
 
 extern crate syntax;
 extern crate rustc;
@@ -92,13 +92,13 @@ fn expand_rn(cx: &mut ExtCtxt, sp: Span, args: &[TokenTree])
         }
     };
 
-    let mut text = &text;
+    let mut text = &*text;
     let mut total = 0;
     while !text.is_empty() {
         match NUMERALS.iter().find(|&&(rn, _)| text.starts_with(rn)) {
             Some(&(rn, val)) => {
                 total += val;
-                text = text.slice_from(rn.len());
+                text = &text[rn.len()..];
             }
             None => {
                 cx.span_err(sp, "invalid Roman numeral");
@@ -107,7 +107,7 @@ fn expand_rn(cx: &mut ExtCtxt, sp: Span, args: &[TokenTree])
         }
     }
 
-    MacEager::expr(cx.expr_usize(sp, total))
+    MacEager::expr(cx.expr_u32(sp, total))
 }
 
 #[plugin_registrar]
index 0f46b4da0d6f971b6ae3371d4850a5b8774493f0..930a40c5050db4c001f0d306d4aa8e671000fa3d 100644 (file)
@@ -634,8 +634,8 @@ use-case for boxes.
 ### Returning data
 
 This is important enough to have its own section entirely. The TL;DR is this:
-you don't generally want to return pointers, even when you might in a language
-like C or C++.
+you don't want to return pointers, even when you might in a language like C or
+C++.
 
 See [Returning Pointers](#returning-pointers) below for more.
 
@@ -709,7 +709,7 @@ fn main() {
         one_hundred: 100,
     });
 
-    let y = box foo(x);
+    let y: Box<BigStruct> = box foo(x);
 }
 ```
 
index abd9af1af33a097e805f0b64cba83d0ccbbc6cdf..676f1cc425ad4f3962487eb0ccc747b02e1bde63 100644 (file)
@@ -435,3 +435,46 @@ println!("the inverse of {} is {:?}", 2.0f64, inverse(2.0f64));
 println!("the inverse of {} is {:?}", 0.0f32, inverse(0.0f32));
 println!("the inverse of {} is {:?}", 0.0f64, inverse(0.0f64));
 ```
+
+## Default methods
+
+There's one last feature of traits we should cover: default methods. It's
+easiest just to show an example:
+
+```rust
+trait Foo {
+    fn bar(&self);
+
+    fn baz(&self) { println!("We called baz."); }
+}
+```
+
+Implementors of the `Foo` trait need to implement `bar()`, but they don't
+need to implement `baz()`. They'll get this default behavior. They can
+override the default if they so choose:
+
+```rust
+# trait Foo {
+# fn bar(&self);
+# fn baz(&self) { println!("We called baz."); }
+# }
+struct UseDefault;
+
+impl Foo for UseDefault {
+    fn bar(&self) { println!("We called bar."); }
+}
+
+struct OverrideDefault;
+
+impl Foo for OverrideDefault {
+    fn bar(&self) { println!("We called bar."); }
+
+    fn baz(&self) { println!("Override baz!"); }
+}
+
+let default = UseDefault;
+default.baz(); // prints "We called bar."
+
+let over = OverrideDefault;
+over.baz(); // prints "Override baz!"
+```
index fd3309dce12cbd01e1c573e05beeddb096a7c2f1..c524fae7f0a42e6272ce736cd5d54517702baa11 100644 (file)
@@ -13,7 +13,7 @@ import fileinput
 import subprocess
 import re
 import os
-from licenseck import *
+from licenseck import check_license
 import snapshot
 
 err = 0
@@ -22,13 +22,8 @@ cr_flag = "ignore-tidy-cr"
 tab_flag = "ignore-tidy-tab"
 linelength_flag = "ignore-tidy-linelength"
 
-# Be careful to support Python 2.4, 2.6, and 3.x here!
-config_proc = subprocess.Popen(["git", "config", "core.autocrlf"],
-                               stdout=subprocess.PIPE)
-result = config_proc.communicate()[0]
-
-true = "true".encode('utf8')
-autocrlf = result.strip() == true if result is not None else False
+interesting_files = ['.rs', '.py', '.js', '.sh', '.c', '.h']
+uninteresting_files = ['miniz.c', 'jquery', 'rust_android_dummy']
 
 
 def report_error_name_no(name, no, s):
@@ -51,6 +46,34 @@ def do_license_check(name, contents):
     if not check_license(name, contents):
         report_error_name_no(name, 1, "incorrect license")
 
+
+def update_counts(current_name):
+    global file_counts
+    global count_other_linted_files
+
+    _, ext = os.path.splitext(current_name)
+
+    if ext in interesting_files:
+        file_counts[ext] += 1
+    else:
+        count_other_linted_files += 1
+
+
+def interesting_file(f):
+    if any(x in f for x in uninteresting_files):
+        return False
+
+    return any(os.path.splitext(f)[1] == ext for ext in interesting_files)
+
+
+# Be careful to support Python 2.4, 2.6, and 3.x here!
+config_proc = subprocess.Popen(["git", "config", "core.autocrlf"],
+                               stdout=subprocess.PIPE)
+result = config_proc.communicate()[0]
+
+true = "true".encode('utf8')
+autocrlf = result.strip() == true if result is not None else False
+
 current_name = ""
 current_contents = ""
 check_tab = True
@@ -63,28 +86,16 @@ if len(sys.argv) < 2:
 
 src_dir = sys.argv[1]
 
-try:
-    count_lines = 0
-    count_non_blank_lines = 0
+count_lines = 0
+count_non_blank_lines = 0
+count_other_linted_files = 0
 
-    interesting_files = ['.rs', '.py', '.js', '.sh', '.c', '.h']
+file_counts = {ext: 0 for ext in interesting_files}
 
-    file_counts = {ext: 0 for ext in interesting_files}
-    file_counts['other'] = 0
-
-    def update_counts(current_name):
-        global file_counts
-        _, ext = os.path.splitext(current_name)
-
-        if ext in file_counts:
-            file_counts[ext] += 1
-        else:
-            file_counts['other'] += 1
-
-    all_paths = set()
+all_paths = set()
 
+try:
     for (dirpath, dirnames, filenames) in os.walk(src_dir):
-
         # Skip some third-party directories
         skippable_dirs = {
             'src/jemalloc',
@@ -103,14 +114,6 @@ try:
         if any(d in dirpath for d in skippable_dirs):
             continue
 
-        def interesting_file(f):
-            if "miniz.c" in f \
-            or "jquery" in f \
-            or "rust_android_dummy" in f:
-                return False
-
-            return any(os.path.splitext(f)[1] == ext for ext in interesting_files)
-
         file_names = [os.path.join(dirpath, f) for f in filenames
                       if interesting_file(f)
                       and not f.endswith("_gen.rs")
@@ -196,10 +199,11 @@ except UnicodeDecodeError as e:
     report_err("UTF-8 decoding error " + str(e))
 
 print
-for ext in file_counts:
-    print "* linted " + str(file_counts[ext]) + " " + ext + " files"
-print "* total lines of code: " + str(count_lines)
-print "* total non-blank lines of code: " + str(count_non_blank_lines)
+for ext in sorted(file_counts, key=file_counts.get, reverse=True):
+    print "* linted {} {} files".format(file_counts[ext], ext)
+print "* linted {} other files".format(count_other_linted_files)
+print "* total lines of code: {}".format(count_lines)
+print "* total non-blank lines of code: {}".format(count_non_blank_lines)
 print
 
 sys.exit(err)
index dc8716d1378df6ce3296716f204ad70a444f0c88..312076b1b13b2818d43480b32ffea2c96a097ef4 100755 (executable)
@@ -84,8 +84,8 @@ def fetch(f):
         sys.stderr.write("cannot load %s" % f)
         exit(1)
 
-def is_valid_unicode(n):
-    return 0 <= n <= 0xD7FF or 0xE000 <= n <= 0x10FFFF
+def is_surrogate(n):
+    return 0xD800 <= n <= 0xDFFF
 
 def load_unicode_data(f):
     fetch(f)
@@ -96,19 +96,28 @@ def load_unicode_data(f):
     canon_decomp = {}
     compat_decomp = {}
 
+    udict = {};
+    range_start = -1;
     for line in fileinput.input(f):
-        fields = line.split(";")
-        if len(fields) != 15:
+        data = line.split(';');
+        if len(data) != 15:
             continue
-        [code, name, gencat, combine, bidi,
-         decomp, deci, digit, num, mirror,
-         old, iso, upcase, lowcase, titlecase ] = fields
-
-        code_org = code
-        code     = int(code, 16)
-
-        if not is_valid_unicode(code):
+        cp = int(data[0], 16);
+        if is_surrogate(cp):
             continue
+        if range_start >= 0:
+            for i in xrange(range_start, cp):
+                udict[i] = data;
+            range_start = -1;
+        if data[1].endswith(", First>"):
+            range_start = cp;
+            continue;
+        udict[cp] = data;
+
+    for code in udict:
+        [code_org, name, gencat, combine, bidi,
+         decomp, deci, digit, num, mirror,
+         old, iso, upcase, lowcase, titlecase ] = udict[code];
 
         # generate char to char direct common and simple conversions
         # uppercase to lowercase
@@ -290,11 +299,11 @@ def emit_bsearch_range_table(f):
 fn bsearch_range_table(c: char, r: &'static [(char,char)]) -> bool {
     use core::cmp::Ordering::{Equal, Less, Greater};
     use core::slice::SliceExt;
-    r.binary_search(|&(lo,hi)| {
+    r.binary_search_by(|&(lo,hi)| {
         if lo <= c && c <= hi { Equal }
         else if hi < c { Less }
         else { Greater }
-    }).found().is_some()
+    }).is_ok()
 }\n
 """)
 
@@ -303,7 +312,7 @@ def emit_table(f, name, t_data, t_type = "&'static [(char, char)]", is_pub=True,
     pub_string = ""
     if is_pub:
         pub_string = "pub "
-    f.write("    %sstatic %s: %s = &[\n" % (pub_string, name, t_type))
+    f.write("    %sconst %s: %s = &[\n" % (pub_string, name, t_type))
     data = ""
     first = True
     for dat in t_data:
@@ -329,14 +338,14 @@ def emit_property_module(f, mod, tbl, emit_fn):
 def emit_regex_module(f, cats, w_data):
     f.write("pub mod regex {\n")
     regex_class = "&'static [(char, char)]"
-    class_table = "&'static [(&'static str, &'static %s)]" % regex_class
+    class_table = "&'static [(&'static str, %s)]" % regex_class
 
     emit_table(f, "UNICODE_CLASSES", cats, class_table,
-        pfun=lambda x: "(\"%s\",&super::%s::%s_table)" % (x[0], x[1], x[0]))
+        pfun=lambda x: "(\"%s\",super::%s::%s_table)" % (x[0], x[1], x[0]))
 
-    f.write("    pub static PERLD: &'static %s = &super::general_category::Nd_table;\n\n"
+    f.write("    pub const PERLD: %s = super::general_category::Nd_table;\n\n"
             % regex_class)
-    f.write("    pub static PERLS: &'static %s = &super::property::White_Space_table;\n\n"
+    f.write("    pub const PERLS: %s = super::property::White_Space_table;\n\n"
             % regex_class)
 
     emit_table(f, "PERLW", w_data, regex_class)
@@ -350,7 +359,7 @@ def emit_conversions_module(f, lowerupper, upperlower):
     use core::slice::SliceExt;
     use core::option::Option;
     use core::option::Option::{Some, None};
-    use core::slice;
+    use core::result::Result::{Ok, Err};
 
     pub fn to_lower(c: char) -> char {
         match bsearch_case_table(c, LuLl_table) {
@@ -367,13 +376,13 @@ def emit_conversions_module(f, lowerupper, upperlower):
     }
 
     fn bsearch_case_table(c: char, table: &'static [(char, char)]) -> Option<usize> {
-        match table.binary_search(|&(key, _)| {
+        match table.binary_search_by(|&(key, _)| {
             if c == key { Equal }
             else if key < c { Less }
             else { Greater }
         }) {
-            slice::BinarySearchResult::Found(i) => Some(i),
-            slice::BinarySearchResult::NotFound(_) => None,
+            Ok(i) => Some(i),
+            Err(_) => None,
         }
     }
 
@@ -386,10 +395,9 @@ def emit_conversions_module(f, lowerupper, upperlower):
 
 def emit_grapheme_module(f, grapheme_table, grapheme_cats):
     f.write("""pub mod grapheme {
-    use core::kinds::Copy;
     use core::slice::SliceExt;
     pub use self::GraphemeCat::*;
-    use core::slice;
+    use core::result::Result::{Ok, Err};
 
     #[allow(non_camel_case_types)]
     #[derive(Clone, Copy)]
@@ -401,16 +409,16 @@ def emit_grapheme_module(f, grapheme_table, grapheme_cats):
 
     fn bsearch_range_value_table(c: char, r: &'static [(char, char, GraphemeCat)]) -> GraphemeCat {
         use core::cmp::Ordering::{Equal, Less, Greater};
-        match r.binary_search(|&(lo, hi, _)| {
+        match r.binary_search_by(|&(lo, hi, _)| {
             if lo <= c && c <= hi { Equal }
             else if hi < c { Less }
             else { Greater }
         }) {
-            slice::BinarySearchResult::Found(idx) => {
+            Ok(idx) => {
                 let (_, _, cat) = r[idx];
                 cat
             }
-            slice::BinarySearchResult::NotFound(_) => GC_Any
+            Err(_) => GC_Any
         }
     }
 
@@ -430,20 +438,20 @@ def emit_charwidth_module(f, width_table):
     f.write("    use core::option::Option;\n")
     f.write("    use core::option::Option::{Some, None};\n")
     f.write("    use core::slice::SliceExt;\n")
-    f.write("    use core::slice;\n")
+    f.write("    use core::result::Result::{Ok, Err};\n")
     f.write("""
     fn bsearch_range_value_table(c: char, is_cjk: bool, r: &'static [(char, char, u8, u8)]) -> u8 {
         use core::cmp::Ordering::{Equal, Less, Greater};
-        match r.binary_search(|&(lo, hi, _, _)| {
+        match r.binary_search_by(|&(lo, hi, _, _)| {
             if lo <= c && c <= hi { Equal }
             else if hi < c { Less }
             else { Greater }
         }) {
-            slice::BinarySearchResult::Found(idx) => {
+            Ok(idx) => {
                 let (_, _, r_ncjk, r_cjk) = r[idx];
                 if is_cjk { r_cjk } else { r_ncjk }
             }
-            slice::BinarySearchResult::NotFound(_) => 1
+            Err(_) => 1
         }
     }
 """)
@@ -530,17 +538,17 @@ def emit_norm_module(f, canon, compat, combine, norm_props):
     fn bsearch_range_value_table(c: char, r: &'static [(char, char, u8)]) -> u8 {
         use core::cmp::Ordering::{Equal, Less, Greater};
         use core::slice::SliceExt;
-        use core::slice;
-        match r.binary_search(|&(lo, hi, _)| {
+        use core::result::Result::{Ok, Err};
+        match r.binary_search_by(|&(lo, hi, _)| {
             if lo <= c && c <= hi { Equal }
             else if hi < c { Less }
             else { Greater }
         }) {
-            slice::BinarySearchResult::Found(idx) => {
+            Ok(idx) => {
                 let (_, _, result) = r[idx];
                 result
             }
-            slice::BinarySearchResult::NotFound(_) => 0
+            Err(_) => 0
         }
     }\n
 """)
@@ -609,7 +617,7 @@ if __name__ == "__main__":
             unicode_version = re.search(pattern, readme.read()).groups()
         rf.write("""
 /// The version of [Unicode](http://www.unicode.org/)
-/// that the `UnicodeChar` and `UnicodeStrPrelude` traits are based on.
+/// that the unicode parts of `CharExt` and `UnicodeStrPrelude` traits are based on.
 pub const UNICODE_VERSION: (u64, u64, u64) = (%s, %s, %s);
 """ % unicode_version)
         (canon_decomp, compat_decomp, gencats, combines,
index 6a6f7e0e9f92cb99627b0fe24cdf71f2e71f8a60..6c3fd186cd423bdea36260cc459fe361602eb0e2 100644 (file)
@@ -152,6 +152,12 @@ extern char *yytext;
 %precedence MOD_SEP
 %precedence RARROW ':'
 
+// In where clauses, "for" should have greater precedence when used as
+// a higher ranked constraint than when used as the beginning of a
+// for_in_type (which is a ty)
+%precedence FORTYPE
+%precedence FOR
+
 // Binops & unops, and their precedences
 %precedence BOX
 %precedence BOXPLACE
@@ -582,6 +588,14 @@ item_impl
 {
   $$ = mk_node("ItemImplNeg", 7, $1, $3, $5, $7, $8, $10, $11);
 }
+| maybe_unsafe IMPL generic_params trait_ref FOR DOTDOT '{' '}'
+{
+  $$ = mk_node("ItemImplDefault", 3, $1, $3, $4);
+}
+| maybe_unsafe IMPL generic_params '!' trait_ref FOR DOTDOT '{' '}'
+{
+  $$ = mk_node("ItemImplDefaultNeg", 3, $1, $3, $4);
+}
 ;
 
 maybe_impl_items
@@ -769,10 +783,14 @@ where_predicates
 ;
 
 where_predicate
-: lifetime ':' bounds    { $$ = mk_node("WherePredicate", 2, $1, $3); }
-| ty ':' ty_param_bounds { $$ = mk_node("WherePredicate", 2, $1, $3); }
+: maybe_for_lifetimes lifetime ':' bounds    { $$ = mk_node("WherePredicate", 3, $1, $2, $4); }
+| maybe_for_lifetimes ty ':' ty_param_bounds { $$ = mk_node("WherePredicate", 3, $1, $2, $4); }
 ;
 
+maybe_for_lifetimes
+: FOR '<' lifetimes '>' { $$ = mk_none(); }
+| %prec FORTYPE %empty  { $$ = mk_none(); }
+
 ty_params
 : ty_param               { $$ = mk_node("TyParams", 1, $1); }
 | ty_params ',' ty_param { $$ = ext_node($1, 1, $3); }
@@ -1024,7 +1042,8 @@ ty_qualified_path_and_generic_values
 }
 | ty_qualified_path ',' ty_sums maybe_bindings
 {
-  $$ = mk_node("GenericValues", 3, mk_none(), ext_node(mk_node("TySums", 1, $1), 1, $3), $4); }
+  $$ = mk_node("GenericValues", 3, mk_none(), mk_node("TySums", 2, $1, $3), $4);
+}
 ;
 
 ty_qualified_path
@@ -1513,31 +1532,35 @@ nonblock_prefix_expr
 ;
 
 expr_qualified_path
-: '<' ty_sum AS trait_ref '>' MOD_SEP ident
+: '<' ty_sum maybe_as_trait_ref '>' MOD_SEP ident
 {
-  $$ = mk_node("ExprQualifiedPath", 3, $2, $4, $7);
+  $$ = mk_node("ExprQualifiedPath", 3, $2, $3, $6);
 }
-| '<' ty_sum AS trait_ref '>' MOD_SEP ident generic_args
+| '<' ty_sum maybe_as_trait_ref '>' MOD_SEP ident generic_args
 {
-  $$ = mk_node("ExprQualifiedPath", 4, $2, $4, $7, $8);
+  $$ = mk_node("ExprQualifiedPath", 4, $2, $3, $6, $7);
 }
-| SHL ty_sum AS trait_ref '>' MOD_SEP ident AS trait_ref '>' MOD_SEP ident
+| SHL ty_sum maybe_as_trait_ref '>' MOD_SEP ident maybe_as_trait_ref '>' MOD_SEP ident
 {
-  $$ = mk_node("ExprQualifiedPath", 3, mk_node("ExprQualifiedPath", 3, $2, $4, $7), $9, $12);
+  $$ = mk_node("ExprQualifiedPath", 3, mk_node("ExprQualifiedPath", 3, $2, $3, $6), $7, $10);
 }
-| SHL ty_sum AS trait_ref '>' MOD_SEP ident generic_args AS trait_ref '>' MOD_SEP ident
+| SHL ty_sum maybe_as_trait_ref '>' MOD_SEP ident generic_args maybe_as_trait_ref '>' MOD_SEP ident
 {
-  $$ = mk_node("ExprQualifiedPath", 3, mk_node("ExprQualifiedPath", 4, $2, $4, $7, $8), $10, $13);
+  $$ = mk_node("ExprQualifiedPath", 3, mk_node("ExprQualifiedPath", 4, $2, $3, $6, $7), $8, $11);
 }
-| SHL ty_sum AS trait_ref '>' MOD_SEP ident AS trait_ref '>' MOD_SEP ident generic_args
+| SHL ty_sum maybe_as_trait_ref '>' MOD_SEP ident maybe_as_trait_ref '>' MOD_SEP ident generic_args
 {
-  $$ = mk_node("ExprQualifiedPath", 4, mk_node("ExprQualifiedPath", 3, $2, $4, $7), $9, $12, $13);
+  $$ = mk_node("ExprQualifiedPath", 4, mk_node("ExprQualifiedPath", 3, $2, $3, $6), $7, $10, $11);
 }
-| SHL ty_sum AS trait_ref '>' MOD_SEP ident generic_args AS trait_ref '>' MOD_SEP ident generic_args
+| SHL ty_sum maybe_as_trait_ref '>' MOD_SEP ident generic_args maybe_as_trait_ref '>' MOD_SEP ident generic_args
 {
-  $$ = mk_node("ExprQualifiedPath", 4, mk_node("ExprQualifiedPath", 4, $2, $4, $7, $8), $10, $13, $14);
+  $$ = mk_node("ExprQualifiedPath", 4, mk_node("ExprQualifiedPath", 4, $2, $3, $6, $7), $8, $11, $12);
 }
 
+maybe_as_trait_ref
+: AS trait_ref { $$ = $2; }
+| %empty       { $$ = mk_none(); }
+;
 
 lambda_expr
 : %prec LAMBDA
index b001609960ca33047e5cbc5a231c1e24b6041d4b..e24a1a025a1f214e40eedafe3b9c7b1d69937922 160000 (submodule)
@@ -1 +1 @@
-Subproject commit b001609960ca33047e5cbc5a231c1e24b6041d4b
+Subproject commit e24a1a025a1f214e40eedafe3b9c7b1d69937922
index c95b413b397edb1fd489298ddde673707e4fce7a..dc1938cac1ada7b51f3d12e264d9e85245f9773d 100644 (file)
@@ -69,6 +69,8 @@
 //! }
 //! ```
 
+use boxed::Box;
+
 use core::prelude::*;
 
 use core::atomic;
@@ -170,7 +172,7 @@ impl<T> Arc<T> {
     pub fn new(data: T) -> Arc<T> {
         // Start the weak pointer count as 1 which is the weak pointer that's
         // held by all the strong pointers (kinda), see std/rc.rs for more info
-        let x = box ArcInner {
+        let x: Box<_> = box ArcInner {
             strong: atomic::AtomicUsize::new(1),
             weak: atomic::AtomicUsize::new(1),
             data: data,
index a93872dfe36bd8d522bd9fa3e56e10715f386605..9351b11010030baed4f8e31a9097fc3b0107ca75 100644 (file)
@@ -42,7 +42,7 @@
 //! }
 //! ```
 //!
-//! This will print `Cons(1i32, Box(Cons(2i32, Box(Nil))))`.
+//! This will print `Cons(1, Box(Cons(2, Box(Nil))))`.
 
 #![stable(feature = "rust1", since = "1.0.0")]
 
@@ -94,6 +94,7 @@ impl<T> Box<T> {
     /// let x = Box::new(5);
     /// ```
     #[stable(feature = "rust1", since = "1.0.0")]
+    #[inline(always)]
     pub fn new(x: T) -> Box<T> {
         box x
     }
@@ -156,7 +157,7 @@ fn default() -> Box<T> { box Default::default() }
 #[stable(feature = "rust1", since = "1.0.0")]
 impl<T> Default for Box<[T]> {
     #[stable(feature = "rust1", since = "1.0.0")]
-    fn default() -> Box<[T]> { box [] }
+    fn default() -> Box<[T]> { Box::<[T; 0]>::new([]) }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
index b7bacaa0cae2bf074ba3a311da0a34c7a7b256b9..bb1ff9428a7c01889b89797073a43df8189529bf 100644 (file)
@@ -72,13 +72,13 @@ fn test_show() {
 #[test]
 fn deref() {
     fn homura<T: Deref<Target=i32>>(_: T) { }
-    homura(Box::new(765i32));
+    homura(Box::new(765));
 }
 
 #[test]
 fn raw_sized() {
     unsafe {
-        let x = Box::new(17i32);
+        let x = Box::new(17);
         let p = boxed::into_raw(x);
         assert_eq!(17, *p);
         *p = 19;
index 726d5c8a23b739c179c22701b9628a4a450ae11a..3b93171386a076e13d1f77a83e31756f2e8fb4a0 100644 (file)
@@ -387,6 +387,7 @@ mod test {
     extern crate test;
     use self::test::Bencher;
     use core::ptr::PtrExt;
+    use boxed::Box;
     use heap;
 
     #[test]
@@ -404,7 +405,7 @@ fn basic_reallocate_inplace_noop() {
     #[bench]
     fn alloc_owned_small(b: &mut Bencher) {
         b.iter(|| {
-            box 10
+            let _: Box<_> = box 10;
         })
     }
 }
index 82bd13475c74eabb6f106112edd5434c7411cc70..5c9a42a8a71747534e2dfce3e98ca1efe6726272 100644 (file)
@@ -56,6 +56,8 @@
 //! The [`heap`](heap/index.html) module defines the low-level interface to the
 //! default global allocator. It is not compatible with the libc allocator API.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "alloc"]
 #![unstable(feature = "alloc")]
 #![feature(staged_api)]
 
 // Primitive types using the heaps above
 
+// Need to conditionally define the mod from `boxed.rs` to avoid
+// duplicating the lang-items when building in test cfg; but also need
+// to allow code to have `use boxed::HEAP;`
+// and `use boxed::Box;` declarations.
 #[cfg(not(test))]
 pub mod boxed;
 #[cfg(test)]
+mod boxed { pub use std::boxed::{Box, HEAP}; }
+#[cfg(test)]
 mod boxed_test;
 pub mod arc;
 pub mod rc;
index f57286bbf11c9af56ee608e8b9af720ddf00eaa4..763dcc7f256e91534ac4a6c07e8745c8f91767fc 100644 (file)
@@ -795,6 +795,7 @@ fn inner(&self) -> &RcBox<T> {
 #[cfg(test)]
 mod tests {
     use super::{Rc, Weak, weak_count, strong_count};
+    use std::boxed::Box;
     use std::cell::RefCell;
     use std::option::Option;
     use std::option::Option::{Some, None};
@@ -826,7 +827,7 @@ fn test_simple_clone() {
 
     #[test]
     fn test_destructor() {
-        let x = Rc::new(box 5);
+        let x: Rc<Box<_>> = Rc::new(box 5);
         assert_eq!(**x, 5);
     }
 
index b43f9adfb26d92ed9c8f8f4ee8df7bc634c0cb46..d08c9b3257a01bd01582980e0f3cc1cd9c5938ad 100644 (file)
@@ -19,6 +19,8 @@
 //! arena but can only hold objects of a single type, and `Arena`, which is a
 //! more complex, slower arena which can hold objects of any type.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "arena"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
@@ -321,7 +323,7 @@ fn test_arena_destructors() {
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 fn test_arena_destructors_fail() {
     let arena = Arena::new();
     // Put some stuff in the arena.
@@ -581,11 +583,11 @@ pub fn bench_copy(b: &mut Bencher) {
     #[bench]
     pub fn bench_copy_nonarena(b: &mut Bencher) {
         b.iter(|| {
-            box Point {
+            let _: Box<_> = box Point {
                 x: 1,
                 y: 2,
                 z: 3,
-            }
+            };
         })
     }
 
@@ -634,10 +636,10 @@ pub fn bench_noncopy(b: &mut Bencher) {
     #[bench]
     pub fn bench_noncopy_nonarena(b: &mut Bencher) {
         b.iter(|| {
-            box Noncopy {
+            let _: Box<_> = box Noncopy {
                 string: "hello world".to_string(),
                 array: vec!( 1, 2, 3, 4, 5 ),
-            }
+            };
         })
     }
 
index 36c76dbad14aefcb20076f4d9c63613aa80fe221..2e575ddb00a3275bb23cf8c33fedea0857050192 100644 (file)
@@ -790,7 +790,7 @@ fn test_push() {
 
     #[test]
     fn test_push_unique() {
-        let mut heap = BinaryHeap::from_vec(vec![box 2, box 4, box 9]);
+        let mut heap = BinaryHeap::<Box<_>>::from_vec(vec![box 2, box 4, box 9]);
         assert_eq!(heap.len(), 3);
         assert!(*heap.peek().unwrap() == box 9);
         heap.push(box 11);
index 5b19de42ac919240167e67892b48ba519dd55b63..7524fb6cf18a65b4effbc2f0585afbab13ab7ecc 100644 (file)
@@ -118,11 +118,11 @@ fn match_words <'a,'b>(a: &'a BitVec, b: &'b BitVec) -> (MatchWords<'a>, MatchWo
 
     // have to uselessly pretend to pad the longer one for type matching
     if a_len < b_len {
-        (a.blocks().enumerate().chain(iter::repeat(0u32).enumerate().take(b_len).skip(a_len)),
-         b.blocks().enumerate().chain(iter::repeat(0u32).enumerate().take(0).skip(0)))
+        (a.blocks().enumerate().chain(iter::repeat(0).enumerate().take(b_len).skip(a_len)),
+         b.blocks().enumerate().chain(iter::repeat(0).enumerate().take(0).skip(0)))
     } else {
-        (a.blocks().enumerate().chain(iter::repeat(0u32).enumerate().take(0).skip(0)),
-         b.blocks().enumerate().chain(iter::repeat(0u32).enumerate().take(a_len).skip(b_len)))
+        (a.blocks().enumerate().chain(iter::repeat(0).enumerate().take(0).skip(0)),
+         b.blocks().enumerate().chain(iter::repeat(0).enumerate().take(a_len).skip(b_len)))
     }
 }
 
@@ -189,17 +189,17 @@ fn blocks_for_bits(bits: usize) -> usize {
     //
     // Note that we can technically avoid this branch with the expression
     // `(nbits + u32::BITS - 1) / 32::BITS`, but if nbits is almost usize::MAX this will overflow.
-    if bits % u32::BITS == 0 {
-        bits / u32::BITS
+    if bits % u32::BITS as usize == 0 {
+        bits / u32::BITS as usize
     } else {
-        bits / u32::BITS + 1
+        bits / u32::BITS as usize + 1
     }
 }
 
 /// Computes the bitmask for the final word of the vector
 fn mask_for_bits(bits: usize) -> u32 {
     // Note especially that a perfect multiple of u32::BITS should mask all 1s.
-    !0u32 >> (u32::BITS - bits % u32::BITS) % u32::BITS
+    !0 >> (u32::BITS as usize - bits % u32::BITS as usize) % u32::BITS as usize
 }
 
 impl BitVec {
@@ -237,7 +237,7 @@ fn blocks(&self) -> Blocks {
     /// An operation might screw up the unused bits in the last block of the
     /// `BitVec`. As per (3), it's assumed to be all 0s. This method fixes it up.
     fn fix_last_block(&mut self) {
-        let extra_bits = self.len() % u32::BITS;
+        let extra_bits = self.len() % u32::BITS as usize;
         if extra_bits > 0 {
             let mask = (1 << extra_bits) - 1;
             let storage_len = self.storage.len();
@@ -275,7 +275,7 @@ pub fn new() -> BitVec {
     pub fn from_elem(nbits: usize, bit: bool) -> BitVec {
         let nblocks = blocks_for_bits(nbits);
         let mut bit_vec = BitVec {
-            storage: repeat(if bit { !0u32 } else { 0u32 }).take(nblocks).collect(),
+            storage: repeat(if bit { !0 } else { 0 }).take(nblocks).collect(),
             nbits: nbits
         };
         bit_vec.fix_last_block();
@@ -313,7 +313,7 @@ pub fn with_capacity(nbits: usize) -> BitVec {
     ///                     false, false, true, false]));
     /// ```
     pub fn from_bytes(bytes: &[u8]) -> BitVec {
-        let len = bytes.len().checked_mul(u8::BITS).expect("capacity overflow");
+        let len = bytes.len().checked_mul(u8::BITS as usize).expect("capacity overflow");
         let mut bit_vec = BitVec::with_capacity(len);
         let complete_words = bytes.len() / 4;
         let extra_bytes = bytes.len() % 4;
@@ -330,7 +330,7 @@ pub fn from_bytes(bytes: &[u8]) -> BitVec {
         }
 
         if extra_bytes > 0 {
-            let mut last_word = 0u32;
+            let mut last_word = 0;
             for (i, &byte) in bytes[complete_words*4..].iter().enumerate() {
                 last_word |= (reverse_bits(byte) as u32) << (i * 8);
             }
@@ -380,8 +380,8 @@ pub fn get(&self, i: usize) -> Option<bool> {
         if i >= self.nbits {
             return None;
         }
-        let w = i / u32::BITS;
-        let b = i % u32::BITS;
+        let w = i / u32::BITS as usize;
+        let b = i % u32::BITS as usize;
         self.storage.get(w).map(|&block|
             (block & (1 << b)) != 0
         )
@@ -407,8 +407,8 @@ pub fn get(&self, i: usize) -> Option<bool> {
                reason = "panic semantics are likely to change in the future")]
     pub fn set(&mut self, i: usize, x: bool) {
         assert!(i < self.nbits);
-        let w = i / u32::BITS;
-        let b = i % u32::BITS;
+        let w = i / u32::BITS as usize;
+        let b = i % u32::BITS as usize;
         let flag = 1 << b;
         let val = if x { self.storage[w] | flag }
                   else { self.storage[w] & !flag };
@@ -431,7 +431,7 @@ pub fn set(&mut self, i: usize, x: bool) {
     /// ```
     #[inline]
     pub fn set_all(&mut self) {
-        for w in &mut self.storage { *w = !0u32; }
+        for w in &mut self.storage { *w = !0; }
         self.fix_last_block();
     }
 
@@ -566,12 +566,12 @@ pub fn difference(&mut self, other: &BitVec) -> bool {
     /// assert_eq!(bv.all(), false);
     /// ```
     pub fn all(&self) -> bool {
-        let mut last_word = !0u32;
+        let mut last_word = !0;
         // Check that every block but the last is all-ones...
         self.blocks().all(|elem| {
             let tmp = last_word;
             last_word = elem;
-            tmp == !0u32
+            tmp == !0
         // and then check the last one has enough ones
         }) && (last_word == mask_for_bits(self.nbits))
     }
@@ -789,7 +789,7 @@ pub fn reserve_exact(&mut self, additional: usize) {
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn capacity(&self) -> usize {
-        self.storage.capacity().checked_mul(u32::BITS).unwrap_or(usize::MAX)
+        self.storage.capacity().checked_mul(u32::BITS as usize).unwrap_or(usize::MAX)
     }
 
     /// Grows the `BitVec` in-place, adding `n` copies of `value` to the `BitVec`.
@@ -818,11 +818,11 @@ pub fn grow(&mut self, n: usize, value: bool) {
         let full_value = if value { !0 } else { 0 };
 
         // Correct the old tail word, setting or clearing formerly unused bits
-        let old_last_word = blocks_for_bits(self.nbits) - 1;
-        if self.nbits % u32::BITS > 0 {
+        let num_cur_blocks = blocks_for_bits(self.nbits);
+        if self.nbits % u32::BITS as usize > 0 {
             let mask = mask_for_bits(self.nbits);
             if value {
-                self.storage[old_last_word] |= !mask;
+                self.storage[num_cur_blocks - 1] |= !mask;
             } else {
                 // Extra bits are already zero by invariant.
             }
@@ -830,7 +830,7 @@ pub fn grow(&mut self, n: usize, value: bool) {
 
         // Fill in words after the old tail word
         let stop_idx = cmp::min(self.storage.len(), new_nblocks);
-        for idx in old_last_word + 1..stop_idx {
+        for idx in num_cur_blocks..stop_idx {
             self.storage[idx] = full_value;
         }
 
@@ -868,7 +868,7 @@ pub fn pop(&mut self) -> Option<bool> {
             // (3)
             self.set(i, false);
             self.nbits = i;
-            if self.nbits % u32::BITS == 0 {
+            if self.nbits % u32::BITS as usize == 0 {
                 // (2)
                 self.storage.pop();
             }
@@ -890,7 +890,7 @@ pub fn pop(&mut self) -> Option<bool> {
     /// ```
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn push(&mut self, elem: bool) {
-        if self.nbits % u32::BITS == 0 {
+        if self.nbits % u32::BITS as usize == 0 {
             self.storage.push(0);
         }
         let insert_pos = self.nbits;
@@ -912,7 +912,7 @@ pub fn is_empty(&self) -> bool { self.len() == 0 }
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn clear(&mut self) {
-        for w in &mut self.storage { *w = 0u32; }
+        for w in &mut self.storage { *w = 0; }
     }
 }
 
@@ -1406,7 +1406,7 @@ pub fn shrink_to_fit(&mut self) {
         // Truncate
         let trunc_len = cmp::max(old_len - n, 1);
         bit_vec.storage.truncate(trunc_len);
-        bit_vec.nbits = trunc_len * u32::BITS;
+        bit_vec.nbits = trunc_len * u32::BITS as usize;
     }
 
     /// Iterator over each u32 stored in the `BitSet`.
@@ -1663,7 +1663,7 @@ pub fn symmetric_difference_with(&mut self, other: &BitSet) {
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn len(&self) -> usize  {
-        self.bit_vec.blocks().fold(0, |acc, n| acc + n.count_ones())
+        self.bit_vec.blocks().fold(0, |acc, n| acc + n.count_ones() as usize)
     }
 
     /// Returns whether there are no bits set in this set
@@ -1831,13 +1831,13 @@ impl<'a> Iterator for TwoBitPositions<'a> {
     fn next(&mut self) -> Option<usize> {
         while self.next_idx < self.set.bit_vec.len() ||
               self.next_idx < self.other.bit_vec.len() {
-            let bit_idx = self.next_idx % u32::BITS;
+            let bit_idx = self.next_idx % u32::BITS as usize;
             if bit_idx == 0 {
                 let s_bit_vec = &self.set.bit_vec;
                 let o_bit_vec = &self.other.bit_vec;
                 // Merging the two words is a bit of an awkward dance since
                 // one BitVec might be longer than the other
-                let word_idx = self.next_idx / u32::BITS;
+                let word_idx = self.next_idx / u32::BITS as usize;
                 let w1 = if word_idx < s_bit_vec.storage.len() {
                              s_bit_vec.storage[word_idx]
                          } else { 0 };
@@ -2313,7 +2313,7 @@ fn test_bit_vec_iterator() {
 
         assert_eq!(bit_vec.iter().collect::<Vec<bool>>(), bools);
 
-        let long: Vec<_> = (0i32..10000).map(|i| i % 2 == 0).collect();
+        let long: Vec<_> = (0..10000).map(|i| i % 2 == 0).collect();
         let bit_vec: BitVec = long.iter().map(|n| *n).collect();
         assert_eq!(bit_vec.iter().collect::<Vec<bool>>(), long)
     }
@@ -2441,43 +2441,43 @@ fn test_big_bit_vec_tests() {
 
     #[test]
     fn test_bit_vec_push_pop() {
-        let mut s = BitVec::from_elem(5 * u32::BITS - 2, false);
-        assert_eq!(s.len(), 5 * u32::BITS - 2);
-        assert_eq!(s[5 * u32::BITS - 3], false);
+        let mut s = BitVec::from_elem(5 * u32::BITS as usize - 2, false);
+        assert_eq!(s.len(), 5 * u32::BITS as usize - 2);
+        assert_eq!(s[5 * u32::BITS as usize - 3], false);
         s.push(true);
         s.push(true);
-        assert_eq!(s[5 * u32::BITS - 2], true);
-        assert_eq!(s[5 * u32::BITS - 1], true);
+        assert_eq!(s[5 * u32::BITS as usize - 2], true);
+        assert_eq!(s[5 * u32::BITS as usize - 1], true);
         // Here the internal vector will need to be extended
         s.push(false);
-        assert_eq!(s[5 * u32::BITS], false);
+        assert_eq!(s[5 * u32::BITS as usize], false);
         s.push(false);
-        assert_eq!(s[5 * u32::BITS + 1], false);
-        assert_eq!(s.len(), 5 * u32::BITS + 2);
+        assert_eq!(s[5 * u32::BITS as usize + 1], false);
+        assert_eq!(s.len(), 5 * u32::BITS as usize + 2);
         // Pop it all off
         assert_eq!(s.pop(), Some(false));
         assert_eq!(s.pop(), Some(false));
         assert_eq!(s.pop(), Some(true));
         assert_eq!(s.pop(), Some(true));
-        assert_eq!(s.len(), 5 * u32::BITS - 2);
+        assert_eq!(s.len(), 5 * u32::BITS as usize - 2);
     }
 
     #[test]
     fn test_bit_vec_truncate() {
-        let mut s = BitVec::from_elem(5 * u32::BITS, true);
+        let mut s = BitVec::from_elem(5 * u32::BITS as usize, true);
 
-        assert_eq!(s, BitVec::from_elem(5 * u32::BITS, true));
-        assert_eq!(s.len(), 5 * u32::BITS);
-        s.truncate(4 * u32::BITS);
-        assert_eq!(s, BitVec::from_elem(4 * u32::BITS, true));
-        assert_eq!(s.len(), 4 * u32::BITS);
+        assert_eq!(s, BitVec::from_elem(5 * u32::BITS as usize, true));
+        assert_eq!(s.len(), 5 * u32::BITS as usize);
+        s.truncate(4 * u32::BITS as usize);
+        assert_eq!(s, BitVec::from_elem(4 * u32::BITS as usize, true));
+        assert_eq!(s.len(), 4 * u32::BITS as usize);
         // Truncating to a size > s.len() should be a noop
-        s.truncate(5 * u32::BITS);
-        assert_eq!(s, BitVec::from_elem(4 * u32::BITS, true));
-        assert_eq!(s.len(), 4 * u32::BITS);
-        s.truncate(3 * u32::BITS - 10);
-        assert_eq!(s, BitVec::from_elem(3 * u32::BITS - 10, true));
-        assert_eq!(s.len(), 3 * u32::BITS - 10);
+        s.truncate(5 * u32::BITS as usize);
+        assert_eq!(s, BitVec::from_elem(4 * u32::BITS as usize, true));
+        assert_eq!(s.len(), 4 * u32::BITS as usize);
+        s.truncate(3 * u32::BITS as usize - 10);
+        assert_eq!(s, BitVec::from_elem(3 * u32::BITS as usize - 10, true));
+        assert_eq!(s.len(), 3 * u32::BITS as usize - 10);
         s.truncate(0);
         assert_eq!(s, BitVec::from_elem(0, true));
         assert_eq!(s.len(), 0);
@@ -2485,26 +2485,26 @@ fn test_bit_vec_truncate() {
 
     #[test]
     fn test_bit_vec_reserve() {
-        let mut s = BitVec::from_elem(5 * u32::BITS, true);
+        let mut s = BitVec::from_elem(5 * u32::BITS as usize, true);
         // Check capacity
-        assert!(s.capacity() >= 5 * u32::BITS);
-        s.reserve(2 * u32::BITS);
-        assert!(s.capacity() >= 7 * u32::BITS);
-        s.reserve(7 * u32::BITS);
-        assert!(s.capacity() >= 12 * u32::BITS);
-        s.reserve_exact(7 * u32::BITS);
-        assert!(s.capacity() >= 12 * u32::BITS);
-        s.reserve(7 * u32::BITS + 1);
-        assert!(s.capacity() >= 12 * u32::BITS + 1);
+        assert!(s.capacity() >= 5 * u32::BITS as usize);
+        s.reserve(2 * u32::BITS as usize);
+        assert!(s.capacity() >= 7 * u32::BITS as usize);
+        s.reserve(7 * u32::BITS as usize);
+        assert!(s.capacity() >= 12 * u32::BITS as usize);
+        s.reserve_exact(7 * u32::BITS as usize);
+        assert!(s.capacity() >= 12 * u32::BITS as usize);
+        s.reserve(7 * u32::BITS as usize + 1);
+        assert!(s.capacity() >= 12 * u32::BITS as usize + 1);
         // Check that length hasn't changed
-        assert_eq!(s.len(), 5 * u32::BITS);
+        assert_eq!(s.len(), 5 * u32::BITS as usize);
         s.push(true);
         s.push(false);
         s.push(true);
-        assert_eq!(s[5 * u32::BITS - 1], true);
-        assert_eq!(s[5 * u32::BITS - 0], true);
-        assert_eq!(s[5 * u32::BITS + 1], false);
-        assert_eq!(s[5 * u32::BITS + 2], true);
+        assert_eq!(s[5 * u32::BITS as usize - 1], true);
+        assert_eq!(s[5 * u32::BITS as usize - 0], true);
+        assert_eq!(s[5 * u32::BITS as usize + 1], false);
+        assert_eq!(s[5 * u32::BITS as usize + 2], true);
     }
 
     #[test]
@@ -2544,7 +2544,7 @@ mod bit_vec_bench {
 
     use super::BitVec;
 
-    static BENCH_BITS : usize = 1 << 14;
+    const BENCH_BITS : usize = 1 << 14;
 
     fn rng() -> rand::IsaacRng {
         let seed: &[_] = &[1, 2, 3, 4, 5, 6, 7, 8, 9, 0];
@@ -2557,7 +2557,7 @@ fn bench_usize_small(b: &mut Bencher) {
         let mut bit_vec = 0 as usize;
         b.iter(|| {
             for _ in 0..100 {
-                bit_vec |= 1 << ((r.next_u32() as usize) % u32::BITS);
+                bit_vec |= 1 << ((r.next_u32() as usize) % u32::BITS as usize);
             }
             black_box(&bit_vec);
         });
@@ -2590,10 +2590,10 @@ fn bench_bit_set_big_variable(b: &mut Bencher) {
     #[bench]
     fn bench_bit_set_small(b: &mut Bencher) {
         let mut r = rng();
-        let mut bit_vec = BitVec::from_elem(u32::BITS, false);
+        let mut bit_vec = BitVec::from_elem(u32::BITS as usize, false);
         b.iter(|| {
             for _ in 0..100 {
-                bit_vec.set((r.next_u32() as usize) % u32::BITS, true);
+                bit_vec.set((r.next_u32() as usize) % u32::BITS as usize, true);
             }
             black_box(&bit_vec);
         });
@@ -2610,7 +2610,7 @@ fn bench_bit_vec_big_union(b: &mut Bencher) {
 
     #[bench]
     fn bench_bit_vec_small_iter(b: &mut Bencher) {
-        let bit_vec = BitVec::from_elem(u32::BITS, false);
+        let bit_vec = BitVec::from_elem(u32::BITS as usize, false);
         b.iter(|| {
             let mut sum = 0;
             for _ in 0..10 {
@@ -3039,7 +3039,7 @@ mod bit_set_bench {
 
     use super::{BitVec, BitSet};
 
-    static BENCH_BITS : usize = 1 << 14;
+    const BENCH_BITS : usize = 1 << 14;
 
     fn rng() -> rand::IsaacRng {
         let seed: &[_] = &[1, 2, 3, 4, 5, 6, 7, 8, 9, 0];
@@ -3052,7 +3052,7 @@ fn bench_bit_vecset_small(b: &mut Bencher) {
         let mut bit_vec = BitSet::new();
         b.iter(|| {
             for _ in 0..100 {
-                bit_vec.insert((r.next_u32() as usize) % u32::BITS);
+                bit_vec.insert((r.next_u32() as usize) % u32::BITS as usize);
             }
             black_box(&bit_vec);
         });
index 8a3a1fcb9f387a8bc060a4f29eb0983a2ae9372c..1fa592ac477a243cf3f9010c51d8b4a6749cb8bd 100644 (file)
@@ -25,7 +25,7 @@
 use core::hash::{Hash, Hasher};
 use core::iter::{Map, FromIterator, IntoIterator};
 use core::ops::{Index, IndexMut};
-use core::{iter, fmt, mem};
+use core::{iter, fmt, mem, usize};
 use Bound::{self, Included, Excluded, Unbounded};
 
 use borrow::Borrow;
@@ -1467,7 +1467,7 @@ macro_rules! range_impl {
             $Range {
                 inner: AbsIter {
                     traversals: traversals,
-                    size: 0, // unused
+                    size: usize::MAX, // unused
                 }
             }
         }
index 4a80d75575e6db431b400987e05bf0b4c4d9d383..f2a6910a30252469d22bdafd6d5c6a127a114e44 100644 (file)
@@ -1215,7 +1215,8 @@ unsafe fn remove_edge(&mut self, index: usize) -> Node<K, V> {
         ptr::copy(
             self.edges_mut().as_mut_ptr().offset(index as isize),
             self.edges().as_ptr().offset(index as isize + 1),
-            self.len() - index + 1
+            // index can be == len+1, so do the +1 first to avoid underflow.
+            (self.len() + 1) - index
         );
 
         edge
index 62dd91915211b85a37aa1295c52ffa6b4439e6b8..68ff94cfbfb942f33ec251dceee5941156f5a90b 100644 (file)
@@ -78,7 +78,7 @@ pub trait CLike {
 fn bit<E:CLike>(e: &E) -> usize {
     use core::usize;
     let value = e.to_usize();
-    assert!(value < usize::BITS,
+    assert!(value < usize::BITS as usize,
             "EnumSet only supports up to {} variants.", usize::BITS - 1);
     1 << value
 }
@@ -95,7 +95,7 @@ pub fn new() -> EnumSet<E> {
     #[unstable(feature = "collections",
                reason = "matches collection reform specification, waiting for dust to settle")]
     pub fn len(&self) -> usize {
-        self.bits.count_ones()
+        self.bits.count_ones() as usize
     }
 
     /// Returns true if the `EnumSet` is empty.
@@ -250,7 +250,7 @@ fn next(&mut self) -> Option<E> {
     }
 
     fn size_hint(&self) -> (usize, Option<usize>) {
-        let exact = self.bits.count_ones();
+        let exact = self.bits.count_ones() as usize;
         (exact, Some(exact))
     }
 }
@@ -490,7 +490,7 @@ fn test_operators() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_overflow() {
         #[allow(dead_code)]
         #[derive(Copy)]
index 98673af3c68a84ab3b6e7b3a9cea8094ec8d2796..15a66bd80d02b32507286f2f174448a5412e113e 100644 (file)
 //!         // for details, and the function `pad` can be used to pad strings.
 //!         let decimals = f.precision().unwrap_or(3);
 //!         let string = f64::to_str_exact(magnitude, decimals);
-//!         f.pad_integral(true, "", string.as_slice())
+//!         f.pad_integral(true, "", &string)
 //!     }
 //! }
 //!
 //! Some examples of the output from both traits:
 //!
 //! ```
-//! assert_eq!(format!("{} {:?}", 3i32, 4i32), "3 4");
+//! assert_eq!(format!("{} {:?}", 3, 4), "3 4");
 //! assert_eq!(format!("{} {:?}", 'a', 'b'), "a 'b'");
 //! assert_eq!(format!("{} {:?}", "foo\n", "bar\n"), "foo\n \"bar\\n\"");
 //! ```
 //!     * `o` - precedes the argument with a "0o"
 //! * '0' - This is used to indicate for integer formats that the padding should
 //!         both be done with a `0` character as well as be sign-aware. A format
-//!         like `{:08d}` would yield `00000001` for the integer `1`, while the
+//!         like `{:08}` would yield `00000001` for the integer `1`, while the
 //!         same format would yield `-0000001` for the integer `-1`. Notice that
 //!         the negative version has one fewer zero than the positive version.
 //!
index 7b66bfee34f2121b15f4e06ae47e832ed4a7edcf..9c1c2cc5906ebca14ebd09ae361595ba4a9ad73d 100644 (file)
@@ -12,7 +12,8 @@
 //!
 //! See [std::collections](../std/collections) for a detailed discussion of collections in Rust.
 
-
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "collections"]
 #![unstable(feature = "collections")]
 #![staged_api]
index 9b5fbfc25114c046012f4f7e2e2748c004017146..5ca3cb380583bc3e5580048b779d9a9ac42e8ccc 100644 (file)
@@ -984,7 +984,7 @@ pub fn check_links<T>(list: &LinkedList<T>) {
 
     #[test]
     fn test_basic() {
-        let mut m = LinkedList::new();
+        let mut m = LinkedList::<Box<_>>::new();
         assert_eq!(m.pop_front(), None);
         assert_eq!(m.pop_back(), None);
         assert_eq!(m.pop_front(), None);
index a2924f8fe53082bb2b6ff4843f20abd07a61c57a..cffa4bbfbf41134bf12a04d9ed8163bb88ade7a4 100644 (file)
@@ -96,6 +96,7 @@
 use core::marker::Sized;
 use core::mem::size_of;
 use core::mem;
+use core::num::wrapping::WrappingOps;
 use core::ops::FnMut;
 use core::option::Option::{self, Some, None};
 use core::ptr::PtrExt;
@@ -1209,10 +1210,14 @@ struct SizeDirection {
 impl Iterator for ElementSwaps {
     type Item = (usize, usize);
 
-    #[inline]
+    // #[inline]
     fn next(&mut self) -> Option<(usize, usize)> {
+        fn new_pos_wrapping(i: usize, s: Direction) -> usize {
+            i.wrapping_add(match s { Pos => 1, Neg => -1 })
+        }
+
         fn new_pos(i: usize, s: Direction) -> usize {
-            i + match s { Pos => 1, Neg => -1 }
+            match s { Pos => i + 1, Neg => i - 1 }
         }
 
         // Find the index of the largest mobile element:
@@ -1220,7 +1225,7 @@ fn new_pos(i: usize, s: Direction) -> usize {
         // swap should be with a smaller `size` element.
         let max = self.sdir.iter().cloned().enumerate()
                            .filter(|&(i, sd)|
-                                new_pos(i, sd.dir) < self.sdir.len() &&
+                                new_pos_wrapping(i, sd.dir) < self.sdir.len() &&
                                 self.sdir[new_pos(i, sd.dir)].size < sd.size)
                            .max_by(|&(_, sd)| sd.size);
         match max {
@@ -1343,8 +1348,8 @@ fn insertion_sort<T, F>(v: &mut [T], mut compare: F) where F: FnMut(&T, &T) -> O
 
 fn merge_sort<T, F>(v: &mut [T], mut compare: F) where F: FnMut(&T, &T) -> Ordering {
     // warning: this wildly uses unsafe.
-    static BASE_INSERTION: usize = 32;
-    static LARGE_INSERTION: usize = 16;
+    const BASE_INSERTION: usize = 32;
+    const LARGE_INSERTION: usize = 16;
 
     // FIXME #12092: smaller insertion runs seems to make sorting
     // vectors of large elements a little faster on some platforms,
@@ -1504,6 +1509,7 @@ unsafe fn step<T>(ptr: &mut *mut T) -> *mut T {
 
 #[cfg(test)]
 mod tests {
+    use alloc::boxed::Box;
     use core::cmp::Ordering::{Greater, Less, Equal};
     use core::prelude::{Some, None, Clone};
     use core::prelude::{Iterator, IteratorExt};
@@ -1641,14 +1647,14 @@ fn test_tail_mut() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_tail_empty() {
         let a = Vec::<i32>::new();
         a.tail();
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_tail_mut_empty() {
         let mut a = Vec::<i32>::new();
         a.tail_mut();
@@ -1675,14 +1681,14 @@ fn test_init_mut() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_init_empty() {
         let a = Vec::<i32>::new();
         a.init();
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_init_mut_empty() {
         let mut a = Vec::<i32>::new();
         a.init_mut();
@@ -1784,7 +1790,7 @@ fn test_swap_remove() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_swap_remove_fail() {
         let mut v = vec![1];
         let _ = v.swap_remove(0);
@@ -1794,7 +1800,7 @@ fn test_swap_remove_fail() {
     #[test]
     fn test_swap_remove_noncopyable() {
         // Tests that we don't accidentally run destructors twice.
-        let mut v = Vec::new();
+        let mut v: Vec<Box<_>> = Vec::new();
         v.push(box 0u8);
         v.push(box 0u8);
         v.push(box 0u8);
@@ -1823,7 +1829,7 @@ fn test_push() {
 
     #[test]
     fn test_truncate() {
-        let mut v = vec![box 6,box 5,box 4];
+        let mut v: Vec<Box<_>> = vec![box 6,box 5,box 4];
         v.truncate(1);
         let v = v;
         assert_eq!(v.len(), 1);
@@ -1833,7 +1839,7 @@ fn test_truncate() {
 
     #[test]
     fn test_clear() {
-        let mut v = vec![box 6,box 5,box 4];
+        let mut v: Vec<Box<_>> = vec![box 6,box 5,box 4];
         v.clear();
         assert_eq!(v.len(), 0);
         // If the unsafe block didn't drop things properly, we blow up here.
@@ -1858,11 +1864,11 @@ fn case(a: Vec<i32>, b: Vec<i32>) {
 
     #[test]
     fn test_dedup_unique() {
-        let mut v0 = vec![box 1, box 1, box 2, box 3];
+        let mut v0: Vec<Box<_>> = vec![box 1, box 1, box 2, box 3];
         v0.dedup();
-        let mut v1 = vec![box 1, box 2, box 2, box 3];
+        let mut v1: Vec<Box<_>> = vec![box 1, box 2, box 2, box 3];
         v1.dedup();
-        let mut v2 = vec![box 1, box 2, box 3, box 3];
+        let mut v2: Vec<Box<_>> = vec![box 1, box 2, box 3, box 3];
         v2.dedup();
         /*
          * If the boxed pointers were leaked or otherwise misused, valgrind
@@ -1872,11 +1878,11 @@ fn test_dedup_unique() {
 
     #[test]
     fn test_dedup_shared() {
-        let mut v0 = vec![box 1, box 1, box 2, box 3];
+        let mut v0: Vec<Box<_>> = vec![box 1, box 1, box 2, box 3];
         v0.dedup();
-        let mut v1 = vec![box 1, box 2, box 2, box 3];
+        let mut v1: Vec<Box<_>> = vec![box 1, box 2, box 2, box 3];
         v1.dedup();
-        let mut v2 = vec![box 1, box 2, box 3, box 3];
+        let mut v2: Vec<Box<_>> = vec![box 1, box 2, box 3, box 3];
         v2.dedup();
         /*
          * If the pointers were leaked or otherwise misused, valgrind and/or
@@ -2170,8 +2176,8 @@ fn test_concat() {
     fn test_connect() {
         let v: [Vec<i32>; 0] = [];
         assert_eq!(v.connect(&0), []);
-        assert_eq!([vec![1i], vec![2, 3]].connect(&0), [1, 0, 2, 3]);
-        assert_eq!([vec![1i], vec![2], vec![3]].connect(&0), [1, 0, 2, 0, 3]);
+        assert_eq!([vec![1], vec![2, 3]].connect(&0), [1, 0, 2, 3]);
+        assert_eq!([vec![1], vec![2], vec![3]].connect(&0), [1, 0, 2, 0, 3]);
 
         let v: [&[_]; 2] = [&[1], &[2, 3]];
         assert_eq!(v.connect(&0), [1, 0, 2, 3]);
@@ -2199,7 +2205,7 @@ fn test_insert() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_insert_oob() {
         let mut a = vec![1, 2, 3];
         a.insert(4, 5);
@@ -2223,7 +2229,7 @@ fn test_remove() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_remove_fail() {
         let mut a = vec![1];
         let _ = a.remove(0);
@@ -2247,10 +2253,11 @@ fn test_slice_2() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_permute_fail() {
-        let v = [(box 0, Rc::new(0)), (box 0, Rc::new(0)),
-                 (box 0, Rc::new(0)), (box 0, Rc::new(0))];
+        let v: [(Box<_>, Rc<_>); 4] =
+            [(box 0, Rc::new(0)), (box 0, Rc::new(0)),
+             (box 0, Rc::new(0)), (box 0, Rc::new(0))];
         let mut i = 0;
         for _ in v.permutations() {
             if i == 2 {
@@ -2521,7 +2528,7 @@ fn test_windowsator() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_windowsator_0() {
         let v = &[1,2,3,4];
         let _it = v.windows(0);
@@ -2557,7 +2564,7 @@ fn test_chunksator() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_chunksator_0() {
         let v = &[1,2,3,4];
         let _it = v.chunks(0);
@@ -2632,7 +2639,7 @@ macro_rules! t {
     #[test]
     fn test_bytes_set_memory() {
         use slice::bytes::MutableByteVector;
-        let mut values = [1u8,2,3,4,5];
+        let mut values = [1,2,3,4,5];
         values[0..5].set_memory(0xAB);
         assert!(values == [0xAB, 0xAB, 0xAB, 0xAB, 0xAB]);
         values[2..4].set_memory(0xFF);
@@ -2640,7 +2647,7 @@ fn test_bytes_set_memory() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_overflow_does_not_cause_segfault() {
         let mut v = vec![];
         v.reserve_exact(-1);
@@ -2649,7 +2656,7 @@ fn test_overflow_does_not_cause_segfault() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_overflow_does_not_cause_segfault_managed() {
         let mut v = vec![Rc::new(1)];
         v.reserve_exact(-1);
@@ -2802,31 +2809,31 @@ fn test_get_mut() {
     fn test_mut_chunks() {
         use core::iter::ExactSizeIterator;
 
-        let mut v = [0u8, 1, 2, 3, 4, 5, 6];
+        let mut v = [0, 1, 2, 3, 4, 5, 6];
         assert_eq!(v.chunks_mut(2).len(), 4);
         for (i, chunk) in v.chunks_mut(3).enumerate() {
             for x in chunk {
                 *x = i as u8;
             }
         }
-        let result = [0u8, 0, 0, 1, 1, 1, 2];
+        let result = [0, 0, 0, 1, 1, 1, 2];
         assert!(v == result);
     }
 
     #[test]
     fn test_mut_chunks_rev() {
-        let mut v = [0u8, 1, 2, 3, 4, 5, 6];
+        let mut v = [0, 1, 2, 3, 4, 5, 6];
         for (i, chunk) in v.chunks_mut(3).rev().enumerate() {
             for x in chunk {
                 *x = i as u8;
             }
         }
-        let result = [2u8, 2, 2, 1, 1, 1, 0];
+        let result = [2, 2, 2, 1, 1, 1, 0];
         assert!(v == result);
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_mut_chunks_0() {
         let mut v = [1, 2, 3, 4];
         let _it = v.chunks_mut(0);
@@ -2844,7 +2851,7 @@ fn test_mut_last() {
 
     #[test]
     fn test_to_vec() {
-        let xs = box [1, 2, 3];
+        let xs: Box<_> = box [1, 2, 3];
         let ys = xs.to_vec();
         assert_eq!(ys, [1, 2, 3]);
     }
index 86fcac3e4b8a09ca34e98ab499568c3bb83153f4..28df6cf96d7e5e28010e9d6223f059658311e382 100644 (file)
 //
 // ignore-lexer-test FIXME #15679
 
-//! Unicode string manipulation (the `str` type).
+//! Unicode string manipulation (the [`str`](../primitive.str.html) type).
 //!
-//! Rust's `str` type is one of the core primitive types of the language. `&str` is the borrowed
-//! string type. This type of string can only be created from other strings, unless it is a static
-//! string (see below). As the word "borrowed" implies, this type of string is owned elsewhere, and
-//! this string cannot be moved out of.
+//! Rust's [`str`](../primitive.str.html) type is one of the core primitive
+//! types of the language. `&str` is the borrowed string type. This type of
+//! string can only be created from other strings, unless it is a `&'static str`
+//! (see below). It is not possible to move out of borrowed strings because they
+//! are owned elsewhere.
+//!
+//! Basic operations are implemented directly by the compiler, but more advanced
+//! operations are defined on the [`StrExt`](trait.StrExt.html) trait.
 //!
 //! # Examples
 //!
@@ -25,8 +29,9 @@
 //! let s = "Hello, world.";
 //! ```
 //!
-//! This `&str` is a `&'static str`, which is the type of string literals. They're `'static`
-//! because literals are available for the entire lifetime of the program.
+//! This `&str` is a `&'static str`, which is the type of string literals.
+//! They're `'static` because literals are available for the entire lifetime of
+//! the program.
 //!
 //! You can get a non-`'static` `&str` by taking a slice of a `String`:
 //!
 //!
 //! # Representation
 //!
-//! Rust's string type, `str`, is a sequence of Unicode scalar values encoded as a stream of UTF-8
-//! bytes. All [strings](../../reference.html#literals) are guaranteed to be validly encoded UTF-8
-//! sequences. Additionally, strings are not null-terminated and can thus contain null bytes.
+//! Rust's string type, `str`, is a sequence of Unicode scalar values encoded as
+//! a stream of UTF-8 bytes. All [strings](../../reference.html#literals) are
+//! guaranteed to be validly encoded UTF-8 sequences. Additionally, strings are
+//! not null-terminated and can thus contain null bytes.
 //!
-//! The actual representation of `str`s have direct mappings to slices: `&str` is the same as
-//! `&[u8]`.
+//! The actual representation of `str`s have direct mappings to slices: `&str`
+//! is the same as `&[u8]`.
 
 #![doc(primitive = "str")]
 #![stable(feature = "rust1", since = "1.0.0")]
 use self::RecompositionState::*;
 use self::DecompositionType::*;
 
-use core::char::CharExt;
 use core::clone::Clone;
 use core::iter::AdditiveIterator;
-use core::iter::{Iterator, IteratorExt};
+use core::iter::{Iterator, IteratorExt, Extend};
 use core::ops::Index;
 use core::ops::RangeFull;
 use core::option::Option::{self, Some, None};
 use core::result::Result;
 use core::slice::AsSlice;
 use core::str as core_str;
+use unicode::char::CharExt;
 use unicode::str::{UnicodeStr, Utf16Encoder};
 
 use vec_deque::VecDeque;
@@ -383,7 +389,7 @@ macro_rules! utf8_first_byte {
 
 // return the value of $ch updated with continuation byte $byte
 macro_rules! utf8_acc_cont_byte {
-    ($ch:expr, $byte:expr) => (($ch << 6) | ($byte & 63u8) as u32)
+    ($ch:expr, $byte:expr) => (($ch << 6) | ($byte & 63) as u32)
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
@@ -756,6 +762,7 @@ fn match_indices<'a, P: Pattern<'a>>(&'a self, pat: P) -> MatchIndices<'a, P> {
     /// ```
     #[unstable(feature = "collections")]
     #[deprecated(since = "1.0.0", reason = "use `split()` with a `&str`")]
+    #[allow(deprecated) /* for SplitStr */]
     fn split_str<'a, P: Pattern<'a>>(&'a self, pat: P) -> SplitStr<'a, P> {
         core_str::StrExt::split_str(&self[..], pat)
     }
@@ -832,17 +839,19 @@ fn lines_any(&self) -> LinesAny {
 
     /// Returns a slice of the string from the character range [`begin`..`end`).
     ///
-    /// That is, start at the `begin`-th code point of the string and continue to the `end`-th code
-    /// point. This does not detect or handle edge cases such as leaving a combining character as
-    /// the first code point of the string.
+    /// That is, start at the `begin`-th code point of the string and continue
+    /// to the `end`-th code point. This does not detect or handle edge cases
+    /// such as leaving a combining character as the first code point of the
+    /// string.
     ///
-    /// Due to the design of UTF-8, this operation is `O(end)`. See `slice`, `slice_to` and
-    /// `slice_from` for `O(1)` variants that use byte indices rather than code point indices.
+    /// Due to the design of UTF-8, this operation is `O(end)`. See `slice`,
+    /// `slice_to` and `slice_from` for `O(1)` variants that use byte indices
+    /// rather than code point indices.
     ///
     /// # Panics
     ///
-    /// Panics if `begin` > `end` or the either `begin` or `end` are beyond the last character of
-    /// the string.
+    /// Panics if `begin` > `end` or the either `begin` or `end` are beyond the
+    /// last character of the string.
     ///
     /// # Examples
     ///
@@ -864,8 +873,8 @@ fn slice_chars(&self, begin: usize, end: usize) -> &str {
     ///
     /// # Unsafety
     ///
-    /// Caller must check both UTF-8 character boundaries and the boundaries of the entire slice as
-    /// well.
+    /// Caller must check both UTF-8 character boundaries and the boundaries of
+    /// the entire slice as well.
     ///
     /// # Examples
     ///
@@ -1082,7 +1091,7 @@ fn char_range_at(&self, start: usize) -> CharRange {
     ///
     /// let s = "中华Việt Nam";
     /// let mut i = s.len();
-    /// while i < 0 {
+    /// while i > 0 {
     ///     let CharRange {ch, next} = s.char_range_at_reverse(i);
     ///     println!("{}: {}", i, ch);
     ///     i = next;
@@ -1502,6 +1511,32 @@ fn trim_left(&self) -> &str {
     fn trim_right(&self) -> &str {
         UnicodeStr::trim_right(&self[..])
     }
+
+    /// Returns the lowercase equivalent of this string.
+    ///
+    /// # Examples
+    ///
+    /// let s = "HELLO";
+    /// assert_eq!(s.to_lowercase(), "hello");
+    #[unstable(feature = "collections")]
+    fn to_lowercase(&self) -> String {
+        let mut s = String::with_capacity(self.len());
+        s.extend(self[..].chars().flat_map(|c| c.to_lowercase()));
+        return s;
+    }
+
+    /// Returns the uppercase equivalent of this string.
+    ///
+    /// # Examples
+    ///
+    /// let s = "hello";
+    /// assert_eq!(s.to_uppercase(), "HELLO");
+    #[unstable(feature = "collections")]
+    fn to_uppercase(&self) -> String {
+        let mut s = String::with_capacity(self.len());
+        s.extend(self[..].chars().flat_map(|c| c.to_uppercase()));
+        return s;
+    }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
@@ -1873,7 +1908,7 @@ fn test_slice_2() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_slice_fail() {
         "中华Việt Nam".slice(0, 2);
     }
@@ -2091,7 +2126,7 @@ fn test_as_bytes() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_as_bytes_fail() {
         // Don't double free. (I'm not sure if this exercises the
         // original problem code path anymore.)
@@ -2128,7 +2163,7 @@ fn test_subslice_offset() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_subslice_offset_2() {
         let a = "alchemiter";
         let b = "cruxtruder";
@@ -2299,8 +2334,8 @@ fn test_rev_iterator() {
 
     #[test]
     fn test_chars_decoding() {
-        let mut bytes = [0u8; 4];
-        for c in (0u32..0x110000).filter_map(|c| ::core::char::from_u32(c)) {
+        let mut bytes = [0; 4];
+        for c in (0..0x110000).filter_map(|c| ::core::char::from_u32(c)) {
             let len = c.encode_utf8(&mut bytes).unwrap_or(0);
             let s = ::core::str::from_utf8(&bytes[..len]).unwrap();
             if Some(c) != s.chars().next() {
@@ -2311,8 +2346,8 @@ fn test_chars_decoding() {
 
     #[test]
     fn test_chars_rev_decoding() {
-        let mut bytes = [0u8; 4];
-        for c in (0u32..0x110000).filter_map(|c| ::core::char::from_u32(c)) {
+        let mut bytes = [0; 4];
+        for c in (0..0x110000).filter_map(|c| ::core::char::from_u32(c)) {
             let len = c.encode_utf8(&mut bytes).unwrap_or(0);
             let s = ::core::str::from_utf8(&bytes[..len]).unwrap();
             if Some(c) != s.chars().rev().next() {
index 94abffa3db61cf6c33d24e87807af67e419fe1a1..83c63e47e506b8d977032561f5e531875b8ac28e 100644 (file)
@@ -139,7 +139,7 @@ pub fn from_utf8(vec: Vec<u8>) -> Result<String, FromUtf8Error> {
     /// ```rust
     /// let input = b"Hello \xF0\x90\x80World";
     /// let output = String::from_utf8_lossy(input);
-    /// assert_eq!(output.as_slice(), "Hello \u{FFFD}World");
+    /// assert_eq!(output, "Hello \u{FFFD}World");
     /// ```
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn from_utf8_lossy<'a>(v: &'a [u8]) -> Cow<'a, str> {
@@ -153,8 +153,8 @@ pub fn from_utf8_lossy<'a>(v: &'a [u8]) -> Cow<'a, str> {
             }
         }
 
-        static TAG_CONT_U8: u8 = 128u8;
-        static REPLACEMENT: &'static [u8] = b"\xEF\xBF\xBD"; // U+FFFD in UTF-8
+        const TAG_CONT_U8: u8 = 128;
+        const REPLACEMENT: &'static [u8] = b"\xEF\xBF\xBD"; // U+FFFD in UTF-8
         let total = v.len();
         fn unsafe_get(xs: &[u8], i: usize) -> u8 {
             unsafe { *xs.get_unchecked(i) }
@@ -195,14 +195,14 @@ macro_rules! error { () => ({
                 }
             })}
 
-            if byte < 128u8 {
+            if byte < 128 {
                 // subseqidx handles this
             } else {
                 let w = unicode_str::utf8_char_width(byte);
 
                 match w {
                     2 => {
-                        if safe_get(v, i, total) & 192u8 != TAG_CONT_U8 {
+                        if safe_get(v, i, total) & 192 != TAG_CONT_U8 {
                             error!();
                             continue;
                         }
@@ -220,7 +220,7 @@ macro_rules! error { () => ({
                             }
                         }
                         i += 1;
-                        if safe_get(v, i, total) & 192u8 != TAG_CONT_U8 {
+                        if safe_get(v, i, total) & 192 != TAG_CONT_U8 {
                             error!();
                             continue;
                         }
@@ -237,12 +237,12 @@ macro_rules! error { () => ({
                             }
                         }
                         i += 1;
-                        if safe_get(v, i, total) & 192u8 != TAG_CONT_U8 {
+                        if safe_get(v, i, total) & 192 != TAG_CONT_U8 {
                             error!();
                             continue;
                         }
                         i += 1;
-                        if safe_get(v, i, total) & 192u8 != TAG_CONT_U8 {
+                        if safe_get(v, i, total) & 192 != TAG_CONT_U8 {
                             error!();
                             continue;
                         }
@@ -355,7 +355,7 @@ pub fn into_bytes(self) -> Vec<u8> {
     /// ```
     /// let mut s = String::from_str("foo");
     /// s.push_str("bar");
-    /// assert_eq!(s.as_slice(), "foobar");
+    /// assert_eq!(s, "foobar");
     /// ```
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
@@ -450,7 +450,7 @@ pub fn shrink_to_fit(&mut self) {
     /// s.push('1');
     /// s.push('2');
     /// s.push('3');
-    /// assert_eq!(s.as_slice(), "abc123");
+    /// assert_eq!(s, "abc123");
     /// ```
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
@@ -503,7 +503,7 @@ pub fn as_bytes(&self) -> &[u8] {
     /// ```
     /// let mut s = String::from_str("hello");
     /// s.truncate(2);
-    /// assert_eq!(s.as_slice(), "he");
+    /// assert_eq!(s, "he");
     /// ```
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
@@ -622,7 +622,7 @@ pub fn insert(&mut self, idx: usize, ch: char) {
     ///     assert!(vec == &[104, 101, 108, 108, 111]);
     ///     vec.reverse();
     /// }
-    /// assert_eq!(s.as_slice(), "olleh");
+    /// assert_eq!(s, "olleh");
     /// ```
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
@@ -1084,40 +1084,40 @@ fn test_from_utf8_lossy() {
     fn test_from_utf16() {
         let pairs =
             [(String::from_str("𐍅𐌿𐌻𐍆𐌹𐌻𐌰\n"),
-              vec![0xd800_u16, 0xdf45_u16, 0xd800_u16, 0xdf3f_u16,
-                0xd800_u16, 0xdf3b_u16, 0xd800_u16, 0xdf46_u16,
-                0xd800_u16, 0xdf39_u16, 0xd800_u16, 0xdf3b_u16,
-                0xd800_u16, 0xdf30_u16, 0x000a_u16]),
+              vec![0xd800, 0xdf45, 0xd800, 0xdf3f,
+                0xd800, 0xdf3b, 0xd800, 0xdf46,
+                0xd800, 0xdf39, 0xd800, 0xdf3b,
+                0xd800, 0xdf30, 0x000a]),
 
              (String::from_str("𐐒𐑉𐐮𐑀𐐲𐑋 𐐏𐐲𐑍\n"),
-              vec![0xd801_u16, 0xdc12_u16, 0xd801_u16,
-                0xdc49_u16, 0xd801_u16, 0xdc2e_u16, 0xd801_u16,
-                0xdc40_u16, 0xd801_u16, 0xdc32_u16, 0xd801_u16,
-                0xdc4b_u16, 0x0020_u16, 0xd801_u16, 0xdc0f_u16,
-                0xd801_u16, 0xdc32_u16, 0xd801_u16, 0xdc4d_u16,
-                0x000a_u16]),
+              vec![0xd801, 0xdc12, 0xd801,
+                0xdc49, 0xd801, 0xdc2e, 0xd801,
+                0xdc40, 0xd801, 0xdc32, 0xd801,
+                0xdc4b, 0x0020, 0xd801, 0xdc0f,
+                0xd801, 0xdc32, 0xd801, 0xdc4d,
+                0x000a]),
 
              (String::from_str("𐌀𐌖𐌋𐌄𐌑𐌉·𐌌𐌄𐌕𐌄𐌋𐌉𐌑\n"),
-              vec![0xd800_u16, 0xdf00_u16, 0xd800_u16, 0xdf16_u16,
-                0xd800_u16, 0xdf0b_u16, 0xd800_u16, 0xdf04_u16,
-                0xd800_u16, 0xdf11_u16, 0xd800_u16, 0xdf09_u16,
-                0x00b7_u16, 0xd800_u16, 0xdf0c_u16, 0xd800_u16,
-                0xdf04_u16, 0xd800_u16, 0xdf15_u16, 0xd800_u16,
-                0xdf04_u16, 0xd800_u16, 0xdf0b_u16, 0xd800_u16,
-                0xdf09_u16, 0xd800_u16, 0xdf11_u16, 0x000a_u16 ]),
+              vec![0xd800, 0xdf00, 0xd800, 0xdf16,
+                0xd800, 0xdf0b, 0xd800, 0xdf04,
+                0xd800, 0xdf11, 0xd800, 0xdf09,
+                0x00b7, 0xd800, 0xdf0c, 0xd800,
+                0xdf04, 0xd800, 0xdf15, 0xd800,
+                0xdf04, 0xd800, 0xdf0b, 0xd800,
+                0xdf09, 0xd800, 0xdf11, 0x000a ]),
 
              (String::from_str("𐒋𐒘𐒈𐒑𐒛𐒒 𐒕𐒓 𐒈𐒚𐒍 𐒏𐒜𐒒𐒖𐒆 𐒕𐒆\n"),
-              vec![0xd801_u16, 0xdc8b_u16, 0xd801_u16, 0xdc98_u16,
-                0xd801_u16, 0xdc88_u16, 0xd801_u16, 0xdc91_u16,
-                0xd801_u16, 0xdc9b_u16, 0xd801_u16, 0xdc92_u16,
-                0x0020_u16, 0xd801_u16, 0xdc95_u16, 0xd801_u16,
-                0xdc93_u16, 0x0020_u16, 0xd801_u16, 0xdc88_u16,
-                0xd801_u16, 0xdc9a_u16, 0xd801_u16, 0xdc8d_u16,
-                0x0020_u16, 0xd801_u16, 0xdc8f_u16, 0xd801_u16,
-                0xdc9c_u16, 0xd801_u16, 0xdc92_u16, 0xd801_u16,
-                0xdc96_u16, 0xd801_u16, 0xdc86_u16, 0x0020_u16,
-                0xd801_u16, 0xdc95_u16, 0xd801_u16, 0xdc86_u16,
-                0x000a_u16 ]),
+              vec![0xd801, 0xdc8b, 0xd801, 0xdc98,
+                0xd801, 0xdc88, 0xd801, 0xdc91,
+                0xd801, 0xdc9b, 0xd801, 0xdc92,
+                0x0020, 0xd801, 0xdc95, 0xd801,
+                0xdc93, 0x0020, 0xd801, 0xdc88,
+                0xd801, 0xdc9a, 0xd801, 0xdc8d,
+                0x0020, 0xd801, 0xdc8f, 0xd801,
+                0xdc9c, 0xd801, 0xdc92, 0xd801,
+                0xdc96, 0xd801, 0xdc86, 0x0020,
+                0xd801, 0xdc95, 0xd801, 0xdc86,
+                0x000a ]),
              // Issue #12318, even-numbered non-BMP planes
              (String::from_str("\u{20000}"),
               vec![0xD840, 0xDC00])];
@@ -1232,14 +1232,14 @@ fn test_str_truncate() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_str_truncate_invalid_len() {
         let mut s = String::from_str("12345");
         s.truncate(6);
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_str_truncate_split_codepoint() {
         let mut s = String::from_str("\u{FC}"); // ü
         s.truncate(1);
@@ -1272,7 +1272,7 @@ fn remove() {
         assert_eq!(s, "ไทย中华Vit Nam; foobar");
     }
 
-    #[test] #[should_fail]
+    #[test] #[should_panic]
     fn remove_bad() {
         "ศ".to_string().remove(1);
     }
@@ -1286,8 +1286,8 @@ fn insert() {
         assert_eq!(s, "ệfooยbar");
     }
 
-    #[test] #[should_fail] fn insert_bad1() { "".to_string().insert(1, 't'); }
-    #[test] #[should_fail] fn insert_bad2() { "ệ".to_string().insert(1, 't'); }
+    #[test] #[should_panic] fn insert_bad1() { "".to_string().insert(1, 't'); }
+    #[test] #[should_panic] fn insert_bad2() { "ệ".to_string().insert(1, 't'); }
 
     #[test]
     fn test_slicing() {
@@ -1303,7 +1303,7 @@ fn test_simple_types() {
         assert_eq!(1.to_string(), "1");
         assert_eq!((-1).to_string(), "-1");
         assert_eq!(200.to_string(), "200");
-        assert_eq!(2u8.to_string(), "2");
+        assert_eq!(2.to_string(), "2");
         assert_eq!(true.to_string(), "true");
         assert_eq!(false.to_string(), "false");
         assert_eq!(("hi".to_string()).to_string(), "hi");
@@ -1421,7 +1421,7 @@ fn from_utf8_lossy_invalid(b: &mut Bencher) {
 
     #[bench]
     fn from_utf8_lossy_100_invalid(b: &mut Bencher) {
-        let s = repeat(0xf5u8).take(100).collect::<Vec<_>>();
+        let s = repeat(0xf5).take(100).collect::<Vec<_>>();
         b.iter(|| {
             let _ = String::from_utf8_lossy(&s);
         });
index 805e4623396b849b22041fc1281d42b3406f7067..ca0092a6e66ddb942c07d2b2b0cb8c55d6c38776 100644 (file)
@@ -1499,9 +1499,9 @@ fn extend<I: IntoIterator<Item=T>>(&mut self, iterable: I) {
 __impl_slice_eq1! { Vec<A>, Vec<B> }
 __impl_slice_eq2! { Vec<A>, &'b [B] }
 __impl_slice_eq2! { Vec<A>, &'b mut [B] }
-__impl_slice_eq2! { CowVec<'a, A>, &'b [B], Clone }
-__impl_slice_eq2! { CowVec<'a, A>, &'b mut [B], Clone }
-__impl_slice_eq2! { CowVec<'a, A>, Vec<B>, Clone }
+__impl_slice_eq2! { Cow<'a, [A]>, &'b [B], Clone }
+__impl_slice_eq2! { Cow<'a, [A]>, &'b mut [B], Clone }
+__impl_slice_eq2! { Cow<'a, [A]>, Vec<B>, Clone }
 
 macro_rules! array_impls {
     ($($N: expr)+) => {
@@ -1510,9 +1510,9 @@ macro_rules! array_impls {
             __impl_slice_eq2! { Vec<A>, [B; $N] }
             __impl_slice_eq2! { Vec<A>, &'b [B; $N] }
             // __impl_slice_eq2! { Vec<A>, &'b mut [B; $N] }
-            // __impl_slice_eq2! { CowVec<'a, A>, [B; $N], Clone }
-            // __impl_slice_eq2! { CowVec<'a, A>, &'b [B; $N], Clone }
-            // __impl_slice_eq2! { CowVec<'a, A>, &'b mut [B; $N], Clone }
+            // __impl_slice_eq2! { Cow<'a, [A]>, [B; $N], Clone }
+            // __impl_slice_eq2! { Cow<'a, [A]>, &'b [B; $N], Clone }
+            // __impl_slice_eq2! { Cow<'a, [A]>, &'b mut [B; $N], Clone }
         )+
     }
 }
@@ -2130,8 +2130,8 @@ fn test_clone() {
     #[test]
     fn test_clone_from() {
         let mut v = vec!();
-        let three = vec!(box 1, box 2, box 3);
-        let two = vec!(box 4, box 5);
+        let three: Vec<Box<_>> = vec!(box 1, box 2, box 3);
+        let two: Vec<Box<_>> = vec!(box 4, box 5);
         // zero, long
         v.clone_from(&three);
         assert_eq!(v, three);
@@ -2242,7 +2242,7 @@ fn drop(&mut self) {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_vec_truncate_fail() {
         struct BadElem(i32);
         impl Drop for BadElem {
@@ -2265,49 +2265,49 @@ fn test_index() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_index_out_of_bounds() {
         let vec = vec![1, 2, 3];
         let _ = vec[3];
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_slice_out_of_bounds_1() {
         let x = vec![1, 2, 3, 4, 5];
         &x[-1..];
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_slice_out_of_bounds_2() {
         let x = vec![1, 2, 3, 4, 5];
         &x[..6];
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_slice_out_of_bounds_3() {
         let x = vec![1, 2, 3, 4, 5];
         &x[-1..4];
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_slice_out_of_bounds_4() {
         let x = vec![1, 2, 3, 4, 5];
         &x[1..6];
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_slice_out_of_bounds_5() {
         let x = vec![1, 2, 3, 4, 5];
         &x[3..2];
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_swap_remove_empty() {
         let mut vec= Vec::<i32>::new();
         vec.swap_remove(0);
@@ -2326,7 +2326,7 @@ fn test_move_iter_unwrap() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_map_in_place_incompatible_types_fail() {
         let v = vec![0, 1, 2];
         v.map_in_place(|_| ());
index abcc0cef9f1feae7ad86e659f1475133de50a471..cab589d55beae584a18385f4911fb2830a72c959 100644 (file)
@@ -26,6 +26,7 @@
 use core::iter::{self, repeat, FromIterator, IntoIterator, RandomAccessIterator};
 use core::mem;
 use core::num::{Int, UnsignedInt};
+use core::num::wrapping::WrappingOps;
 use core::ops::{Index, IndexMut};
 use core::ptr::{self, Unique};
 use core::raw::Slice as RawSlice;
@@ -39,8 +40,8 @@
 #[unstable(feature = "collections")]
 pub use VecDeque as RingBuf;
 
-static INITIAL_CAPACITY: usize = 7; // 2^3 - 1
-static MINIMUM_CAPACITY: usize = 1; // 2 - 1
+const INITIAL_CAPACITY: usize = 7; // 2^3 - 1
+const MINIMUM_CAPACITY: usize = 1; // 2 - 1
 
 /// `VecDeque` is a growable ring buffer, which can be used as a
 /// double-ended queue efficiently.
@@ -120,6 +121,20 @@ fn is_full(&self) -> bool { self.cap - self.len() == 1 }
     #[inline]
     fn wrap_index(&self, idx: usize) -> usize { wrap_index(idx, self.cap) }
 
+    /// Returns the index in the underlying buffer for a given logical element
+    /// index + addend.
+    #[inline]
+    fn wrap_add(&self, idx: usize, addend: usize) -> usize {
+        wrap_index(idx.wrapping_add(addend), self.cap)
+    }
+
+    /// Returns the index in the underlying buffer for a given logical element
+    /// index - subtrahend.
+    #[inline]
+    fn wrap_sub(&self, idx: usize, subtrahend: usize) -> usize {
+        wrap_index(idx.wrapping_sub(subtrahend), self.cap)
+    }
+
     /// Copies a contiguous block of memory len long from src to dst
     #[inline]
     unsafe fn copy(&self, dst: usize, src: usize, len: usize) {
@@ -197,7 +212,7 @@ pub fn with_capacity(n: usize) -> VecDeque<T> {
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn get(&self, i: usize) -> Option<&T> {
         if i < self.len() {
-            let idx = self.wrap_index(self.tail + i);
+            let idx = self.wrap_add(self.tail, i);
             unsafe { Some(&*self.ptr.offset(idx as isize)) }
         } else {
             None
@@ -227,7 +242,7 @@ pub fn get(&self, i: usize) -> Option<&T> {
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn get_mut(&mut self, i: usize) -> Option<&mut T> {
         if i < self.len() {
-            let idx = self.wrap_index(self.tail + i);
+            let idx = self.wrap_add(self.tail, i);
             unsafe { Some(&mut *self.ptr.offset(idx as isize)) }
         } else {
             None
@@ -257,8 +272,8 @@ pub fn get_mut(&mut self, i: usize) -> Option<&mut T> {
     pub fn swap(&mut self, i: usize, j: usize) {
         assert!(i < self.len());
         assert!(j < self.len());
-        let ri = self.wrap_index(self.tail + i);
-        let rj = self.wrap_index(self.tail + j);
+        let ri = self.wrap_add(self.tail, i);
+        let rj = self.wrap_add(self.tail, j);
         unsafe {
             ptr::swap(self.ptr.offset(ri as isize), self.ptr.offset(rj as isize))
         }
@@ -427,7 +442,7 @@ pub fn shrink_to_fit(&mut self) {
                 //   [. . . o o o o o o o . . . . . . ]
                 //        H T
                 //   [o o . o o o o o ]
-                let len = self.wrap_index(self.head - target_cap);
+                let len = self.wrap_sub(self.head, target_cap);
                 unsafe {
                     self.copy_nonoverlapping(0, target_cap, len);
                 }
@@ -438,7 +453,7 @@ pub fn shrink_to_fit(&mut self) {
                 //   [o o o o o . . . . . . . . . o o ]
                 //              H T
                 //   [o o o o o . o o ]
-                debug_assert!(self.wrap_index(self.head - 1) < target_cap);
+                debug_assert!(self.wrap_sub(self.head, 1) < target_cap);
                 let len = self.cap - self.tail;
                 let new_tail = target_cap - len;
                 unsafe {
@@ -775,7 +790,7 @@ pub fn pop_front(&mut self) -> Option<T> {
             None
         } else {
             let tail = self.tail;
-            self.tail = self.wrap_index(self.tail + 1);
+            self.tail = self.wrap_add(self.tail, 1);
             unsafe { Some(self.buffer_read(tail)) }
         }
     }
@@ -799,7 +814,7 @@ pub fn push_front(&mut self, t: T) {
             debug_assert!(!self.is_full());
         }
 
-        self.tail = self.wrap_index(self.tail - 1);
+        self.tail = self.wrap_sub(self.tail, 1);
         let tail = self.tail;
         unsafe { self.buffer_write(tail, t); }
     }
@@ -824,7 +839,7 @@ pub fn push_back(&mut self, t: T) {
         }
 
         let head = self.head;
-        self.head = self.wrap_index(self.head + 1);
+        self.head = self.wrap_add(self.head, 1);
         unsafe { self.buffer_write(head, t) }
     }
 
@@ -847,7 +862,7 @@ pub fn pop_back(&mut self) -> Option<T> {
         if self.is_empty() {
             None
         } else {
-            self.head = self.wrap_index(self.head - 1);
+            self.head = self.wrap_sub(self.head, 1);
             let head = self.head;
             unsafe { Some(self.buffer_read(head)) }
         }
@@ -971,7 +986,7 @@ pub fn insert(&mut self, i: usize, t: T) {
         //      A - The element that should be after the insertion point
         //      M - Indicates element was moved
 
-        let idx = self.wrap_index(self.tail + i);
+        let idx = self.wrap_add(self.tail, i);
 
         let distance_to_tail = i;
         let distance_to_head = self.len() - i;
@@ -990,7 +1005,7 @@ pub fn insert(&mut self, i: usize, t: T) {
                 //      [A o o o o o o o . . . . . I]
                 //
 
-                self.tail = self.wrap_index(self.tail - 1);
+                self.tail = self.wrap_sub(self.tail, 1);
             },
             (true, true, _) => unsafe {
                 // contiguous, insert closer to tail:
@@ -1012,7 +1027,7 @@ pub fn insert(&mut self, i: usize, t: T) {
                 //      [o I A o o o o o . . . . . . . o]
                 //       M                             M
 
-                let new_tail = self.wrap_index(self.tail - 1);
+                let new_tail = self.wrap_sub(self.tail, 1);
 
                 self.copy(new_tail, self.tail, 1);
                 // Already moved the tail, so we only copy `i - 1` elements.
@@ -1031,7 +1046,7 @@ pub fn insert(&mut self, i: usize, t: T) {
                 //                       M M M
 
                 self.copy(idx + 1, idx, self.head - idx);
-                self.head = self.wrap_index(self.head + 1);
+                self.head = self.wrap_add(self.head, 1);
             },
             (false, true, true) => unsafe {
                 // discontiguous, insert closer to tail, tail section:
@@ -1123,7 +1138,7 @@ pub fn insert(&mut self, i: usize, t: T) {
         }
 
         // tail might've been changed so we need to recalculate
-        let new_idx = self.wrap_index(self.tail + i);
+        let new_idx = self.wrap_add(self.tail, i);
         unsafe {
             self.buffer_write(new_idx, t);
         }
@@ -1170,7 +1185,7 @@ pub fn remove(&mut self, i: usize) -> Option<T> {
         //      R - Indicates element that is being removed
         //      M - Indicates element was moved
 
-        let idx = self.wrap_index(self.tail + i);
+        let idx = self.wrap_add(self.tail, i);
 
         let elem = unsafe {
             Some(self.buffer_read(idx))
@@ -1219,7 +1234,7 @@ pub fn remove(&mut self, i: usize) -> Option<T> {
                 //                               M M
 
                 self.copy(self.tail + 1, self.tail, i);
-                self.tail = self.wrap_index(self.tail + 1);
+                self.tail = self.wrap_add(self.tail, 1);
             },
             (false, false, false) => unsafe {
                 // discontiguous, remove closer to head, head section:
@@ -1265,7 +1280,7 @@ pub fn remove(&mut self, i: usize) -> Option<T> {
                     self.copy(0, 1, self.head - 1);
                 }
 
-                self.head = self.wrap_index(self.head - 1);
+                self.head = self.wrap_sub(self.head, 1);
             },
             (false, true, false) => unsafe {
                 // discontiguous, remove closer to tail, head section:
@@ -1286,7 +1301,7 @@ pub fn remove(&mut self, i: usize) -> Option<T> {
                 // move elements from tail to end forward, excluding the last one
                 self.copy(self.tail + 1, self.tail, self.cap - self.tail - 1);
 
-                self.tail = self.wrap_index(self.tail + 1);
+                self.tail = self.wrap_add(self.tail, 1);
             }
         }
 
@@ -1354,7 +1369,7 @@ pub fn split_off(&mut self, at: usize) -> Self {
         }
 
         // Cleanup where the ends of the buffers are
-        self.head = self.wrap_index(self.head - other_len);
+        self.head = self.wrap_sub(self.head, other_len);
         other.head = other.wrap_index(other_len);
 
         other
@@ -1429,7 +1444,7 @@ fn wrap_index(index: usize, size: usize) -> usize {
 #[inline]
 fn count(tail: usize, head: usize, size: usize) -> usize {
     // size is always a power of 2
-    (head - tail) & (size - 1)
+    (head.wrapping_sub(tail)) & (size - 1)
 }
 
 /// `VecDeque` iterator.
@@ -1461,7 +1476,7 @@ fn next(&mut self) -> Option<&'a T> {
             return None;
         }
         let tail = self.tail;
-        self.tail = wrap_index(self.tail + 1, self.ring.len());
+        self.tail = wrap_index(self.tail.wrapping_add(1), self.ring.len());
         unsafe { Some(self.ring.get_unchecked(tail)) }
     }
 
@@ -1479,7 +1494,7 @@ fn next_back(&mut self) -> Option<&'a T> {
         if self.tail == self.head {
             return None;
         }
-        self.head = wrap_index(self.head - 1, self.ring.len());
+        self.head = wrap_index(self.head.wrapping_sub(1), self.ring.len());
         unsafe { Some(self.ring.get_unchecked(self.head)) }
     }
 }
@@ -1500,7 +1515,7 @@ fn idx(&mut self, j: usize) -> Option<&'a T> {
         if j >= self.indexable() {
             None
         } else {
-            let idx = wrap_index(self.tail + j, self.ring.len());
+            let idx = wrap_index(self.tail.wrapping_add(j), self.ring.len());
             unsafe { Some(self.ring.get_unchecked(idx)) }
         }
     }
@@ -1524,7 +1539,7 @@ fn next(&mut self) -> Option<&'a mut T> {
             return None;
         }
         let tail = self.tail;
-        self.tail = wrap_index(self.tail + 1, self.ring.len());
+        self.tail = wrap_index(self.tail.wrapping_add(1), self.ring.len());
 
         unsafe {
             let elem = self.ring.get_unchecked_mut(tail);
@@ -1546,7 +1561,7 @@ fn next_back(&mut self) -> Option<&'a mut T> {
         if self.tail == self.head {
             return None;
         }
-        self.head = wrap_index(self.head - 1, self.ring.len());
+        self.head = wrap_index(self.head.wrapping_sub(1), self.ring.len());
 
         unsafe {
             let elem = self.ring.get_unchecked_mut(self.head);
@@ -1869,7 +1884,7 @@ fn test_index() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_index_out_of_bounds() {
         let mut deq = VecDeque::new();
         for i in 1..4 {
index 5a0aa750bf5670dc1a569ca9f9c5e9715c17c884..431c8d5df8c0a11dfa27efa2394b1a2db30a57a8 100644 (file)
@@ -1205,7 +1205,7 @@ fn test_mut_rev_iterator() {
 
     #[test]
     fn test_move_iter() {
-        let mut m = VecMap::new();
+        let mut m: VecMap<Box<_>> = VecMap::new();
         m.insert(1, box 2);
         let mut called = false;
         for (k, v) in m {
@@ -1432,7 +1432,7 @@ fn test_index() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_index_nonexistent() {
         let mut map = VecMap::new();
 
index 38e2bd98ef9e3d64629f9e247850a376c5d2ba6a..c316236a8041291efd6ff1b588ecab8325b21921 100644 (file)
@@ -1067,6 +1067,7 @@ pub struct AtomicInt {
     v: UnsafeCell<int>,
 }
 
+#[allow(deprecated)]
 unsafe impl Sync for AtomicInt {}
 
 #[unstable(feature = "core")]
@@ -1077,6 +1078,7 @@ pub struct AtomicUint {
     v: UnsafeCell<uint>,
 }
 
+#[allow(deprecated)]
 unsafe impl Sync for AtomicUint {}
 
 #[unstable(feature = "core")]
index b8a22c30f9e1ed14a9146b22772af699adc45901..4f77a20c7cac853e0367af0794deab2c74a82c79 100644 (file)
@@ -631,9 +631,6 @@ fn deref_mut<'a>(&'a mut self) -> &'a mut T {
 ///
 /// Types like `Cell<T>` and `RefCell<T>` use this type to wrap their internal data.
 ///
-/// `UnsafeCell<T>` doesn't opt-out from any marker traits, instead, types with an `UnsafeCell<T>`
-/// interior are expected to opt-out from those traits themselves.
-///
 /// # Examples
 ///
 /// ```
index 8e27ae1cea97039342dceb76b1e04b541d6faa41..010415b364aa04a75506c86f7d6d82a83e3d0602 100644 (file)
 use slice::SliceExt;
 
 // UTF-8 ranges and tags for encoding characters
-const TAG_CONT: u8    = 0b1000_0000u8;
-const TAG_TWO_B: u8   = 0b1100_0000u8;
-const TAG_THREE_B: u8 = 0b1110_0000u8;
-const TAG_FOUR_B: u8  = 0b1111_0000u8;
-const MAX_ONE_B: u32   =     0x80u32;
-const MAX_TWO_B: u32   =    0x800u32;
-const MAX_THREE_B: u32 =  0x10000u32;
+const TAG_CONT: u8    = 0b1000_0000;
+const TAG_TWO_B: u8   = 0b1100_0000;
+const TAG_THREE_B: u8 = 0b1110_0000;
+const TAG_FOUR_B: u8  = 0b1111_0000;
+const MAX_ONE_B: u32   =     0x80;
+const MAX_TWO_B: u32   =    0x800;
+const MAX_THREE_B: u32 =  0x10000;
 
 /*
     Lu  Uppercase_Letter        an uppercase letter
@@ -118,7 +118,7 @@ pub fn from_u32(i: u32) -> Option<char> {
 /// assert_eq!(c, Some('4'));
 /// ```
 #[inline]
-#[unstable(feature = "core", reason = "pending integer conventions")]
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn from_digit(num: u32, radix: u32) -> Option<char> {
     if radix > 36 {
         panic!("from_digit: radix is too high (maximum 36)");
@@ -136,230 +136,25 @@ pub fn from_digit(num: u32, radix: u32) -> Option<char> {
     }
 }
 
-/// Basic `char` manipulations.
-#[stable(feature = "rust1", since = "1.0.0")]
+// NB: the stabilization and documentation for this trait is in
+// unicode/char.rs, not here
+#[allow(missing_docs)] // docs in libunicode/u_char.rs
 pub trait CharExt {
-    /// Checks if a `char` parses as a numeric digit in the given radix.
-    ///
-    /// Compared to `is_numeric()`, this function only recognizes the characters
-    /// `0-9`, `a-z` and `A-Z`.
-    ///
-    /// # Return value
-    ///
-    /// Returns `true` if `c` is a valid digit under `radix`, and `false`
-    /// otherwise.
-    ///
-    /// # Panics
-    ///
-    /// Panics if given a radix > 36.
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// let c = '1';
-    ///
-    /// assert!(c.is_digit(10));
-    ///
-    /// assert!('f'.is_digit(16));
-    /// ```
-    #[unstable(feature = "core",
-               reason = "pending integer conventions")]
     fn is_digit(self, radix: u32) -> bool;
-
-    /// Converts a character to the corresponding digit.
-    ///
-    /// # Return value
-    ///
-    /// If `c` is between '0' and '9', the corresponding value between 0 and
-    /// 9. If `c` is 'a' or 'A', 10. If `c` is 'b' or 'B', 11, etc. Returns
-    /// none if the character does not refer to a digit in the given radix.
-    ///
-    /// # Panics
-    ///
-    /// Panics if given a radix outside the range [0..36].
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// let c = '1';
-    ///
-    /// assert_eq!(c.to_digit(10), Some(1));
-    ///
-    /// assert_eq!('f'.to_digit(16), Some(15));
-    /// ```
-    #[unstable(feature = "core",
-               reason = "pending integer conventions")]
     fn to_digit(self, radix: u32) -> Option<u32>;
-
-    /// Returns an iterator that yields the hexadecimal Unicode escape of a character, as `char`s.
-    ///
-    /// All characters are escaped with Rust syntax of the form `\\u{NNNN}` where `NNNN` is the
-    /// shortest hexadecimal representation of the code point.
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// for i in '❤'.escape_unicode() {
-    ///     println!("{}", i);
-    /// }
-    /// ```
-    ///
-    /// This prints:
-    ///
-    /// ```text
-    /// \
-    /// u
-    /// {
-    /// 2
-    /// 7
-    /// 6
-    /// 4
-    /// }
-    /// ```
-    ///
-    /// Collecting into a `String`:
-    ///
-    /// ```
-    /// let heart: String = '❤'.escape_unicode().collect();
-    ///
-    /// assert_eq!(heart, r"\u{2764}");
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn escape_unicode(self) -> EscapeUnicode;
-
-    /// Returns an iterator that yields the 'default' ASCII and
-    /// C++11-like literal escape of a character, as `char`s.
-    ///
-    /// The default is chosen with a bias toward producing literals that are
-    /// legal in a variety of languages, including C++11 and similar C-family
-    /// languages. The exact rules are:
-    ///
-    /// * Tab, CR and LF are escaped as '\t', '\r' and '\n' respectively.
-    /// * Single-quote, double-quote and backslash chars are backslash-
-    ///   escaped.
-    /// * Any other chars in the range [0x20,0x7e] are not escaped.
-    /// * Any other chars are given hex Unicode escapes; see `escape_unicode`.
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// for i in '"'.escape_default() {
-    ///     println!("{}", i);
-    /// }
-    /// ```
-    ///
-    /// This prints:
-    ///
-    /// ```text
-    /// \
-    /// "
-    /// ```
-    ///
-    /// Collecting into a `String`:
-    ///
-    /// ```
-    /// let quote: String = '"'.escape_default().collect();
-    ///
-    /// assert_eq!(quote, "\\\"");
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn escape_default(self) -> EscapeDefault;
-
-    /// Returns the number of bytes this character would need if encoded in UTF-8.
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// let n = 'ß'.len_utf8();
-    ///
-    /// assert_eq!(n, 2);
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn len_utf8(self) -> usize;
-
-    /// Returns the number of bytes this character would need if encoded in UTF-16.
-    ///
-    /// # Examples
-    ///
-    /// ```
-    /// let n = 'ß'.len_utf16();
-    ///
-    /// assert_eq!(n, 1);
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn len_utf16(self) -> usize;
-
-    /// Encodes this character as UTF-8 into the provided byte buffer, and then returns the number
-    /// of bytes written.
-    ///
-    /// If the buffer is not large enough, nothing will be written into it and a `None` will be
-    /// returned.
-    ///
-    /// # Examples
-    ///
-    /// In both of these examples, 'ß' takes two bytes to encode.
-    ///
-    /// ```
-    /// let mut b = [0; 2];
-    ///
-    /// let result = 'ß'.encode_utf8(&mut b);
-    ///
-    /// assert_eq!(result, Some(2));
-    /// ```
-    ///
-    /// A buffer that's too small:
-    ///
-    /// ```
-    /// let mut b = [0; 1];
-    ///
-    /// let result = 'ß'.encode_utf8(&mut b);
-    ///
-    /// assert_eq!(result, None);
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn encode_utf8(self, dst: &mut [u8]) -> Option<usize>;
-
-    /// Encodes this character as UTF-16 into the provided `u16` buffer, and then returns the
-    /// number of `u16`s written.
-    ///
-    /// If the buffer is not large enough, nothing will be written into it and a `None` will be
-    /// returned.
-    ///
-    /// # Examples
-    ///
-    /// In both of these examples, 'ß' takes one byte to encode.
-    ///
-    /// ```
-    /// let mut b = [0; 1];
-    ///
-    /// let result = 'ß'.encode_utf16(&mut b);
-    ///
-    /// assert_eq!(result, Some(1));
-    /// ```
-    ///
-    /// A buffer that's too small:
-    ///
-    /// ```
-    /// let mut b = [0; 0];
-    ///
-    /// let result = 'ß'.encode_utf8(&mut b);
-    ///
-    /// assert_eq!(result, None);
-    /// ```
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn encode_utf16(self, dst: &mut [u16]) -> Option<usize>;
 }
 
-#[stable(feature = "rust1", since = "1.0.0")]
 impl CharExt for char {
-    #[unstable(feature = "core",
-               reason = "pending integer conventions")]
     fn is_digit(self, radix: u32) -> bool {
         self.to_digit(radix).is_some()
     }
 
-    #[unstable(feature = "core",
-               reason = "pending integer conventions")]
     fn to_digit(self, radix: u32) -> Option<u32> {
         if radix > 36 {
             panic!("to_digit: radix is too high (maximum 36)");
@@ -374,12 +169,10 @@ fn to_digit(self, radix: u32) -> Option<u32> {
         else { None }
     }
 
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn escape_unicode(self) -> EscapeUnicode {
         EscapeUnicode { c: self, state: EscapeUnicodeState::Backslash }
     }
 
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn escape_default(self) -> EscapeDefault {
         let init_state = match self {
             '\t' => EscapeDefaultState::Backslash('t'),
@@ -395,7 +188,6 @@ fn escape_default(self) -> EscapeDefault {
     }
 
     #[inline]
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn len_utf8(self) -> usize {
         let code = self as u32;
         if code < MAX_ONE_B {
@@ -410,22 +202,17 @@ fn len_utf8(self) -> usize {
     }
 
     #[inline]
-    #[stable(feature = "rust1", since = "1.0.0")]
     fn len_utf16(self) -> usize {
         let ch = self as u32;
-        if (ch & 0xFFFF_u32) == ch { 1 } else { 2 }
+        if (ch & 0xFFFF) == ch { 1 } else { 2 }
     }
 
     #[inline]
-    #[unstable(feature = "core",
-               reason = "pending decision about Iterator/Writer/Reader")]
     fn encode_utf8(self, dst: &mut [u8]) -> Option<usize> {
         encode_utf8_raw(self as u32, dst)
     }
 
     #[inline]
-    #[unstable(feature = "core",
-               reason = "pending decision about Iterator/Writer/Reader")]
     fn encode_utf16(self, dst: &mut [u16]) -> Option<usize> {
         encode_utf16_raw(self as u32, dst)
     }
@@ -437,26 +224,25 @@ fn encode_utf16(self, dst: &mut [u16]) -> Option<usize> {
 /// If the buffer is not large enough, nothing will be written into it
 /// and a `None` will be returned.
 #[inline]
-#[unstable(feature = "core")]
 pub fn encode_utf8_raw(code: u32, dst: &mut [u8]) -> Option<usize> {
     // Marked #[inline] to allow llvm optimizing it away
     if code < MAX_ONE_B && dst.len() >= 1 {
         dst[0] = code as u8;
         Some(1)
     } else if code < MAX_TWO_B && dst.len() >= 2 {
-        dst[0] = (code >> 6 & 0x1F_u32) as u8 | TAG_TWO_B;
-        dst[1] = (code & 0x3F_u32) as u8 | TAG_CONT;
+        dst[0] = (code >> 6 & 0x1F) as u8 | TAG_TWO_B;
+        dst[1] = (code & 0x3F) as u8 | TAG_CONT;
         Some(2)
     } else if code < MAX_THREE_B && dst.len() >= 3  {
-        dst[0] = (code >> 12 & 0x0F_u32) as u8 | TAG_THREE_B;
-        dst[1] = (code >>  6 & 0x3F_u32) as u8 | TAG_CONT;
-        dst[2] = (code & 0x3F_u32) as u8 | TAG_CONT;
+        dst[0] = (code >> 12 & 0x0F) as u8 | TAG_THREE_B;
+        dst[1] = (code >>  6 & 0x3F) as u8 | TAG_CONT;
+        dst[2] = (code & 0x3F) as u8 | TAG_CONT;
         Some(3)
     } else if dst.len() >= 4 {
-        dst[0] = (code >> 18 & 0x07_u32) as u8 | TAG_FOUR_B;
-        dst[1] = (code >> 12 & 0x3F_u32) as u8 | TAG_CONT;
-        dst[2] = (code >>  6 & 0x3F_u32) as u8 | TAG_CONT;
-        dst[3] = (code & 0x3F_u32) as u8 | TAG_CONT;
+        dst[0] = (code >> 18 & 0x07) as u8 | TAG_FOUR_B;
+        dst[1] = (code >> 12 & 0x3F) as u8 | TAG_CONT;
+        dst[2] = (code >>  6 & 0x3F) as u8 | TAG_CONT;
+        dst[3] = (code & 0x3F) as u8 | TAG_CONT;
         Some(4)
     } else {
         None
@@ -469,18 +255,17 @@ pub fn encode_utf8_raw(code: u32, dst: &mut [u8]) -> Option<usize> {
 /// If the buffer is not large enough, nothing will be written into it
 /// and a `None` will be returned.
 #[inline]
-#[unstable(feature = "core")]
 pub fn encode_utf16_raw(mut ch: u32, dst: &mut [u16]) -> Option<usize> {
     // Marked #[inline] to allow llvm optimizing it away
-    if (ch & 0xFFFF_u32) == ch  && dst.len() >= 1 {
+    if (ch & 0xFFFF) == ch  && dst.len() >= 1 {
         // The BMP falls through (assuming non-surrogate, as it should)
         dst[0] = ch as u16;
         Some(1)
     } else if dst.len() >= 2 {
         // Supplementary planes break into surrogates.
-        ch -= 0x1_0000_u32;
-        dst[0] = 0xD800_u16 | ((ch >> 10) as u16);
-        dst[1] = 0xDC00_u16 | ((ch as u16) & 0x3FF_u16);
+        ch -= 0x1_0000;
+        dst[0] = 0xD800 | ((ch >> 10) as u16);
+        dst[1] = 0xDC00 | ((ch as u16) & 0x3FF);
         Some(2)
     } else {
         None
@@ -497,7 +282,6 @@ pub struct EscapeUnicode {
 }
 
 #[derive(Clone)]
-#[unstable(feature = "core")]
 enum EscapeUnicodeState {
     Backslash,
     Type,
@@ -559,7 +343,6 @@ pub struct EscapeDefault {
 }
 
 #[derive(Clone)]
-#[unstable(feature = "core")]
 enum EscapeDefaultState {
     Backslash(char),
     Char(char),
index f92e631c1f25c4becc028f0056484346b26fa603..0df04c296c8aee771002f1438487a21355aef03e 100644 (file)
@@ -53,7 +53,7 @@ pub enum SignFormat {
     SignNeg
 }
 
-static DIGIT_E_RADIX: u32 = ('e' as u32) - ('a' as u32) + 11;
+const DIGIT_E_RADIX: u32 = ('e' as u32) - ('a' as u32) + 11;
 
 /// Converts a number to its string representation as a byte vector.
 /// This is meant to be a common base implementation for all numeric string
@@ -123,13 +123,13 @@ pub fn float_to_str_bytes_common<T: Float, U, F>(
     // For an f64 the exponent is in the range of [-1022, 1023] for base 2, so
     // we may have up to that many digits. Give ourselves some extra wiggle room
     // otherwise as well.
-    let mut buf = [0u8; 1536];
+    let mut buf = [0; 1536];
     let mut end = 0;
     let radix_gen: T = cast(radix as int).unwrap();
 
     let (num, exp) = match exp_format {
-        ExpNone => (num, 0i32),
-        ExpDec if num == _0 => (num, 0i32),
+        ExpNone => (num, 0),
+        ExpDec if num == _0 => (num, 0),
         ExpDec => {
             let (exp, exp_base) = match exp_format {
                 ExpDec => (num.abs().log10().floor(), cast::<f64, T>(10.0f64).unwrap()),
@@ -156,7 +156,7 @@ pub fn float_to_str_bytes_common<T: Float, U, F>(
         deccum = deccum / radix_gen;
         deccum = deccum.trunc();
 
-        let c = char::from_digit(current_digit.to_int().unwrap() as u32, radix);
+        let c = char::from_digit(current_digit.to_isize().unwrap() as u32, radix);
         buf[end] = c.unwrap() as u8;
         end += 1;
 
@@ -211,7 +211,7 @@ pub fn float_to_str_bytes_common<T: Float, U, F>(
             // See note in first loop.
             let current_digit = deccum.trunc().abs();
 
-            let c = char::from_digit(current_digit.to_int().unwrap() as u32,
+            let c = char::from_digit(current_digit.to_isize().unwrap() as u32,
                                      radix);
             buf[end] = c.unwrap() as u8;
             end += 1;
index 9544fbaa55b256b65fd48dd58ee682dc14c1386a..e640bf02f5a32adfd11fe3b53d13fab0271a470e 100644 (file)
@@ -565,7 +565,7 @@ fn with_padding<F>(&mut self, padding: usize, default: Alignment,
             Alignment::Center => (padding / 2, (padding + 1) / 2),
         };
 
-        let mut fill = [0u8; 4];
+        let mut fill = [0; 4];
         let len = self.fill.encode_utf8(&mut fill).unwrap_or(0);
         let fill = unsafe { str::from_utf8_unchecked(&fill[..len]) };
 
@@ -689,7 +689,7 @@ fn fmt(&self, f: &mut Formatter) -> Result {
 #[stable(feature = "rust1", since = "1.0.0")]
 impl Display for char {
     fn fmt(&self, f: &mut Formatter) -> Result {
-        let mut utf8 = [0u8; 4];
+        let mut utf8 = [0; 4];
         let amt = self.encode_utf8(&mut utf8).unwrap_or(0);
         let s: &str = unsafe { mem::transmute(&utf8[..amt]) };
         Display::fmt(s, f)
index 0175e21c8da6152b47bfbbae924118a19bc3bc64..b3f2302bb3e0741418ed6ef5be380603b855f9b8 100644 (file)
@@ -38,7 +38,7 @@ fn fmt_int<T: Int>(&self, mut x: T, f: &mut fmt::Formatter) -> fmt::Result {
         // characters for a base 2 number.
         let zero = Int::zero();
         let is_positive = x >= zero;
-        let mut buf = [0u8; 64];
+        let mut buf = [0; 64];
         let mut curr = buf.len();
         let base = cast(self.base()).unwrap();
         if is_positive {
@@ -84,7 +84,7 @@ fn fmt_int<T: Int>(&self, mut x: T, f: &mut fmt::Formatter) -> fmt::Result {
 
 /// A hexadecimal (base 16) radix, formatted with upper-case characters
 #[derive(Clone, PartialEq)]
-pub struct UpperHex;
+struct UpperHex;
 
 macro_rules! radix {
     ($T:ident, $base:expr, $prefix:expr, $($x:pat => $conv:expr),+) => {
@@ -156,7 +156,7 @@ pub fn radix<T>(x: T, base: u8) -> RadixFmt<T, Radix> {
 }
 
 macro_rules! radix_fmt {
-    ($T:ty as $U:ty, $fmt:ident, $S:expr) => {
+    ($T:ty as $U:ty, $fmt:ident) => {
         #[stable(feature = "rust1", since = "1.0.0")]
         impl fmt::Debug for RadixFmt<$T, Radix> {
             fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
@@ -182,8 +182,8 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
     }
 }
 
-macro_rules! show {
-    ($T:ident with $S:expr) => {
+macro_rules! debug {
+    ($T:ident) => {
         #[stable(feature = "rust1", since = "1.0.0")]
         impl fmt::Debug for $T {
             fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
@@ -194,27 +194,24 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
 }
 macro_rules! integer {
     ($Int:ident, $Uint:ident) => {
-        integer! { $Int, $Uint, stringify!($Int), stringify!($Uint) }
-    };
-    ($Int:ident, $Uint:ident, $SI:expr, $SU:expr) => {
         int_base! { Display  for $Int as $Int   -> Decimal }
         int_base! { Binary   for $Int as $Uint  -> Binary }
         int_base! { Octal    for $Int as $Uint  -> Octal }
         int_base! { LowerHex for $Int as $Uint  -> LowerHex }
         int_base! { UpperHex for $Int as $Uint  -> UpperHex }
-        radix_fmt! { $Int as $Int, fmt_int, $SI }
-        show! { $Int with $SI }
+        radix_fmt! { $Int as $Int, fmt_int }
+        debug! { $Int }
 
         int_base! { Display  for $Uint as $Uint -> Decimal }
         int_base! { Binary   for $Uint as $Uint -> Binary }
         int_base! { Octal    for $Uint as $Uint -> Octal }
         int_base! { LowerHex for $Uint as $Uint -> LowerHex }
         int_base! { UpperHex for $Uint as $Uint -> UpperHex }
-        radix_fmt! { $Uint as $Uint, fmt_int, $SU }
-        show! { $Uint with $SU }
+        radix_fmt! { $Uint as $Uint, fmt_int }
+        debug! { $Uint }
     }
 }
-integer! { isize, usize, "i", "u" }
+integer! { isize, usize }
 integer! { i8, u8 }
 integer! { i16, u16 }
 integer! { i32, u32 }
index edc4b7e10ee49b04b024a3b3076d2f425f12358a..4b545435ea171345a5041daf53a2b260a7231bfd 100644 (file)
@@ -182,7 +182,7 @@ fn hash<H: Hasher>(&self, state: &mut H) {
                 }
 
                 fn hash_slice<H: Hasher>(data: &[$ty], state: &mut H) {
-                    let newlen = data.len() * ::$ty::BYTES;
+                    let newlen = data.len() * ::$ty::BYTES as usize;
                     let ptr = data.as_ptr() as *const u8;
                     state.write(unsafe { slice::from_raw_parts(ptr, newlen) })
                 }
index 39bcbacdff182c23b137037d007099a58ca17ed8..bd1516e0cfcc8b49e57334af9a99036b14a5cc4f 100644 (file)
@@ -14,7 +14,7 @@
 
 use prelude::*;
 use default::Default;
-
+use num::wrapping::WrappingOps;
 use super::Hasher;
 
 /// An implementation of SipHash 2-4.
@@ -60,7 +60,7 @@ macro_rules! u8to64_le {
     ($buf:expr, $i:expr, $len:expr) =>
     ({
         let mut t = 0;
-        let mut out = 0u64;
+        let mut out = 0;
         while t < $len {
             out |= ($buf[t+$i] as u64) << t*8;
             t += 1;
@@ -71,17 +71,17 @@ macro_rules! u8to64_le {
 
 macro_rules! rotl {
     ($x:expr, $b:expr) =>
-    (($x << $b) | ($x >> (64 - $b)))
+    (($x << $b) | ($x >> (64.wrapping_sub($b))))
 }
 
 macro_rules! compress {
     ($v0:expr, $v1:expr, $v2:expr, $v3:expr) =>
     ({
-        $v0 += $v1; $v1 = rotl!($v1, 13); $v1 ^= $v0;
+        $v0 = $v0.wrapping_add($v1); $v1 = rotl!($v1, 13); $v1 ^= $v0;
         $v0 = rotl!($v0, 32);
-        $v2 += $v3; $v3 = rotl!($v3, 16); $v3 ^= $v2;
-        $v0 += $v3; $v3 = rotl!($v3, 21); $v3 ^= $v0;
-        $v2 += $v1; $v1 = rotl!($v1, 17); $v1 ^= $v2;
+        $v2 = $v2.wrapping_add($v3); $v3 = rotl!($v3, 16); $v3 ^= $v2;
+        $v0 = $v0.wrapping_add($v3); $v3 = rotl!($v3, 21); $v3 ^= $v0;
+        $v2 = $v2.wrapping_add($v1); $v1 = rotl!($v1, 17); $v1 ^= $v2;
         $v2 = rotl!($v2, 32);
     })
 }
index 1ca243134cc6c6d985ca7f6b107c935c2d9ace58..7fccb93f2a0028ad5ef82c4a3bbaab72c3eadcc2 100644 (file)
@@ -230,7 +230,7 @@ pub struct TyDesc {
     /// use std::mem;
     ///
     /// let v: &[u8] = unsafe { mem::transmute("L") };
-    /// assert!(v == [76u8]);
+    /// assert!(v == [76]);
     /// ```
     #[stable(feature = "rust1", since = "1.0.0")]
     pub fn transmute<T,U>(e: T) -> U;
@@ -545,4 +545,11 @@ pub fn volatile_copy_nonoverlapping_memory<T>(dst: *mut T, src: *const T,
     pub fn u32_mul_with_overflow(x: u32, y: u32) -> (u32, bool);
     /// Performs checked `u64` multiplication.
     pub fn u64_mul_with_overflow(x: u64, y: u64) -> (u64, bool);
+
+    /// Returns (a + b) mod 2^N, where N is the width of N in bits.
+    pub fn overflowing_add<T>(a: T, b: T) -> T;
+    /// Returns (a - b) mod 2^N, where N is the width of N in bits.
+    pub fn overflowing_sub<T>(a: T, b: T) -> T;
+    /// Returns (a * b) mod 2^N, where N is the width of N in bits.
+    pub fn overflowing_mul<T>(a: T, b: T) -> T;
 }
index 88a729a3db09e92682022b71406d35cd6f483930..d5e891a156e9bb3b8f248a0cf352dad6e9751369 100644 (file)
@@ -611,7 +611,7 @@ fn partition<B, F>(self, mut f: F) -> (B, B) where
     ///
     /// ```
     /// let a = [1, 2, 3, 4, 5];
-    /// assert!(a.iter().fold(0, |a, &b| a + b) == 15);
+    /// assert!(a.iter().fold(0, |acc, &item| acc + item) == 15);
     /// ```
     #[inline]
     #[stable(feature = "rust1", since = "1.0.0")]
@@ -728,10 +728,11 @@ fn rposition<P>(&mut self, mut predicate: P) -> Option<usize> where
         P: FnMut(Self::Item) -> bool,
         Self: ExactSizeIterator + DoubleEndedIterator
     {
-        let mut i = self.len() - 1;
+        let mut i = self.len();
+
         while let Some(v) = self.next_back() {
             if predicate(v) {
-                return Some(i);
+                return Some(i - 1);
             }
             i -= 1;
         }
@@ -1129,7 +1130,11 @@ fn indexable(&self) -> usize { self.iter.indexable() }
     #[inline]
     fn idx(&mut self, index: usize) -> Option<<I as Iterator>::Item> {
         let amt = self.indexable();
-        self.iter.idx(amt - index - 1)
+        if amt > index {
+            self.iter.idx(amt - index - 1)
+        } else {
+            None
+        }
     }
 }
 
@@ -1144,7 +1149,7 @@ pub trait AdditiveIterator<A> {
     /// ```
     /// use std::iter::AdditiveIterator;
     ///
-    /// let a = [1i32, 2, 3, 4, 5];
+    /// let a = [1, 2, 3, 4, 5];
     /// let mut it = a.iter().cloned();
     /// assert!(it.sum() == 15);
     /// ```
@@ -1274,14 +1279,14 @@ pub struct Cloned<I> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T, D, I> Iterator for Cloned<I> where
-    T: Clone,
-    D: Deref<Target=T>,
-    I: Iterator<Item=D>,
+impl<I> Iterator for Cloned<I> where
+    I: Iterator,
+    I::Item: Deref,
+    <I::Item as Deref>::Target: Clone
 {
-    type Item = T;
+    type Item = <I::Item as Deref>::Target;
 
-    fn next(&mut self) -> Option<T> {
+    fn next(&mut self) -> Option<<Self as Iterator>::Item> {
         self.it.next().cloned()
     }
 
@@ -1291,28 +1296,28 @@ fn size_hint(&self) -> (usize, Option<usize>) {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T, D, I> DoubleEndedIterator for Cloned<I> where
-    T: Clone,
-    D: Deref<Target=T>,
-    I: DoubleEndedIterator<Item=D>,
+impl<I> DoubleEndedIterator for Cloned<I> where
+    I: DoubleEndedIterator,
+    I::Item: Deref,
+    <I::Item as Deref>::Target: Clone
 {
-    fn next_back(&mut self) -> Option<T> {
+    fn next_back(&mut self) -> Option<<Self as Iterator>::Item> {
         self.it.next_back().cloned()
     }
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T, D, I> ExactSizeIterator for Cloned<I> where
-    T: Clone,
-    D: Deref<Target=T>,
-    I: ExactSizeIterator<Item=D>,
+impl<I> ExactSizeIterator for Cloned<I> where
+    I: ExactSizeIterator,
+    I::Item: Deref,
+    <I::Item as Deref>::Target: Clone
 {}
 
 #[unstable(feature = "core", reason = "trait is experimental")]
-impl<T, D, I> RandomAccessIterator for Cloned<I> where
-    T: Clone,
-    D: Deref<Target=T>,
-    I: RandomAccessIterator<Item=D>
+impl<I> RandomAccessIterator for Cloned<I> where
+    I: RandomAccessIterator,
+    I::Item: Deref,
+    <I::Item as Deref>::Target: Clone
 {
     #[inline]
     fn indexable(&self) -> usize {
@@ -1320,7 +1325,7 @@ fn indexable(&self) -> usize {
     }
 
     #[inline]
-    fn idx(&mut self, index: usize) -> Option<T> {
+    fn idx(&mut self, index: usize) -> Option<<Self as Iterator>::Item> {
         self.it.idx(index).cloned()
     }
 }
@@ -1395,11 +1400,14 @@ pub struct Chain<A, B> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T, A, B> Iterator for Chain<A, B> where A: Iterator<Item=T>, B: Iterator<Item=T> {
-    type Item = T;
+impl<A, B> Iterator for Chain<A, B> where
+    A: Iterator,
+    B: Iterator<Item = A::Item>
+{
+    type Item = A::Item;
 
     #[inline]
-    fn next(&mut self) -> Option<T> {
+    fn next(&mut self) -> Option<A::Item> {
         if self.flag {
             self.b.next()
         } else {
@@ -1429,12 +1437,12 @@ fn size_hint(&self) -> (usize, Option<usize>) {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T, A, B> DoubleEndedIterator for Chain<A, B> where
-    A: DoubleEndedIterator<Item=T>,
-    B: DoubleEndedIterator<Item=T>,
+impl<A, B> DoubleEndedIterator for Chain<A, B> where
+    A: DoubleEndedIterator,
+    B: DoubleEndedIterator<Item=A::Item>,
 {
     #[inline]
-    fn next_back(&mut self) -> Option<T> {
+    fn next_back(&mut self) -> Option<A::Item> {
         match self.b.next_back() {
             Some(x) => Some(x),
             None => self.a.next_back()
@@ -1443,9 +1451,9 @@ fn next_back(&mut self) -> Option<T> {
 }
 
 #[unstable(feature = "core", reason = "trait is experimental")]
-impl<T, A, B> RandomAccessIterator for Chain<A, B> where
-    A: RandomAccessIterator<Item=T>,
-    B: RandomAccessIterator<Item=T>,
+impl<A, B> RandomAccessIterator for Chain<A, B> where
+    A: RandomAccessIterator,
+    B: RandomAccessIterator<Item = A::Item>,
 {
     #[inline]
     fn indexable(&self) -> usize {
@@ -1454,7 +1462,7 @@ fn indexable(&self) -> usize {
     }
 
     #[inline]
-    fn idx(&mut self, index: usize) -> Option<T> {
+    fn idx(&mut self, index: usize) -> Option<A::Item> {
         let len = self.a.indexable();
         if index < len {
             self.a.idx(index)
@@ -1474,14 +1482,12 @@ pub struct Zip<A, B> {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T, U, A, B> Iterator for Zip<A, B> where
-    A: Iterator<Item = T>,
-    B: Iterator<Item = U>,
+impl<A, B> Iterator for Zip<A, B> where A: Iterator, B: Iterator
 {
-    type Item = (T, U);
+    type Item = (A::Item, B::Item);
 
     #[inline]
-    fn next(&mut self) -> Option<(T, U)> {
+    fn next(&mut self) -> Option<(A::Item, B::Item)> {
         match self.a.next() {
             None => None,
             Some(x) => match self.b.next() {
@@ -1510,12 +1516,12 @@ fn size_hint(&self) -> (usize, Option<usize>) {
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<T, U, A, B> DoubleEndedIterator for Zip<A, B> where
-    A: DoubleEndedIterator + ExactSizeIterator<Item=T>,
-    B: DoubleEndedIterator + ExactSizeIterator<Item=U>,
+impl<A, B> DoubleEndedIterator for Zip<A, B> where
+    A: DoubleEndedIterator + ExactSizeIterator,
+    B: DoubleEndedIterator + ExactSizeIterator,
 {
     #[inline]
-    fn next_back(&mut self) -> Option<(T, U)> {
+    fn next_back(&mut self) -> Option<(A::Item, B::Item)> {
         let a_sz = self.a.len();
         let b_sz = self.b.len();
         if a_sz != b_sz {
@@ -1535,9 +1541,9 @@ fn next_back(&mut self) -> Option<(T, U)> {
 }
 
 #[unstable(feature = "core", reason = "trait is experimental")]
-impl<T, U, A, B> RandomAccessIterator for Zip<A, B> where
-    A: RandomAccessIterator<Item=T>,
-    B: RandomAccessIterator<Item=U>,
+impl<A, B> RandomAccessIterator for Zip<A, B> where
+    A: RandomAccessIterator,
+    B: RandomAccessIterator
 {
     #[inline]
     fn indexable(&self) -> usize {
@@ -1545,7 +1551,7 @@ fn indexable(&self) -> usize {
     }
 
     #[inline]
-    fn idx(&mut self, index: usize) -> Option<(T, U)> {
+    fn idx(&mut self, index: usize) -> Option<(A::Item, B::Item)> {
         match self.a.idx(index) {
             None => None,
             Some(x) => match self.b.idx(index) {
@@ -1565,24 +1571,13 @@ pub struct Map<I, F> {
     f: F,
 }
 
-impl<I: Iterator, F, B> Map<I, F> where F: FnMut(I::Item) -> B {
-    #[inline]
-    fn do_map(&mut self, elt: Option<I::Item>) -> Option<B> {
-        match elt {
-            Some(a) => Some((self.f)(a)),
-            _ => None
-        }
-    }
-}
-
 #[stable(feature = "rust1", since = "1.0.0")]
 impl<B, I: Iterator, F> Iterator for Map<I, F> where F: FnMut(I::Item) -> B {
     type Item = B;
 
     #[inline]
     fn next(&mut self) -> Option<B> {
-        let next = self.iter.next();
-        self.do_map(next)
+        self.iter.next().map(|a| (self.f)(a))
     }
 
     #[inline]
@@ -1597,8 +1592,7 @@ impl<B, I: DoubleEndedIterator, F> DoubleEndedIterator for Map<I, F> where
 {
     #[inline]
     fn next_back(&mut self) -> Option<B> {
-        let next = self.iter.next_back();
-        self.do_map(next)
+        self.iter.next_back().map(|a| (self.f)(a))
     }
 }
 
@@ -1613,8 +1607,7 @@ fn indexable(&self) -> usize {
 
     #[inline]
     fn idx(&mut self, index: usize) -> Option<B> {
-        let elt = self.iter.idx(index);
-        self.do_map(elt)
+        self.iter.idx(index).map(|a| (self.f)(a))
     }
 }
 
@@ -2061,12 +2054,14 @@ pub struct Scan<I, St, F> {
     f: F,
 
     /// The current internal state to be passed to the closure next.
+    #[unstable(feature = "core")]
     pub state: St,
 }
 
 #[stable(feature = "rust1", since = "1.0.0")]
-impl<A, B, I: Iterator<Item=A>, St, F> Iterator for Scan<I, St, F> where
-    F: FnMut(&mut St, A) -> Option<B>,
+impl<B, I, St, F> Iterator for Scan<I, St, F> where
+    I: Iterator,
+    F: FnMut(&mut St, I::Item) -> Option<B>,
 {
     type Item = B;
 
@@ -2338,6 +2333,7 @@ fn idx(&mut self, index: usize) -> Option<I::Item> {
 pub struct Unfold<St, F> {
     f: F,
     /// Internal state that will be passed to the closure on the next iteration
+    #[unstable(feature = "core")]
     pub state: St,
 }
 
@@ -2467,7 +2463,7 @@ fn size_hint(&self) -> (usize, Option<usize>) {
             Some(a) => {
                 let sz = self.stop.to_i64().map(|b| b.checked_sub(a));
                 match sz {
-                    Some(Some(bound)) => bound.to_uint(),
+                    Some(Some(bound)) => bound.to_usize(),
                     _ => None,
                 }
             },
@@ -2475,7 +2471,7 @@ fn size_hint(&self) -> (usize, Option<usize>) {
                 Some(a) => {
                     let sz = self.stop.to_u64().map(|b| b.checked_sub(a));
                     match sz {
-                        Some(Some(bound)) => bound.to_uint(),
+                        Some(Some(bound)) => bound.to_usize(),
                         _ => None
                     }
                 },
@@ -2741,7 +2737,7 @@ fn size_hint(&self) -> (usize, Option<usize>) {
         if self.start >= self.end {
             (0, Some(0))
         } else {
-            let length = (self.end - self.start).to_uint();
+            let length = (self.end - self.start).to_usize();
             (length.unwrap_or(0), length)
         }
     }
index 7cc963bed358f9aa666ff401bc3f520a3d84109a..45a5563ceeb170c62a1764fe8033aee9a1e77210 100644 (file)
@@ -35,8 +35,7 @@
 //!   often generated by LLVM. Additionally, this library can make explicit
 //!   calls to these functions. Their signatures are the same as found in C.
 //!   These functions are often provided by the system libc, but can also be
-//!   provided by `librlibc` which is distributed with the standard rust
-//!   distribution.
+//!   provided by the [rlibc crate](https://crates.io/crates/rlibc).
 //!
 //! * `rust_begin_unwind` - This function takes three arguments, a
 //!   `fmt::Arguments`, a `&str`, and a `usize`. These three arguments dictate
@@ -47,6 +46,8 @@
 // Since libcore defines many fundamental lang items, all tests live in a
 // separate crate, libcoretest, to avoid bizarre issues.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "core"]
 #![unstable(feature = "core")]
 #![staged_api]
@@ -69,6 +70,7 @@
 #![feature(unboxed_closures)]
 #![feature(rustc_attrs)]
 #![feature(optin_builtin_traits)]
+#![feature(concat_idents)]
 
 #[macro_use]
 mod macros;
index 94ca9ec37b49b515523e2e6ed713e1df3c6074cb..c2860d435114f64329d48c30daae5224a4c7b4cf 100644 (file)
@@ -100,10 +100,12 @@ macro_rules! assert_eq {
 /// This will invoke the `panic!` macro if the provided expression cannot be
 /// evaluated to `true` at runtime.
 ///
-/// Unlike `assert!`, `debug_assert!` statements can be disabled by passing
-/// `--cfg ndebug` to the compiler. This makes `debug_assert!` useful for
-/// checks that are too expensive to be present in a release build but may be
-/// helpful during development.
+/// Unlike `assert!`, `debug_assert!` statements are only enabled in non
+/// optimized builds by default. An optimized build will omit all
+/// `debug_assert!` statements unless `-C debug-assertions` is passed to the
+/// compiler. This makes `debug_assert!` useful for checks that are too
+/// expensive to be present in a release build but may be helpful during
+/// development.
 ///
 /// # Example
 ///
@@ -125,7 +127,7 @@ macro_rules! assert_eq {
 #[macro_export]
 #[stable(feature = "rust1", since = "1.0.0")]
 macro_rules! debug_assert {
-    ($($arg:tt)*) => (if cfg!(not(ndebug)) { assert!($($arg)*); })
+    ($($arg:tt)*) => (if cfg!(debug_assertions) { assert!($($arg)*); })
 }
 
 /// Asserts that two expressions are equal to each other, testing equality in
@@ -133,10 +135,12 @@ macro_rules! debug_assert {
 ///
 /// On panic, this macro will print the values of the expressions.
 ///
-/// Unlike `assert_eq!`, `debug_assert_eq!` statements can be disabled by
-/// passing `--cfg ndebug` to the compiler. This makes `debug_assert_eq!`
-/// useful for checks that are too expensive to be present in a release build
-/// but may be helpful during development.
+/// Unlike `assert_eq!`, `debug_assert_eq!` statements are only enabled in non
+/// optimized builds by default. An optimized build will omit all
+/// `debug_assert_eq!` statements unless `-C debug-assertions` is passed to the
+/// compiler. This makes `debug_assert_eq!` useful for checks that are too
+/// expensive to be present in a release build but may be helpful during
+/// development.
 ///
 /// # Example
 ///
@@ -147,7 +151,7 @@ macro_rules! debug_assert {
 /// ```
 #[macro_export]
 macro_rules! debug_assert_eq {
-    ($($arg:tt)*) => (if cfg!(not(ndebug)) { assert_eq!($($arg)*); })
+    ($($arg:tt)*) => (if cfg!(debug_assertions) { assert_eq!($($arg)*); })
 }
 
 /// Short circuiting evaluation on Err
@@ -227,7 +231,7 @@ macro_rules! writeln {
 ///
 /// ```rust
 /// fn divide_by_three(x: u32) -> u32 { // one of the poorest implementations of x/3
-///     for i in std::iter::count(0_u32, 1) {
+///     for i in std::iter::count(0, 1) {
 ///         if 3*i < i { panic!("u32 overflow"); }
 ///         if x < 3*i { return i-1; }
 ///     }
index 868a671b9560e2985188874f3b333463af95143d..fe53ea1f0af8413d6ef81333123448dcc5736aef 100644 (file)
@@ -193,14 +193,9 @@ pub trait Copy : MarkerTrait {
 /// the `sync` crate do ensure that any mutation cannot cause data
 /// races.  Hence these types are `Sync`.
 ///
-/// Users writing their own types with interior mutability (or anything
-/// else that is not thread-safe) should use the `NoSync` marker type
-/// (from `std::marker`) to ensure that the compiler doesn't
-/// consider the user-defined type to be `Sync`.  Any types with
-/// interior mutability must also use the `std::cell::UnsafeCell` wrapper
-/// around the value(s) which can be mutated when behind a `&`
-/// reference; not doing this is undefined behaviour (for example,
-/// `transmute`-ing from `&T` to `&mut T` is illegal).
+/// Any types with interior mutability must also use the `std::cell::UnsafeCell` wrapper around the
+/// value(s) which can be mutated when behind a `&` reference; not doing this is undefined
+/// behaviour (for example, `transmute`-ing from `&T` to `&mut T` is illegal).
 #[stable(feature = "rust1", since = "1.0.0")]
 #[lang="sync"]
 #[rustc_on_unimplemented = "`{Self}` cannot be shared between threads safely"]
@@ -351,7 +346,45 @@ pub trait PhantomFn<A:?Sized,R:?Sized=()> { }
 /// instance, it will behave *as if* an instance of the type `T` were
 /// present for the purpose of various automatic analyses.
 ///
-/// For example, embedding a `PhantomData<T>` will inform the compiler
+/// # Examples
+///
+/// When handling external resources over a foreign function interface, `PhantomData<T>` can
+/// prevent mismatches by enforcing types in the method implementations, although the struct
+/// doesn't actually contain values of the resource type.
+///
+/// ```
+/// # trait ResType { fn foo(&self); };
+/// # struct ParamType;
+/// # mod foreign_lib {
+/// # pub fn new(_: usize) -> *mut () { 42 as *mut () }
+/// # pub fn do_stuff(_: *mut (), _: usize) {}
+/// # }
+/// # fn convert_params(_: ParamType) -> usize { 42 }
+/// use std::marker::PhantomData;
+/// use std::mem;
+///
+/// struct ExternalResource<R> {
+///    resource_handle: *mut (),
+///    resource_type: PhantomData<R>,
+/// }
+///
+/// impl<R: ResType> ExternalResource<R> {
+///     fn new() -> ExternalResource<R> {
+///         let size_of_res = mem::size_of::<R>();
+///         ExternalResource {
+///             resource_handle: foreign_lib::new(size_of_res),
+///             resource_type: PhantomData,
+///         }
+///     }
+///
+///     fn do_stuff(&self, param: ParamType) {
+///         let foreign_params = convert_params(param);
+///         foreign_lib::do_stuff(self.resource_handle, foreign_params);
+///     }
+/// }
+/// ```
+///
+/// Another example: embedding a `PhantomData<T>` will inform the compiler
 /// that one or more instances of the type `T` could be dropped when
 /// instances of the type itself is dropped, though that may not be
 /// apparent from the other structure of the type itself. This is
index b542c9d47f7d4a386d9ac5148b7275ae245d008b..0d8e3044eccea1374cb06a9c54737cbc45d202b5 100644 (file)
 use option::Option;
 
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const RADIX: uint = 2;
+pub const RADIX: u32 = 2;
 
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MANTISSA_DIGITS: uint = 24;
+pub const MANTISSA_DIGITS: u32 = 24;
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const DIGITS: uint = 6;
+pub const DIGITS: u32 = 6;
 
 #[stable(feature = "rust1", since = "1.0.0")]
 pub const EPSILON: f32 = 1.19209290e-07_f32;
 pub const MAX: f32 = 3.40282347e+38_f32;
 
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MIN_EXP: int = -125;
+pub const MIN_EXP: i32 = -125;
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MAX_EXP: int = 128;
+pub const MAX_EXP: i32 = 128;
 
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MIN_10_EXP: int = -37;
+pub const MIN_10_EXP: i32 = -37;
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MAX_10_EXP: int = 38;
+pub const MAX_10_EXP: i32 = 38;
 
 #[stable(feature = "rust1", since = "1.0.0")]
 pub const NAN: f32 = 0.0_f32/0.0_f32;
@@ -193,12 +193,12 @@ fn classify(self) -> Fp {
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn mantissa_digits(_: Option<f32>) -> uint { MANTISSA_DIGITS }
+    fn mantissa_digits(_: Option<f32>) -> uint { MANTISSA_DIGITS as uint }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn digits(_: Option<f32>) -> uint { DIGITS }
+    fn digits(_: Option<f32>) -> uint { DIGITS as uint }
 
     #[inline]
     #[unstable(feature = "core")]
@@ -208,22 +208,22 @@ fn epsilon() -> f32 { EPSILON }
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn min_exp(_: Option<f32>) -> int { MIN_EXP }
+    fn min_exp(_: Option<f32>) -> int { MIN_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn max_exp(_: Option<f32>) -> int { MAX_EXP }
+    fn max_exp(_: Option<f32>) -> int { MAX_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn min_10_exp(_: Option<f32>) -> int { MIN_10_EXP }
+    fn min_10_exp(_: Option<f32>) -> int { MIN_10_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn max_10_exp(_: Option<f32>) -> int { MAX_10_EXP }
+    fn max_10_exp(_: Option<f32>) -> int { MAX_10_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
index 2aae7107548c6f3ecab3fa7d632635b7c277933e..d7e91058a46fbcb9fc38d91adc3185cd8020a897 100644 (file)
 // members of `Bounded` and `Float`.
 
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const RADIX: uint = 2;
+pub const RADIX: u32 = 2;
 
-pub const MANTISSA_DIGITS: uint = 53;
+pub const MANTISSA_DIGITS: u32 = 53;
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const DIGITS: uint = 15;
+pub const DIGITS: u32 = 15;
 
 #[stable(feature = "rust1", since = "1.0.0")]
 pub const EPSILON: f64 = 2.2204460492503131e-16_f64;
 pub const MAX: f64 = 1.7976931348623157e+308_f64;
 
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MIN_EXP: int = -1021;
+pub const MIN_EXP: i32 = -1021;
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MAX_EXP: int = 1024;
+pub const MAX_EXP: i32 = 1024;
 
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MIN_10_EXP: int = -307;
+pub const MIN_10_EXP: i32 = -307;
 #[unstable(feature = "core", reason = "pending integer conventions")]
-pub const MAX_10_EXP: int = 308;
+pub const MAX_10_EXP: i32 = 308;
 
 #[stable(feature = "rust1", since = "1.0.0")]
 pub const NAN: f64 = 0.0_f64/0.0_f64;
@@ -200,12 +200,12 @@ fn classify(self) -> Fp {
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn mantissa_digits(_: Option<f64>) -> uint { MANTISSA_DIGITS }
+    fn mantissa_digits(_: Option<f64>) -> uint { MANTISSA_DIGITS as uint }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn digits(_: Option<f64>) -> uint { DIGITS }
+    fn digits(_: Option<f64>) -> uint { DIGITS as uint }
 
     #[inline]
     #[unstable(feature = "core")]
@@ -215,22 +215,22 @@ fn epsilon() -> f64 { EPSILON }
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn min_exp(_: Option<f64>) -> int { MIN_EXP }
+    fn min_exp(_: Option<f64>) -> int { MIN_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn max_exp(_: Option<f64>) -> int { MAX_EXP }
+    fn max_exp(_: Option<f64>) -> int { MAX_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn min_10_exp(_: Option<f64>) -> int { MIN_10_EXP }
+    fn min_10_exp(_: Option<f64>) -> int { MIN_10_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
     #[deprecated(since = "1.0.0")]
-    fn max_10_exp(_: Option<f64>) -> int { MAX_10_EXP }
+    fn max_10_exp(_: Option<f64>) -> int { MAX_10_EXP as int }
 
     #[inline]
     #[unstable(feature = "core")]
index 954c8a08e64d6bafdd15a6ef6c2fe9e6ad29e8c9..fe0d6d13c4c06483649bdbf737fe89c68048cf43 100644 (file)
@@ -15,11 +15,11 @@ macro_rules! int_module { ($T:ty, $bits:expr) => (
 // FIXME(#11621): Should be deprecated once CTFE is implemented in favour of
 // calling the `mem::size_of` function.
 #[unstable(feature = "core")]
-pub const BITS : uint = $bits;
+pub const BITS : u32 = $bits;
 // FIXME(#11621): Should be deprecated once CTFE is implemented in favour of
 // calling the `mem::size_of` function.
 #[unstable(feature = "core")]
-pub const BYTES : uint = ($bits / 8);
+pub const BYTES : u32 = ($bits / 8);
 
 // FIXME(#11621): Should be deprecated once CTFE is implemented in favour of
 // calling the `Bounded::min_value` function.
index 318799f59a8101f48a41e9f02d6aa89f6ddc88ff..752eca797bd1398d5219b43220db75ed4cfaf6b7 100644 (file)
@@ -15,6 +15,8 @@
 #![stable(feature = "rust1", since = "1.0.0")]
 #![allow(missing_docs)]
 
+use self::wrapping::{OverflowingOps, WrappingOps};
+
 use char::CharExt;
 use clone::Clone;
 use cmp::{PartialEq, Eq, PartialOrd, Ord};
@@ -30,6 +32,9 @@
 use result::Result::{self, Ok, Err};
 use str::{FromStr, StrExt};
 
+#[unstable(feature = "core", reason = "may be removed or relocated")]
+pub mod wrapping;
+
 /// A built-in signed or unsigned integer.
 #[stable(feature = "rust1", since = "1.0.0")]
 pub trait Int
@@ -48,6 +53,8 @@ pub trait Int
     + BitXor<Output=Self>
     + Shl<uint, Output=Self>
     + Shr<uint, Output=Self>
+    + WrappingOps
+    + OverflowingOps
 {
     /// Returns the `0` value of this integer type.
     // FIXME (#5527): Should be an associated constant
@@ -86,7 +93,7 @@ pub trait Int
     /// ```
     #[unstable(feature = "core",
                reason = "pending integer conventions")]
-    fn count_ones(self) -> uint;
+    fn count_ones(self) -> u32;
 
     /// Returns the number of zeros in the binary representation of `self`.
     ///
@@ -102,7 +109,7 @@ pub trait Int
     #[unstable(feature = "core",
                reason = "pending integer conventions")]
     #[inline]
-    fn count_zeros(self) -> uint {
+    fn count_zeros(self) -> u32 {
         (!self).count_ones()
     }
 
@@ -120,7 +127,7 @@ fn count_zeros(self) -> uint {
     /// ```
     #[unstable(feature = "core",
                reason = "pending integer conventions")]
-    fn leading_zeros(self) -> uint;
+    fn leading_zeros(self) -> u32;
 
     /// Returns the number of trailing zeros in the binary representation
     /// of `self`.
@@ -136,7 +143,7 @@ fn count_zeros(self) -> uint {
     /// ```
     #[unstable(feature = "core",
                reason = "pending integer conventions")]
-    fn trailing_zeros(self) -> uint;
+    fn trailing_zeros(self) -> u32;
 
     /// Shifts the bits to the left by a specified amount amount, `n`, wrapping
     /// the truncated bits to the end of the resulting integer.
@@ -153,7 +160,7 @@ fn count_zeros(self) -> uint {
     /// ```
     #[unstable(feature = "core",
                reason = "pending integer conventions")]
-    fn rotate_left(self, n: uint) -> Self;
+    fn rotate_left(self, n: u32) -> Self;
 
     /// Shifts the bits to the right by a specified amount amount, `n`, wrapping
     /// the truncated bits to the beginning of the resulting integer.
@@ -170,7 +177,7 @@ fn count_zeros(self) -> uint {
     /// ```
     #[unstable(feature = "core",
                reason = "pending integer conventions")]
-    fn rotate_right(self, n: uint) -> Self;
+    fn rotate_right(self, n: u32) -> Self;
 
     /// Reverses the byte order of the integer.
     ///
@@ -376,11 +383,23 @@ fn pow(self, mut exp: u32) -> Self {
         let mut base = self;
         let mut acc: Self = Int::one();
 
+        let mut prev_base = self;
+        let mut base_oflo = false;
         while exp > 0 {
             if (exp & 1) == 1 {
-                acc = acc * base;
+                if base_oflo {
+                    // ensure overflow occurs in the same manner it
+                    // would have otherwise (i.e. signal any exception
+                    // it would have otherwise).
+                    acc = acc * (prev_base * prev_base);
+                } else {
+                    acc = acc * base;
+                }
             }
-            base = base * base;
+            prev_base = base;
+            let (new_base, new_base_oflo) = base.overflowing_mul(base);
+            base = new_base;
+            base_oflo = new_base_oflo;
             exp /= 2;
         }
         acc
@@ -418,23 +437,23 @@ fn min_value() -> $T { 0 }
             fn max_value() -> $T { -1 }
 
             #[inline]
-            fn count_ones(self) -> uint { unsafe { $ctpop(self as $ActualT) as uint } }
+            fn count_ones(self) -> u32 { unsafe { $ctpop(self as $ActualT) as u32 } }
 
             #[inline]
-            fn leading_zeros(self) -> uint { unsafe { $ctlz(self as $ActualT) as uint } }
+            fn leading_zeros(self) -> u32 { unsafe { $ctlz(self as $ActualT) as u32 } }
 
             #[inline]
-            fn trailing_zeros(self) -> uint { unsafe { $cttz(self as $ActualT) as uint } }
+            fn trailing_zeros(self) -> u32 { unsafe { $cttz(self as $ActualT) as u32 } }
 
             #[inline]
-            fn rotate_left(self, n: uint) -> $T {
+            fn rotate_left(self, n: u32) -> $T {
                 // Protect against undefined behaviour for over-long bit shifts
                 let n = n % $BITS;
                 (self << n) | (self >> (($BITS - n) % $BITS))
             }
 
             #[inline]
-            fn rotate_right(self, n: uint) -> $T {
+            fn rotate_right(self, n: u32) -> $T {
                 // Protect against undefined behaviour for over-long bit shifts
                 let n = n % $BITS;
                 (self >> n) | (self << (($BITS - n) % $BITS))
@@ -549,19 +568,19 @@ fn min_value() -> $T { (-1 as $T) << ($BITS - 1) }
             fn max_value() -> $T { let min: $T = Int::min_value(); !min }
 
             #[inline]
-            fn count_ones(self) -> uint { (self as $UnsignedT).count_ones() }
+            fn count_ones(self) -> u32 { (self as $UnsignedT).count_ones() }
 
             #[inline]
-            fn leading_zeros(self) -> uint { (self as $UnsignedT).leading_zeros() }
+            fn leading_zeros(self) -> u32 { (self as $UnsignedT).leading_zeros() }
 
             #[inline]
-            fn trailing_zeros(self) -> uint { (self as $UnsignedT).trailing_zeros() }
+            fn trailing_zeros(self) -> u32 { (self as $UnsignedT).trailing_zeros() }
 
             #[inline]
-            fn rotate_left(self, n: uint) -> $T { (self as $UnsignedT).rotate_left(n) as $T }
+            fn rotate_left(self, n: u32) -> $T { (self as $UnsignedT).rotate_left(n) as $T }
 
             #[inline]
-            fn rotate_right(self, n: uint) -> $T { (self as $UnsignedT).rotate_right(n) as $T }
+            fn rotate_right(self, n: u32) -> $T { (self as $UnsignedT).rotate_right(n) as $T }
 
             #[inline]
             fn swap_bytes(self) -> $T { (self as $UnsignedT).swap_bytes() as $T }
@@ -691,12 +710,12 @@ fn is_negative(self) -> bool { self < 0 }
 
 /// A built-in unsigned integer.
 #[stable(feature = "rust1", since = "1.0.0")]
-pub trait UnsignedInt: Int {
+pub trait UnsignedInt: Int + WrappingOps {
     /// Returns `true` iff `self == 2^k` for some `k`.
     #[stable(feature = "rust1", since = "1.0.0")]
     #[inline]
     fn is_power_of_two(self) -> bool {
-        (self - Int::one()) & self == Int::zero() && !(self == Int::zero())
+        (self.wrapping_sub(Int::one())) & self == Int::zero() && !(self == Int::zero())
     }
 
     /// Returns the smallest power of two greater than or equal to `self`.
@@ -706,7 +725,7 @@ fn is_power_of_two(self) -> bool {
     fn next_power_of_two(self) -> Self {
         let bits = size_of::<Self>() * 8;
         let one: Self = Int::one();
-        one << ((bits - (self - one).leading_zeros()) % bits)
+        one << ((bits - self.wrapping_sub(one).leading_zeros() as usize) % bits)
     }
 
     /// Returns the smallest power of two greater than or equal to `n`. If the
@@ -743,8 +762,16 @@ impl UnsignedInt for u64 {}
 pub trait ToPrimitive {
     /// Converts the value of `self` to an `int`.
     #[inline]
+    #[unstable(feature = "core")]
+    #[deprecated(since = "1.0.0", reason = "use to_isize")]
     fn to_int(&self) -> Option<int> {
-        self.to_i64().and_then(|x| x.to_int())
+        self.to_i64().and_then(|x| x.to_isize())
+    }
+
+    /// Converts the value of `self` to an `isize`.
+    #[inline]
+    fn to_isize(&self) -> Option<isize> {
+        self.to_i64().and_then(|x| x.to_isize())
     }
 
     /// Converts the value of `self` to an `i8`.
@@ -770,8 +797,16 @@ fn to_i32(&self) -> Option<i32> {
 
     /// Converts the value of `self` to an `uint`.
     #[inline]
+    #[unstable(feature = "core")]
+    #[deprecated(since = "1.0.0", reason = "use to_usize")]
     fn to_uint(&self) -> Option<uint> {
-        self.to_u64().and_then(|x| x.to_uint())
+        self.to_u64().and_then(|x| x.to_usize())
+    }
+
+    /// Converts the value of `self` to a `usize`.
+    #[inline]
+    fn to_usize(&self) -> Option<usize> {
+        self.to_u64().and_then(|x| x.to_usize())
     }
 
     /// Converts the value of `self` to an `u8`.
@@ -848,6 +883,8 @@ impl ToPrimitive for $T {
             #[inline]
             fn to_int(&self) -> Option<int> { impl_to_primitive_int_to_int!($T, int, *self) }
             #[inline]
+            fn to_isize(&self) -> Option<isize> { impl_to_primitive_int_to_int!($T, isize, *self) }
+            #[inline]
             fn to_i8(&self) -> Option<i8> { impl_to_primitive_int_to_int!($T, i8, *self) }
             #[inline]
             fn to_i16(&self) -> Option<i16> { impl_to_primitive_int_to_int!($T, i16, *self) }
@@ -859,6 +896,8 @@ fn to_i64(&self) -> Option<i64> { impl_to_primitive_int_to_int!($T, i64, *self)
             #[inline]
             fn to_uint(&self) -> Option<uint> { impl_to_primitive_int_to_uint!($T, uint, *self) }
             #[inline]
+            fn to_usize(&self) -> Option<usize> { impl_to_primitive_int_to_uint!($T, usize, *self) }
+            #[inline]
             fn to_u8(&self) -> Option<u8> { impl_to_primitive_int_to_uint!($T, u8, *self) }
             #[inline]
             fn to_u16(&self) -> Option<u16> { impl_to_primitive_int_to_uint!($T, u16, *self) }
@@ -875,7 +914,7 @@ fn to_f64(&self) -> Option<f64> { Some(*self as f64) }
     )
 }
 
-impl_to_primitive_int! { int }
+impl_to_primitive_int! { isize }
 impl_to_primitive_int! { i8 }
 impl_to_primitive_int! { i16 }
 impl_to_primitive_int! { i32 }
@@ -918,6 +957,8 @@ impl ToPrimitive for $T {
             #[inline]
             fn to_int(&self) -> Option<int> { impl_to_primitive_uint_to_int!(int, *self) }
             #[inline]
+            fn to_isize(&self) -> Option<int> { impl_to_primitive_uint_to_int!(isize, *self) }
+            #[inline]
             fn to_i8(&self) -> Option<i8> { impl_to_primitive_uint_to_int!(i8, *self) }
             #[inline]
             fn to_i16(&self) -> Option<i16> { impl_to_primitive_uint_to_int!(i16, *self) }
@@ -929,6 +970,8 @@ fn to_i64(&self) -> Option<i64> { impl_to_primitive_uint_to_int!(i64, *self) }
             #[inline]
             fn to_uint(&self) -> Option<uint> { impl_to_primitive_uint_to_uint!($T, uint, *self) }
             #[inline]
+            fn to_usize(&self) -> Option<uint> { impl_to_primitive_uint_to_uint!($T, usize, *self) }
+            #[inline]
             fn to_u8(&self) -> Option<u8> { impl_to_primitive_uint_to_uint!($T, u8, *self) }
             #[inline]
             fn to_u16(&self) -> Option<u16> { impl_to_primitive_uint_to_uint!($T, u16, *self) }
@@ -945,7 +988,7 @@ fn to_f64(&self) -> Option<f64> { Some(*self as f64) }
     )
 }
 
-impl_to_primitive_uint! { uint }
+impl_to_primitive_uint! { usize }
 impl_to_primitive_uint! { u8 }
 impl_to_primitive_uint! { u16 }
 impl_to_primitive_uint! { u32 }
@@ -973,6 +1016,8 @@ impl ToPrimitive for $T {
             #[inline]
             fn to_int(&self) -> Option<int> { Some(*self as int) }
             #[inline]
+            fn to_isize(&self) -> Option<int> { Some(*self as isize) }
+            #[inline]
             fn to_i8(&self) -> Option<i8> { Some(*self as i8) }
             #[inline]
             fn to_i16(&self) -> Option<i16> { Some(*self as i16) }
@@ -984,6 +1029,8 @@ fn to_i64(&self) -> Option<i64> { Some(*self as i64) }
             #[inline]
             fn to_uint(&self) -> Option<uint> { Some(*self as uint) }
             #[inline]
+            fn to_usize(&self) -> Option<uint> { Some(*self as usize) }
+            #[inline]
             fn to_u8(&self) -> Option<u8> { Some(*self as u8) }
             #[inline]
             fn to_u16(&self) -> Option<u16> { Some(*self as u16) }
@@ -1009,10 +1056,19 @@ pub trait FromPrimitive : ::marker::Sized {
     /// Convert an `int` to return an optional value of this type. If the
     /// value cannot be represented by this value, the `None` is returned.
     #[inline]
+    #[unstable(feature = "core")]
+    #[deprecated(since = "1.0.0", reason = "use from_isize")]
     fn from_int(n: int) -> Option<Self> {
         FromPrimitive::from_i64(n as i64)
     }
 
+    /// Convert an `isize` to return an optional value of this type. If the
+    /// value cannot be represented by this value, the `None` is returned.
+    #[inline]
+    fn from_isize(n: isize) -> Option<Self> {
+        FromPrimitive::from_i64(n as i64)
+    }
+
     /// Convert an `i8` to return an optional value of this type. If the
     /// type cannot be represented by this value, the `None` is returned.
     #[inline]
@@ -1041,10 +1097,19 @@ fn from_i32(n: i32) -> Option<Self> {
     /// Convert an `uint` to return an optional value of this type. If the
     /// type cannot be represented by this value, the `None` is returned.
     #[inline]
+    #[unstable(feature = "core")]
+    #[deprecated(since = "1.0.0", reason = "use from_usize")]
     fn from_uint(n: uint) -> Option<Self> {
         FromPrimitive::from_u64(n as u64)
     }
 
+    /// Convert a `usize` to return an optional value of this type. If the
+    /// type cannot be represented by this value, the `None` is returned.
+    #[inline]
+    fn from_usize(n: usize) -> Option<Self> {
+        FromPrimitive::from_u64(n as u64)
+    }
+
     /// Convert an `u8` to return an optional value of this type. If the
     /// type cannot be represented by this value, the `None` is returned.
     #[inline]
@@ -1087,8 +1152,15 @@ fn from_f64(n: f64) -> Option<Self> {
 
 /// A utility function that just calls `FromPrimitive::from_int`.
 #[unstable(feature = "core", reason = "likely to be removed")]
+#[deprecated(since = "1.0.0", reason = "use from_isize")]
 pub fn from_int<A: FromPrimitive>(n: int) -> Option<A> {
-    FromPrimitive::from_int(n)
+    FromPrimitive::from_isize(n)
+}
+
+/// A utility function that just calls `FromPrimitive::from_isize`.
+#[unstable(feature = "core", reason = "likely to be removed")]
+pub fn from_isize<A: FromPrimitive>(n: isize) -> Option<A> {
+    FromPrimitive::from_isize(n)
 }
 
 /// A utility function that just calls `FromPrimitive::from_i8`.
@@ -1117,8 +1189,15 @@ pub fn from_i64<A: FromPrimitive>(n: i64) -> Option<A> {
 
 /// A utility function that just calls `FromPrimitive::from_uint`.
 #[unstable(feature = "core", reason = "likely to be removed")]
+#[deprecated(since = "1.0.0", reason = "use from_uint")]
 pub fn from_uint<A: FromPrimitive>(n: uint) -> Option<A> {
-    FromPrimitive::from_uint(n)
+    FromPrimitive::from_usize(n)
+}
+
+/// A utility function that just calls `FromPrimitive::from_usize`.
+#[unstable(feature = "core", reason = "likely to be removed")]
+pub fn from_usize<A: FromPrimitive>(n: usize) -> Option<A> {
+    FromPrimitive::from_usize(n)
 }
 
 /// A utility function that just calls `FromPrimitive::from_u8`.
@@ -1159,6 +1238,7 @@ pub fn from_f64<A: FromPrimitive>(n: f64) -> Option<A> {
 
 macro_rules! impl_from_primitive {
     ($T:ty, $to_ty:ident) => (
+        #[allow(deprecated)]
         impl FromPrimitive for $T {
             #[inline] fn from_int(n: int) -> Option<$T> { n.$to_ty() }
             #[inline] fn from_i8(n: i8) -> Option<$T> { n.$to_ty() }
@@ -1220,6 +1300,7 @@ macro_rules! impl_num_cast {
     ($T:ty, $conv:ident) => (
         impl NumCast for $T {
             #[inline]
+            #[allow(deprecated)]
             fn from<N: ToPrimitive>(n: N) -> Option<$T> {
                 // `$conv` could be generated using `concat_idents!`, but that
                 // macro seems to be broken at the moment
@@ -1436,7 +1517,7 @@ pub trait FromStrRadix {
     fn from_str_radix(str: &str, radix: u32) -> Result<Self, Self::Err>;
 }
 
-/// A utility function that just calls FromStrRadix::from_str_radix.
+/// A utility function that just calls `FromStrRadix::from_str_radix`.
 #[unstable(feature = "core", reason = "needs reevaluation")]
 pub fn from_str_radix<T: FromStrRadix>(str: &str, radix: u32)
                                        -> Result<T, T::Err> {
@@ -1718,12 +1799,12 @@ fn from_str_radix(src: &str, radix: u32)
         }
     }
 }
-from_str_radix_int_impl! { int }
+from_str_radix_int_impl! { isize }
 from_str_radix_int_impl! { i8 }
 from_str_radix_int_impl! { i16 }
 from_str_radix_int_impl! { i32 }
 from_str_radix_int_impl! { i64 }
-from_str_radix_int_impl! { uint }
+from_str_radix_int_impl! { usize }
 from_str_radix_int_impl! { u8 }
 from_str_radix_int_impl! { u16 }
 from_str_radix_int_impl! { u32 }
index 06502be54aaccded31e2541928248cde27f77407..d0c4885ad00b77ebbfaef418cb230976e6955f21 100644 (file)
 macro_rules! uint_module { ($T:ty, $T_SIGNED:ty, $bits:expr) => (
 
 #[unstable(feature = "core")]
-pub const BITS : uint = $bits;
+pub const BITS : u32 = $bits;
 #[unstable(feature = "core")]
-pub const BYTES : uint = ($bits / 8);
+pub const BYTES : u32 = ($bits / 8);
 
 #[stable(feature = "rust1", since = "1.0.0")]
 pub const MIN: $T = 0 as $T;
 #[stable(feature = "rust1", since = "1.0.0")]
-pub const MAX: $T = 0 as $T - 1 as $T;
+pub const MAX: $T = !0 as $T;
 
 ) }
diff --git a/src/libcore/num/wrapping.rs b/src/libcore/num/wrapping.rs
new file mode 100644 (file)
index 0000000..f8fc4ef
--- /dev/null
@@ -0,0 +1,278 @@
+// 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.
+#![allow(missing_docs)]
+
+use ops::*;
+
+use intrinsics::{overflowing_add, overflowing_sub, overflowing_mul};
+
+use intrinsics::{i8_add_with_overflow, u8_add_with_overflow};
+use intrinsics::{i16_add_with_overflow, u16_add_with_overflow};
+use intrinsics::{i32_add_with_overflow, u32_add_with_overflow};
+use intrinsics::{i64_add_with_overflow, u64_add_with_overflow};
+use intrinsics::{i8_sub_with_overflow, u8_sub_with_overflow};
+use intrinsics::{i16_sub_with_overflow, u16_sub_with_overflow};
+use intrinsics::{i32_sub_with_overflow, u32_sub_with_overflow};
+use intrinsics::{i64_sub_with_overflow, u64_sub_with_overflow};
+use intrinsics::{i8_mul_with_overflow, u8_mul_with_overflow};
+use intrinsics::{i16_mul_with_overflow, u16_mul_with_overflow};
+use intrinsics::{i32_mul_with_overflow, u32_mul_with_overflow};
+use intrinsics::{i64_mul_with_overflow, u64_mul_with_overflow};
+
+pub trait WrappingOps {
+    fn wrapping_add(self, rhs: Self) -> Self;
+    fn wrapping_sub(self, rhs: Self) -> Self;
+    fn wrapping_mul(self, rhs: Self) -> Self;
+}
+
+#[unstable(feature = "core", reason = "may be removed, renamed, or relocated")]
+pub trait OverflowingOps {
+    fn overflowing_add(self, rhs: Self) -> (Self, bool);
+    fn overflowing_sub(self, rhs: Self) -> (Self, bool);
+    fn overflowing_mul(self, rhs: Self) -> (Self, bool);
+}
+
+macro_rules! wrapping_impl {
+    ($($t:ty)*) => ($(
+        impl WrappingOps for $t {
+            #[inline(always)]
+            fn wrapping_add(self, rhs: $t) -> $t {
+                unsafe {
+                    overflowing_add(self, rhs)
+                }
+            }
+            #[inline(always)]
+            fn wrapping_sub(self, rhs: $t) -> $t {
+                unsafe {
+                    overflowing_sub(self, rhs)
+                }
+            }
+            #[inline(always)]
+            fn wrapping_mul(self, rhs: $t) -> $t {
+                unsafe {
+                    overflowing_mul(self, rhs)
+                }
+            }
+        }
+    )*)
+}
+
+wrapping_impl! { uint u8 u16 u32 u64 int i8 i16 i32 i64 }
+
+#[unstable(feature = "core", reason = "may be removed, renamed, or relocated")]
+#[derive(PartialEq,Eq,PartialOrd,Ord,Clone,Copy)]
+pub struct Wrapping<T>(pub T);
+
+impl<T:WrappingOps> Add for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn add(self, other: Wrapping<T>) -> Wrapping<T> {
+        Wrapping(self.0.wrapping_add(other.0))
+    }
+}
+
+impl<T:WrappingOps> Sub for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn sub(self, other: Wrapping<T>) -> Wrapping<T> {
+        Wrapping(self.0.wrapping_sub(other.0))
+    }
+}
+
+impl<T:WrappingOps> Mul for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn mul(self, other: Wrapping<T>) -> Wrapping<T> {
+        Wrapping(self.0.wrapping_mul(other.0))
+    }
+}
+
+impl<T:WrappingOps+Not<Output=T>> Not for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    fn not(self) -> Wrapping<T> {
+        Wrapping(!self.0)
+    }
+}
+
+impl<T:WrappingOps+BitXor<Output=T>> BitXor for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn bitxor(self, other: Wrapping<T>) -> Wrapping<T> {
+        Wrapping(self.0 ^ other.0)
+    }
+}
+
+impl<T:WrappingOps+BitOr<Output=T>> BitOr for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn bitor(self, other: Wrapping<T>) -> Wrapping<T> {
+        Wrapping(self.0 | other.0)
+    }
+}
+
+impl<T:WrappingOps+BitAnd<Output=T>> BitAnd for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn bitand(self, other: Wrapping<T>) -> Wrapping<T> {
+        Wrapping(self.0 & other.0)
+    }
+}
+
+impl<T:WrappingOps+Shl<uint,Output=T>> Shl<uint> for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn shl(self, other: uint) -> Wrapping<T> {
+        Wrapping(self.0 << other)
+    }
+}
+
+impl<T:WrappingOps+Shr<uint,Output=T>> Shr<uint> for Wrapping<T> {
+    type Output = Wrapping<T>;
+
+    #[inline(always)]
+    fn shr(self, other: uint) -> Wrapping<T> {
+        Wrapping(self.0 >> other)
+    }
+}
+
+macro_rules! overflowing_impl {
+    ($($t:ident)*) => ($(
+        impl OverflowingOps for $t {
+            #[inline(always)]
+            fn overflowing_add(self, rhs: $t) -> ($t, bool) {
+                unsafe {
+                    concat_idents!($t, _add_with_overflow)(self, rhs)
+                }
+            }
+            #[inline(always)]
+            fn overflowing_sub(self, rhs: $t) -> ($t, bool) {
+                unsafe {
+                    concat_idents!($t, _sub_with_overflow)(self, rhs)
+                }
+            }
+            #[inline(always)]
+            fn overflowing_mul(self, rhs: $t) -> ($t, bool) {
+                unsafe {
+                    concat_idents!($t, _mul_with_overflow)(self, rhs)
+                }
+            }
+        }
+    )*)
+}
+
+overflowing_impl! { u8 u16 u32 u64 i8 i16 i32 i64 }
+
+#[cfg(target_pointer_width = "64")]
+impl OverflowingOps for usize {
+    #[inline(always)]
+    fn overflowing_add(self, rhs: usize) -> (usize, bool) {
+        unsafe {
+            let res = u64_add_with_overflow(self as u64, rhs as u64);
+            (res.0 as usize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_sub(self, rhs: usize) -> (usize, bool) {
+        unsafe {
+            let res = u64_sub_with_overflow(self as u64, rhs as u64);
+            (res.0 as usize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_mul(self, rhs: usize) -> (usize, bool) {
+        unsafe {
+            let res = u64_mul_with_overflow(self as u64, rhs as u64);
+            (res.0 as usize, res.1)
+        }
+    }
+}
+
+#[cfg(target_pointer_width = "32")]
+impl OverflowingOps for usize {
+    #[inline(always)]
+    fn overflowing_add(self, rhs: usize) -> (usize, bool) {
+        unsafe {
+            let res = u32_add_with_overflow(self as u32, rhs as u32);
+            (res.0 as usize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_sub(self, rhs: usize) -> (usize, bool) {
+        unsafe {
+            let res = u32_sub_with_overflow(self as u32, rhs as u32);
+            (res.0 as usize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_mul(self, rhs: usize) -> (usize, bool) {
+        unsafe {
+            let res = u32_mul_with_overflow(self as u32, rhs as u32);
+            (res.0 as usize, res.1)
+        }
+    }
+}
+
+#[cfg(target_pointer_width = "64")]
+impl OverflowingOps for isize {
+    #[inline(always)]
+    fn overflowing_add(self, rhs: isize) -> (isize, bool) {
+        unsafe {
+            let res = i64_add_with_overflow(self as i64, rhs as i64);
+            (res.0 as isize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_sub(self, rhs: isize) -> (isize, bool) {
+        unsafe {
+            let res = i64_sub_with_overflow(self as i64, rhs as i64);
+            (res.0 as isize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_mul(self, rhs: isize) -> (isize, bool) {
+        unsafe {
+            let res = i64_mul_with_overflow(self as i64, rhs as i64);
+            (res.0 as isize, res.1)
+        }
+    }
+}
+
+#[cfg(target_pointer_width = "32")]
+impl OverflowingOps for isize {
+    #[inline(always)]
+    fn overflowing_add(self, rhs: isize) -> (isize, bool) {
+        unsafe {
+            let res = i32_add_with_overflow(self as i32, rhs as i32);
+            (res.0 as isize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_sub(self, rhs: isize) -> (isize, bool) {
+        unsafe {
+            let res = i32_sub_with_overflow(self as i32, rhs as i32);
+            (res.0 as isize, res.1)
+        }
+    }
+    #[inline(always)]
+    fn overflowing_mul(self, rhs: isize) -> (isize, bool) {
+        unsafe {
+            let res = i32_mul_with_overflow(self as i32, rhs as i32);
+            (res.0 as isize, res.1)
+        }
+    }
+}
index c382ac46d5db9895a99241e95d32291f3da1650e..4116d8be9fb5c034dddf16bf96a088c7745870ca 100644 (file)
@@ -913,6 +913,7 @@ macro_rules! shr_impl_all {
 #[stable(feature = "rust1", since = "1.0.0")]
 pub trait Index<Idx: ?Sized> {
     /// The returned type after indexing
+    #[stable(feature = "rust1", since = "1.0.0")]
     type Output: ?Sized;
 
     /// The method for the indexing (`Foo[Bar]`) operation
index 1ecbd8fae8cdb664b5f9549a358ea6c7cb7b7b01..5343cdaaf088c52aa1631b1b3804c166544b4af1 100644 (file)
@@ -385,7 +385,7 @@ pub fn unwrap_or(self, def: T) -> T {
     /// # Example
     ///
     /// ```
-    /// let k = 10i32;
+    /// let k = 10;
     /// assert_eq!(Some(4).unwrap_or_else(|| 2 * k), 4);
     /// assert_eq!(None.unwrap_or_else(|| 2 * k), 20);
     /// ```
index 5cc210df5b464e5d6581614df4d17a2012a6f323..35dfc7626872705f3378f8c3a0ad17161a6d9cee 100644 (file)
@@ -70,6 +70,7 @@ impl<T> Copy for Slice<T> {}
 #[deprecated(reason = "unboxed new closures do not have a universal representation; \
                        `&Fn` (etc) trait objects should use `TraitObject` instead",
              since= "1.0.0")]
+#[allow(deprecated) /* for deriving Copy impl */]
 pub struct Closure {
     pub code: *mut (),
     pub env: *mut (),
index b8271562d2e670c22677a86ce61964f51325a053..6c3afdf884953ad0966eef3707fb5404cdcbfc9a 100644 (file)
 //! fn write_info(info: &Info) -> Result<(), IoError> {
 //!     let mut file = File::open_mode(&Path::new("my_best_friends.txt"), Open, Write);
 //!     // Early return on error
-//!     if let Err(e) = file.write_line(format!("name: {}", info.name).as_slice()) {
+//!     if let Err(e) = file.write_line(&format!("name: {}", info.name)) {
 //!         return Err(e)
 //!     }
-//!     if let Err(e) = file.write_line(format!("age: {}", info.age).as_slice()) {
+//!     if let Err(e) = file.write_line(&format!("age: {}", info.age)) {
 //!         return Err(e)
 //!     }
-//!     return file.write_line(format!("rating: {}", info.rating).as_slice());
+//!     return file.write_line(&format!("rating: {}", info.rating));
 //! }
 //! ```
 //!
 //! fn write_info(info: &Info) -> Result<(), IoError> {
 //!     let mut file = File::open_mode(&Path::new("my_best_friends.txt"), Open, Write);
 //!     // Early return on error
-//!     try!(file.write_line(format!("name: {}", info.name).as_slice()));
-//!     try!(file.write_line(format!("age: {}", info.age).as_slice()));
-//!     try!(file.write_line(format!("rating: {}", info.rating).as_slice()));
+//!     try!(file.write_line(&format!("name: {}", info.name)));
+//!     try!(file.write_line(&format!("age: {}", info.age)));
+//!     try!(file.write_line(&format!("rating: {}", info.rating)));
 //!     return Ok(());
 //! }
 //! ```
index 5b78da34eddde0e7dd363383b3fd0d4b719c5640..1f58d7753549d699fee276187b16e99b1d147b42 100644 (file)
@@ -351,6 +351,7 @@ fn chunks_mut(&mut self, chunk_size: usize) -> ChunksMut<T> {
         ChunksMut { v: self, chunk_size: chunk_size }
     }
 
+    #[inline]
     fn swap(&mut self, a: usize, b: usize) {
         unsafe {
             // Can't take two mutable loans from one vector, so instead just cast
@@ -1167,13 +1168,23 @@ fn size_hint(&self) -> (usize, Option<usize>) {
 forward_iterator! { RSplitNMut: T, &'a mut [T] }
 
 /// An iterator over overlapping subslices of length `size`.
-#[derive(Clone)]
 #[stable(feature = "rust1", since = "1.0.0")]
 pub struct Windows<'a, T:'a> {
     v: &'a [T],
     size: usize
 }
 
+// FIXME(#19839) Remove in favor of `#[derive(Clone)]`
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<'a, T> Clone for Windows<'a, T> {
+    fn clone(&self) -> Windows<'a, T> {
+        Windows {
+            v: self.v,
+            size: self.size,
+        }
+    }
+}
+
 #[stable(feature = "rust1", since = "1.0.0")]
 impl<'a, T> Iterator for Windows<'a, T> {
     type Item = &'a [T];
@@ -1239,13 +1250,23 @@ fn idx(&mut self, index: usize) -> Option<&'a [T]> {
 ///
 /// When the slice len is not evenly divided by the chunk size, the last slice
 /// of the iteration will be the remainder.
-#[derive(Clone)]
 #[stable(feature = "rust1", since = "1.0.0")]
 pub struct Chunks<'a, T:'a> {
     v: &'a [T],
     size: usize
 }
 
+// FIXME(#19839) Remove in favor of `#[derive(Clone)]`
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<'a, T> Clone for Chunks<'a, T> {
+    fn clone(&self) -> Chunks<'a, T> {
+        Chunks {
+            v: self.v,
+            size: self.size,
+        }
+    }
+}
+
 #[stable(feature = "rust1", since = "1.0.0")]
 impl<'a, T> Iterator for Chunks<'a, T> {
     type Item = &'a [T];
index bb03994fc7a82ddf0bb0b83c2a72fd0d0c39d063..a5ade2ae2a5793345e602245f87f097594c5a1f3 100644 (file)
@@ -134,12 +134,23 @@ impl FromStr for bool {
 
     /// Parse a `bool` from a string.
     ///
-    /// Yields an `Option<bool>`, because `s` may or may not actually be
-    /// parseable.
+    /// Yields a `Result<bool, ParseBoolError>`, because `s` may or may not
+    /// actually be parseable.
     ///
     /// # Examples
     ///
     /// ```rust
+    /// use std::str::FromStr;
+    ///
+    /// assert_eq!(FromStr::from_str("true"), Ok(true));
+    /// assert_eq!(FromStr::from_str("false"), Ok(false));
+    /// assert!(<bool as FromStr>::from_str("not even a boolean").is_err());
+    /// ```
+    ///
+    /// Note, in many cases, the StrExt::parse() which is based on
+    /// this FromStr::from_str() is more proper.
+    ///
+    /// ```rust
     /// assert_eq!("true".parse(), Ok(true));
     /// assert_eq!("false".parse(), Ok(false));
     /// assert!("not even a boolean".parse::<bool>().is_err());
@@ -324,21 +335,20 @@ pub struct Chars<'a> {
     iter: slice::Iter<'a, u8>
 }
 
-// Return the initial codepoint accumulator for the first byte.
-// The first byte is special, only want bottom 5 bits for width 2, 4 bits
-// for width 3, and 3 bits for width 4
-macro_rules! utf8_first_byte {
-    ($byte:expr, $width:expr) => (($byte & (0x7F >> $width)) as u32)
-}
+/// Return the initial codepoint accumulator for the first byte.
+/// The first byte is special, only want bottom 5 bits for width 2, 4 bits
+/// for width 3, and 3 bits for width 4.
+#[inline]
+fn utf8_first_byte(byte: u8, width: u32) -> u32 { (byte & (0x7F >> width)) as u32 }
 
-// return the value of $ch updated with continuation byte $byte
-macro_rules! utf8_acc_cont_byte {
-    ($ch:expr, $byte:expr) => (($ch << 6) | ($byte & CONT_MASK) as u32)
-}
+/// Return the value of `ch` updated with continuation byte `byte`.
+#[inline]
+fn utf8_acc_cont_byte(ch: u32, byte: u8) -> u32 { (ch << 6) | (byte & CONT_MASK) as u32 }
 
-macro_rules! utf8_is_cont_byte {
-    ($byte:expr) => (($byte & !CONT_MASK) == TAG_CONT_U8)
-}
+/// Checks whether the byte is a UTF-8 continuation byte (i.e. starts with the
+/// bits `10`).
+#[inline]
+fn utf8_is_cont_byte(byte: u8) -> bool { (byte & !CONT_MASK) == TAG_CONT_U8 }
 
 #[inline]
 fn unwrap_or_0(opt: Option<&u8>) -> u8 {
@@ -363,20 +373,20 @@ pub fn next_code_point(bytes: &mut slice::Iter<u8>) -> Option<u32> {
     // Multibyte case follows
     // Decode from a byte combination out of: [[[x y] z] w]
     // NOTE: Performance is sensitive to the exact formulation here
-    let init = utf8_first_byte!(x, 2);
+    let init = utf8_first_byte(x, 2);
     let y = unwrap_or_0(bytes.next());
-    let mut ch = utf8_acc_cont_byte!(init, y);
+    let mut ch = utf8_acc_cont_byte(init, y);
     if x >= 0xE0 {
         // [[x y z] w] case
         // 5th bit in 0xE0 .. 0xEF is always clear, so `init` is still valid
         let z = unwrap_or_0(bytes.next());
-        let y_z = utf8_acc_cont_byte!((y & CONT_MASK) as u32, z);
+        let y_z = utf8_acc_cont_byte((y & CONT_MASK) as u32, z);
         ch = init << 12 | y_z;
         if x >= 0xF0 {
             // [x y z w] case
             // use only the lower 3 bits of `init`
             let w = unwrap_or_0(bytes.next());
-            ch = (init & 7) << 18 | utf8_acc_cont_byte!(y_z, w);
+            ch = (init & 7) << 18 | utf8_acc_cont_byte(y_z, w);
         }
     }
 
@@ -399,18 +409,18 @@ pub fn next_code_point_reverse(bytes: &mut slice::Iter<u8>) -> Option<u32> {
     // Decode from a byte combination out of: [x [y [z w]]]
     let mut ch;
     let z = unwrap_or_0(bytes.next_back());
-    ch = utf8_first_byte!(z, 2);
-    if utf8_is_cont_byte!(z) {
+    ch = utf8_first_byte(z, 2);
+    if utf8_is_cont_byte(z) {
         let y = unwrap_or_0(bytes.next_back());
-        ch = utf8_first_byte!(y, 3);
-        if utf8_is_cont_byte!(y) {
+        ch = utf8_first_byte(y, 3);
+        if utf8_is_cont_byte(y) {
             let x = unwrap_or_0(bytes.next_back());
-            ch = utf8_first_byte!(x, 4);
-            ch = utf8_acc_cont_byte!(ch, y);
+            ch = utf8_first_byte(x, 4);
+            ch = utf8_acc_cont_byte(ch, y);
         }
-        ch = utf8_acc_cont_byte!(ch, z);
+        ch = utf8_acc_cont_byte(ch, z);
     }
-    ch = utf8_acc_cont_byte!(ch, w);
+    ch = utf8_acc_cont_byte(ch, w);
 
     Some(ch)
 }
@@ -833,6 +843,7 @@ fn next(&mut self, haystack: &[u8], needle: &[u8], long_period: bool)
     #[inline]
     #[allow(dead_code)]
     fn maximal_suffix(arr: &[u8], reversed: bool) -> (usize, usize) {
+        use num::wrapping::WrappingOps;
         let mut left = -1; // Corresponds to i in the paper
         let mut right = 0; // Corresponds to j in the paper
         let mut offset = 1; // Corresponds to k in the paper
@@ -842,17 +853,17 @@ fn maximal_suffix(arr: &[u8], reversed: bool) -> (usize, usize) {
             let a;
             let b;
             if reversed {
-                a = arr[left + offset];
+                a = arr[left.wrapping_add(offset)];
                 b = arr[right + offset];
             } else {
                 a = arr[right + offset];
-                b = arr[left + offset];
+                b = arr[left.wrapping_add(offset)];
             }
             if a < b {
                 // Suffix is smaller, period is entire prefix so far.
                 right += offset;
                 offset = 1;
-                period = right - left;
+                period = right.wrapping_sub(left);
             } else if a == b {
                 // Advance through repetition of the current period.
                 if offset == period {
@@ -869,7 +880,7 @@ fn maximal_suffix(arr: &[u8], reversed: bool) -> (usize, usize) {
                 period = 1;
             }
         }
-        (left + 1, period)
+        (left.wrapping_add(1), period)
     }
 }
 
@@ -938,6 +949,7 @@ fn next(&mut self) -> Option<(usize, usize)> {
 #[unstable(feature = "core")]
 #[deprecated(since = "1.0.0", reason = "use `Split` with a `&str`")]
 pub struct SplitStr<'a, P: Pattern<'a>>(Split<'a, P>);
+#[allow(deprecated)]
 impl<'a, P: Pattern<'a>> Iterator for SplitStr<'a, P> {
     type Item = &'a str;
 
@@ -1030,7 +1042,7 @@ macro_rules! next { () => {
         // ASCII characters are always valid, so only large
         // bytes need more examination.
         if first >= 128 {
-            let w = UTF8_CHAR_WIDTH[first as usize] as usize;
+            let w = UTF8_CHAR_WIDTH[first as usize];
             let second = next!();
             // 2-byte encoding is for codepoints  \u{0080} to  \u{07ff}
             //        first  C2 80        last DF BF
@@ -1109,9 +1121,9 @@ pub struct CharRange {
 }
 
 /// Mask of the value bits of a continuation byte
-const CONT_MASK: u8 = 0b0011_1111u8;
+const CONT_MASK: u8 = 0b0011_1111;
 /// Value of the tag bits (tag mask is !CONT_MASK) of a continuation byte
-const TAG_CONT_U8: u8 = 0b1000_0000u8;
+const TAG_CONT_U8: u8 = 0b1000_0000;
 
 /*
 Section: Trait implementations
@@ -1328,6 +1340,7 @@ pub trait StrExt {
     fn split_terminator<'a, P: Pattern<'a>>(&'a self, pat: P) -> SplitTerminator<'a, P>;
     fn rsplitn<'a, P: Pattern<'a>>(&'a self, count: usize, pat: P) -> RSplitN<'a, P>;
     fn match_indices<'a, P: Pattern<'a>>(&'a self, pat: P) -> MatchIndices<'a, P>;
+    #[allow(deprecated) /* for SplitStr */]
     fn split_str<'a, P: Pattern<'a>>(&'a self, pat: P) -> SplitStr<'a, P>;
     fn lines<'a>(&'a self) -> Lines<'a>;
     fn lines_any<'a>(&'a self) -> LinesAny<'a>;
@@ -1557,7 +1570,7 @@ fn is_char_boundary(&self, index: usize) -> bool {
         if index == self.len() { return true; }
         match self.as_bytes().get(index) {
             None => false,
-            Some(&b) => b < 128u8 || b >= 192u8,
+            Some(&b) => b < 128 || b >= 192,
         }
     }
 
@@ -1583,14 +1596,14 @@ fn multibyte_char_range_at_reverse(s: &str, mut i: usize) -> CharRange {
                 i -= 1;
             }
 
-            let mut val = s.as_bytes()[i] as u32;
-            let w = UTF8_CHAR_WIDTH[val as usize] as usize;
-            assert!((w != 0));
+            let first= s.as_bytes()[i];
+            let w = UTF8_CHAR_WIDTH[first as usize];
+            assert!(w != 0);
 
-            val = utf8_first_byte!(val, w);
-            val = utf8_acc_cont_byte!(val, s.as_bytes()[i + 1]);
-            if w > 2 { val = utf8_acc_cont_byte!(val, s.as_bytes()[i + 2]); }
-            if w > 3 { val = utf8_acc_cont_byte!(val, s.as_bytes()[i + 3]); }
+            let mut val = utf8_first_byte(first, w as u32);
+            val = utf8_acc_cont_byte(val, s.as_bytes()[i + 1]);
+            if w > 2 { val = utf8_acc_cont_byte(val, s.as_bytes()[i + 2]); }
+            if w > 3 { val = utf8_acc_cont_byte(val, s.as_bytes()[i + 3]); }
 
             return CharRange {ch: unsafe { mem::transmute(val) }, next: i};
         }
@@ -1669,22 +1682,22 @@ fn parse<T: FromStr>(&self) -> Result<T, T::Err> { FromStr::from_str(self) }
 #[inline]
 #[unstable(feature = "core")]
 pub fn char_range_at_raw(bytes: &[u8], i: usize) -> (u32, usize) {
-    if bytes[i] < 128u8 {
+    if bytes[i] < 128 {
         return (bytes[i] as u32, i + 1);
     }
 
     // Multibyte case is a fn to allow char_range_at to inline cleanly
     fn multibyte_char_range_at(bytes: &[u8], i: usize) -> (u32, usize) {
-        let mut val = bytes[i] as u32;
-        let w = UTF8_CHAR_WIDTH[val as usize] as usize;
-        assert!((w != 0));
+        let first = bytes[i];
+        let w = UTF8_CHAR_WIDTH[first as usize];
+        assert!(w != 0);
 
-        val = utf8_first_byte!(val, w);
-        val = utf8_acc_cont_byte!(val, bytes[i + 1]);
-        if w > 2 { val = utf8_acc_cont_byte!(val, bytes[i + 2]); }
-        if w > 3 { val = utf8_acc_cont_byte!(val, bytes[i + 3]); }
+        let mut val = utf8_first_byte(first, w as u32);
+        val = utf8_acc_cont_byte(val, bytes[i + 1]);
+        if w > 2 { val = utf8_acc_cont_byte(val, bytes[i + 2]); }
+        if w > 3 { val = utf8_acc_cont_byte(val, bytes[i + 3]); }
 
-        return (val, i + w);
+        return (val, i + w as usize);
     }
 
     multibyte_char_range_at(bytes, i)
index 8b5e46f85fa6ac181b1e7968adaa364214c407ad..39f5d237a2b7364501ab7a52bbccc5ca2b8df2c4 100644 (file)
@@ -68,7 +68,7 @@ fn any_downcast_ref() {
 #[test]
 fn any_downcast_mut() {
     let mut a = 5_usize;
-    let mut b = box 7_usize;
+    let mut b: Box<_> = box 7_usize;
 
     let a_r = &mut a as &mut Any;
     let tmp: &mut uint = &mut *b;
index 317ef3a570143e9611f73d3e00047ccbf71c8045..3397cbb18faa09c38284194e5149a95cb7141047 100644 (file)
@@ -109,7 +109,7 @@ fn double_borrow_single_release_no_borrow_mut() {
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 fn discard_doesnt_unborrow() {
     let x = RefCell::new(0);
     let _b = x.borrow();
index 32dc6440b1326e546c8110da9fbf6ce7b3f7e98c..65e941d160d0453d0fce8e837c2c1dda14f12c41 100644 (file)
@@ -57,35 +57,47 @@ fn test_to_digit() {
 
 #[test]
 fn test_to_lowercase() {
-    assert_eq!('A'.to_lowercase(), 'a');
-    assert_eq!('Ö'.to_lowercase(), 'ö');
-    assert_eq!('ß'.to_lowercase(), 'ß');
-    assert_eq!('Ü'.to_lowercase(), 'ü');
-    assert_eq!('💩'.to_lowercase(), '💩');
-    assert_eq!('Σ'.to_lowercase(), 'σ');
-    assert_eq!('Τ'.to_lowercase(), 'τ');
-    assert_eq!('Ι'.to_lowercase(), 'ι');
-    assert_eq!('Γ'.to_lowercase(), 'γ');
-    assert_eq!('Μ'.to_lowercase(), 'μ');
-    assert_eq!('Α'.to_lowercase(), 'α');
-    assert_eq!('Σ'.to_lowercase(), 'σ');
+    fn lower(c: char) -> char {
+        let mut it = c.to_lowercase();
+        let c = it.next().unwrap();
+        assert!(it.next().is_none());
+        c
+    }
+    assert_eq!(lower('A'), 'a');
+    assert_eq!(lower('Ö'), 'ö');
+    assert_eq!(lower('ß'), 'ß');
+    assert_eq!(lower('Ü'), 'ü');
+    assert_eq!(lower('💩'), '💩');
+    assert_eq!(lower('Σ'), 'σ');
+    assert_eq!(lower('Τ'), 'τ');
+    assert_eq!(lower('Ι'), 'ι');
+    assert_eq!(lower('Γ'), 'γ');
+    assert_eq!(lower('Μ'), 'μ');
+    assert_eq!(lower('Α'), 'α');
+    assert_eq!(lower('Σ'), 'σ');
 }
 
 #[test]
 fn test_to_uppercase() {
-    assert_eq!('a'.to_uppercase(), 'A');
-    assert_eq!('ö'.to_uppercase(), 'Ö');
-    assert_eq!('ß'.to_uppercase(), 'ß'); // not ẞ: Latin capital letter sharp s
-    assert_eq!('ü'.to_uppercase(), 'Ü');
-    assert_eq!('💩'.to_uppercase(), '💩');
-
-    assert_eq!('σ'.to_uppercase(), 'Σ');
-    assert_eq!('τ'.to_uppercase(), 'Τ');
-    assert_eq!('ι'.to_uppercase(), 'Ι');
-    assert_eq!('γ'.to_uppercase(), 'Γ');
-    assert_eq!('μ'.to_uppercase(), 'Μ');
-    assert_eq!('α'.to_uppercase(), 'Α');
-    assert_eq!('ς'.to_uppercase(), 'Σ');
+    fn upper(c: char) -> char {
+        let mut it = c.to_uppercase();
+        let c = it.next().unwrap();
+        assert!(it.next().is_none());
+        c
+    }
+    assert_eq!(upper('a'), 'A');
+    assert_eq!(upper('ö'), 'Ö');
+    assert_eq!(upper('ß'), 'ß'); // not ẞ: Latin capital letter sharp s
+    assert_eq!(upper('ü'), 'Ü');
+    assert_eq!(upper('💩'), '💩');
+
+    assert_eq!(upper('σ'), 'Σ');
+    assert_eq!(upper('τ'), 'Τ');
+    assert_eq!(upper('ι'), 'Ι');
+    assert_eq!(upper('γ'), 'Γ');
+    assert_eq!(upper('μ'), 'Μ');
+    assert_eq!(upper('α'), 'Α');
+    assert_eq!(upper('ς'), 'Σ');
 }
 
 #[test]
@@ -165,7 +177,7 @@ fn string(c: char) -> String { c.escape_unicode().collect() }
 #[test]
 fn test_encode_utf8() {
     fn check(input: char, expect: &[u8]) {
-        let mut buf = [0u8; 4];
+        let mut buf = [0; 4];
         let n = input.encode_utf8(&mut buf).unwrap_or(0);
         assert_eq!(&buf[..n], expect);
     }
@@ -179,7 +191,7 @@ fn check(input: char, expect: &[u8]) {
 #[test]
 fn test_encode_utf16() {
     fn check(input: char, expect: &[u16]) {
-        let mut buf = [0u16; 2];
+        let mut buf = [0; 2];
         let n = input.encode_utf16(&mut buf).unwrap_or(0);
         assert_eq!(&buf[..n], expect);
     }
index 55fcb8498513c5a804cff7d0cbf3976e0b639171..2a48395271db3804ccb20a0b0c6be55bc67e72f4 100644 (file)
@@ -30,7 +30,7 @@ fn test_success() {
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 fn test_fail() {
     let mut i = 0;
     try_finally(
index bc3995439a0173c782f158f56daa1c835dd3b7ac..7db8db444ff20901b67040498155a4c2196a90a3 100644 (file)
@@ -161,7 +161,7 @@ fn test_format_radix() {
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 fn test_radix_base_too_large() {
     let _ = radix(55, 37);
 }
index 9b6af182f729c291751d2db896acfbc4e5c74200..5c11f0196aeb8d7cdf377fe5d44fb573ac5f642d 100644 (file)
@@ -62,9 +62,10 @@ fn hash<T: Hash>(t: &T) -> u64 {
     // FIXME (#18283) Enable test
     //let s: Box<str> = box "a";
     //assert_eq!(hasher.hash(& s), 97 + 0xFF);
-    let cs: &[u8] = &[1u8, 2u8, 3u8];
+    let cs: &[u8] = &[1, 2, 3];
     assert_eq!(hash(& cs), 9);
-    let cs: Box<[u8]> = box [1u8, 2u8, 3u8];
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let cs: Box<[u8]> = Box::new([1, 2, 3]);
     assert_eq!(hash(& cs), 9);
 
     // FIXME (#18248) Add tests for hashing Rc<str> and Rc<[T]>
@@ -85,7 +86,7 @@ struct CustomHasher { output: u64 }
 
 impl Hasher for CustomHasher {
     fn finish(&self) -> u64 { self.output }
-    fn write(&mut self, data: &[u8]) { panic!() }
+    fn write(&mut self, _: &[u8]) { panic!() }
     fn write_u64(&mut self, data: u64) { self.output = data; }
 }
 
index 248cad32ef4d24c7af645dc16543d783bf9cf682..8289d06d04c61b2541ac73b79e6063e8d50881c7 100644 (file)
@@ -100,8 +100,8 @@ fn test_siphash() {
         [ 0x72, 0x45, 0x06, 0xeb, 0x4c, 0x32, 0x8a, 0x95, ]
     ];
 
-    let k0 = 0x_07_06_05_04_03_02_01_00_u64;
-    let k1 = 0x_0f_0e_0d_0c_0b_0a_09_08_u64;
+    let k0 = 0x_07_06_05_04_03_02_01_00;
+    let k1 = 0x_0f_0e_0d_0c_0b_0a_09_08;
     let mut buf = Vec::new();
     let mut t = 0;
     let mut state_inc = SipState::new_with_keys(k0, k1);
@@ -230,8 +230,8 @@ fn test_hash_no_concat_alias() {
     assert!(s != t && t != u);
     assert!(hash(&s) != hash(&t) && hash(&s) != hash(&u));
 
-    let v: (&[u8], &[u8], &[u8]) = (&[1u8], &[0u8, 0], &[0u8]);
-    let w: (&[u8], &[u8], &[u8]) = (&[1u8, 0, 0, 0], &[], &[]);
+    let v: (&[u8], &[u8], &[u8]) = (&[1], &[0, 0], &[0]);
+    let w: (&[u8], &[u8], &[u8]) = (&[1, 0, 0, 0], &[], &[]);
 
     assert!(v != w);
     assert!(hash(&v) != hash(&w));
index abf88583c03ffac03f1a6a40a0c9c51a86e20060..0f4e7fcdda57bdb3469316492c823aa141acbdd9 100644 (file)
@@ -404,7 +404,8 @@ fn test_collect() {
 
 #[test]
 fn test_all() {
-    let v: Box<[int]> = box [1, 2, 3, 4, 5];
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let v: Box<[int]> = Box::new([1, 2, 3, 4, 5]);
     assert!(v.iter().all(|&x| x < 10));
     assert!(!v.iter().all(|&x| x % 2 == 0));
     assert!(!v.iter().all(|&x| x > 100));
@@ -413,7 +414,8 @@ fn test_all() {
 
 #[test]
 fn test_any() {
-    let v: Box<[int]> = box [1, 2, 3, 4, 5];
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let v: Box<[int]> = Box::new([1, 2, 3, 4, 5]);
     assert!(v.iter().any(|&x| x < 10));
     assert!(v.iter().any(|&x| x % 2 == 0));
     assert!(!v.iter().any(|&x| x > 100));
@@ -579,10 +581,11 @@ fn test_rposition() {
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 fn test_rposition_panic() {
-    let v = [(box 0, box 0), (box 0, box 0),
-             (box 0, box 0), (box 0, box 0)];
+    let v: [(Box<_>, Box<_>); 4] =
+        [(box 0, box 0), (box 0, box 0),
+         (box 0, box 0), (box 0, box 0)];
     let mut i = 0;
     v.iter().rposition(|_elt| {
         if i == 2 {
@@ -775,9 +778,9 @@ fn test_range_step() {
     assert_eq!(range_step(0, 20, 5).collect::<Vec<int>>(), [0, 5, 10, 15]);
     assert_eq!(range_step(20, 0, -5).collect::<Vec<int>>(), [20, 15, 10, 5]);
     assert_eq!(range_step(20, 0, -6).collect::<Vec<int>>(), [20, 14, 8, 2]);
-    assert_eq!(range_step(200u8, 255, 50).collect::<Vec<u8>>(), [200u8, 250]);
-    assert_eq!(range_step(200i, -5, 1).collect::<Vec<int>>(), []);
-    assert_eq!(range_step(200i, 200, 1).collect::<Vec<int>>(), []);
+    assert_eq!(range_step(200, 255, 50).collect::<Vec<u8>>(), [200, 250]);
+    assert_eq!(range_step(200, -5, 1).collect::<Vec<int>>(), []);
+    assert_eq!(range_step(200, 200, 1).collect::<Vec<int>>(), []);
 }
 
 #[test]
@@ -785,7 +788,7 @@ fn test_range_step_inclusive() {
     assert_eq!(range_step_inclusive(0, 20, 5).collect::<Vec<int>>(), [0, 5, 10, 15, 20]);
     assert_eq!(range_step_inclusive(20, 0, -5).collect::<Vec<int>>(), [20, 15, 10, 5, 0]);
     assert_eq!(range_step_inclusive(20, 0, -6).collect::<Vec<int>>(), [20, 14, 8, 2]);
-    assert_eq!(range_step_inclusive(200u8, 255, 50).collect::<Vec<u8>>(), [200u8, 250]);
+    assert_eq!(range_step_inclusive(200, 255, 50).collect::<Vec<u8>>(), [200, 250]);
     assert_eq!(range_step_inclusive(200, -5, 1).collect::<Vec<int>>(), []);
     assert_eq!(range_step_inclusive(200, 200, 1).collect::<Vec<int>>(), [200]);
 }
index 03924910e0485d12acf5f4c86798842dacac6fe6..1dbbb845d46e0f87fad11e82cc358fe255eb9a2e 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![feature(box_syntax)]
 #![feature(int_uint)]
 #![feature(unboxed_closures)]
index 73000670c61aa839e975fb39829b45eb39be2789..bf3e1cf03cbddfb516fe2137b43d44e63d9b89a6 100644 (file)
@@ -103,7 +103,7 @@ impl Foo for int {}
     }
 
     unsafe {
-        assert_eq!([76u8], transmute::<_, Vec<u8>>("L".to_string()));
+        assert_eq!([76], transmute::<_, Vec<u8>>("L".to_string()));
     }
 }
 
index d1bfb475b074b41d2a38faebbccf16cffaf3ab09..fa41167cae8a6dda7742850facc156fa30f3e26d 100644 (file)
@@ -70,12 +70,12 @@ fn test_bitwise_operators() {
         assert!(-(0b11 as $T) - (1 as $T) == (0b11 as $T).not());
     }
 
-    static A: $T = 0b0101100;
-    static B: $T = 0b0100001;
-    static C: $T = 0b1111001;
+    const A: $T = 0b0101100;
+    const B: $T = 0b0100001;
+    const C: $T = 0b1111001;
 
-    static _0: $T = 0;
-    static _1: $T = !0;
+    const _0: $T = 0;
+    const _1: $T = !0;
 
     #[test]
     fn test_count_ones() {
index 1cd1989c11dc3e5088cf210b06ff74965677d0e0..9087b87f640cb77519b19df956e97e8f0cc285ea 100644 (file)
@@ -88,35 +88,35 @@ fn test_from_str_radix_float() {
 
     #[test]
     fn test_int_from_str_overflow() {
-        let mut i8_val: i8 = 127_i8;
+        let mut i8_val: i8 = 127;
         assert_eq!("127".parse::<i8>().ok(), Some(i8_val));
         assert_eq!("128".parse::<i8>().ok(), None);
 
-        i8_val += 1 as i8;
+        i8_val = i8_val.wrapping_add(1);
         assert_eq!("-128".parse::<i8>().ok(), Some(i8_val));
         assert_eq!("-129".parse::<i8>().ok(), None);
 
-        let mut i16_val: i16 = 32_767_i16;
+        let mut i16_val: i16 = 32_767;
         assert_eq!("32767".parse::<i16>().ok(), Some(i16_val));
         assert_eq!("32768".parse::<i16>().ok(), None);
 
-        i16_val += 1 as i16;
+        i16_val = i16_val.wrapping_add(1);
         assert_eq!("-32768".parse::<i16>().ok(), Some(i16_val));
         assert_eq!("-32769".parse::<i16>().ok(), None);
 
-        let mut i32_val: i32 = 2_147_483_647_i32;
+        let mut i32_val: i32 = 2_147_483_647;
         assert_eq!("2147483647".parse::<i32>().ok(), Some(i32_val));
         assert_eq!("2147483648".parse::<i32>().ok(), None);
 
-        i32_val += 1 as i32;
+        i32_val = i32_val.wrapping_add(1);
         assert_eq!("-2147483648".parse::<i32>().ok(), Some(i32_val));
         assert_eq!("-2147483649".parse::<i32>().ok(), None);
 
-        let mut i64_val: i64 = 9_223_372_036_854_775_807_i64;
+        let mut i64_val: i64 = 9_223_372_036_854_775_807;
         assert_eq!("9223372036854775807".parse::<i64>().ok(), Some(i64_val));
         assert_eq!("9223372036854775808".parse::<i64>().ok(), None);
 
-        i64_val += 1 as i64;
+        i64_val = i64_val.wrapping_add(1);
         assert_eq!("-9223372036854775808".parse::<i64>().ok(), Some(i64_val));
         assert_eq!("-9223372036854775809".parse::<i64>().ok(), None);
     }
index 5c6efc857f1f98fb5d6433543bc0f54124b90994..39e41a4fad3b7d5092c834aa43c69a443b1018b7 100644 (file)
@@ -38,12 +38,12 @@ fn test_bitwise_operators() {
         assert!(MAX - (0b1011 as $T) == (0b1011 as $T).not());
     }
 
-    static A: $T = 0b0101100;
-    static B: $T = 0b0100001;
-    static C: $T = 0b1111001;
+    const A: $T = 0b0101100;
+    const B: $T = 0b0100001;
+    const C: $T = 0b1111001;
 
-    static _0: $T = 0;
-    static _1: $T = !0;
+    const _0: $T = 0;
+    const _1: $T = !0;
 
     #[test]
     fn test_count_ones() {
index 860bd40e21eeed7dcda76a520887bd87e4e14818..fe0b10e91192bce5c1b62e288d0b0c9df9ffc748 100644 (file)
@@ -16,7 +16,7 @@
 #[test]
 fn test_get_ptr() {
     unsafe {
-        let x = box 0;
+        let x: Box<_> = box 0;
         let addr_x: *const int = mem::transmute(&*x);
         let opt = Some(x);
         let y = opt.unwrap();
@@ -80,7 +80,7 @@ fn test_option_dance() {
     assert!(y.is_none());
 }
 
-#[test] #[should_fail]
+#[test] #[should_panic]
 fn test_option_too_much_dance() {
     let mut y = Some(marker::NoCopy);
     let _y2 = y.take().unwrap();
@@ -139,14 +139,14 @@ fn test_unwrap() {
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 fn test_unwrap_panic1() {
     let x: Option<int> = None;
     x.unwrap();
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 fn test_unwrap_panic2() {
     let x: Option<String> = None;
     x.unwrap();
index c8a54ef59abda2c0676e72bd196db6090ae220c8..6a25c8be14e5a97e8fde1cc2719180260a405fc6 100644 (file)
@@ -139,12 +139,12 @@ fn test_ptr_addition() {
 fn test_ptr_subtraction() {
     unsafe {
         let xs = vec![0,1,2,3,4,5,6,7,8,9];
-        let mut idx = 9i8;
+        let mut idx = 9;
         let ptr = xs.as_ptr();
 
-        while idx >= 0i8 {
+        while idx >= 0 {
             assert_eq!(*(ptr.offset(idx as int)), idx as int);
-            idx = idx - 1i8;
+            idx = idx - 1;
         }
 
         let mut xs_mut = xs;
index 10cc3ad64242720e59c2d5e9682a09d8f6aab45d..1c175ba99f7739619bd7c7b90148666d27c41052 100644 (file)
@@ -126,7 +126,7 @@ fn handler(msg: &'static str) -> int {
 }
 
 #[test]
-#[should_fail]
+#[should_panic]
 pub fn test_unwrap_or_else_panic() {
     fn handler(msg: &'static str) -> int {
         if msg == "I got this." {
index 019f935911f7a78315f834be60b88c8928835c13..a89d3380707051cbdf8613a9484464f82699d133 100644 (file)
@@ -188,15 +188,13 @@ fn trim_ws() {
 
 mod pattern {
     use std::str::Pattern;
-    use std::str::{Searcher, ReverseSearcher, DoubleEndedSearcher};
+    use std::str::{Searcher, ReverseSearcher};
     use std::str::SearchStep::{self, Match, Reject, Done};
 
     macro_rules! make_test {
         ($name:ident, $p:expr, $h:expr, [$($e:expr,)*]) => {
             mod $name {
-                use std::str::Pattern;
-                use std::str::{Searcher, ReverseSearcher, DoubleEndedSearcher};
-                use std::str::SearchStep::{self, Match, Reject, Done};
+                use std::str::SearchStep::{Match, Reject};
                 use super::{cmp_search_to_vec};
                 #[test]
                 fn fwd() {
index 2ce52cdec2560a92ee1e32559e2ae4392b73e37e..a5cfe908aa86e88a4220433ff8c2076327af0ce0 100644 (file)
@@ -14,6 +14,8 @@
 //! [def]: https://en.wikipedia.org/wiki/DEFLATE
 //! [mz]: https://code.google.com/p/miniz/
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "flate"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
@@ -73,9 +75,9 @@ fn tinfl_decompress_mem_to_heap(psrc_buf: *const c_void,
                                     -> *mut c_void;
 }
 
-static LZ_NORM : c_int = 0x80;  // LZ with 128 probes, "normal"
-static TINFL_FLAG_PARSE_ZLIB_HEADER : c_int = 0x1; // parse zlib header and adler32 checksum
-static TDEFL_WRITE_ZLIB_HEADER : c_int = 0x01000; // write zlib header and adler32 checksum
+const LZ_NORM: c_int = 0x80;  // LZ with 128 probes, "normal"
+const TINFL_FLAG_PARSE_ZLIB_HEADER: c_int = 0x1; // parse zlib header and adler32 checksum
+const TDEFL_WRITE_ZLIB_HEADER: c_int = 0x01000; // write zlib header and adler32 checksum
 
 fn deflate_bytes_internal(bytes: &[u8], flags: c_int) -> Option<Bytes> {
     unsafe {
index 4e25e51e9a466075c58b49ae0207413b88a8b426..9b220409ef59789b162b2ce380ade3d05624e39b 100644 (file)
@@ -14,6 +14,8 @@
 //! Parsing does not happen at runtime: structures of `std::fmt::rt` are
 //! generated instead.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "fmt_macros"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
index 6240b0e6afdd50861f59ced7b8a752cd8dd626b9..38abf3881bdf63aaac1c47e870c1d44e6bd5996b 100644 (file)
@@ -46,7 +46,7 @@
 //!
 //! fn print_usage(program: &str, opts: &[OptGroup]) {
 //!     let brief = format!("Usage: {} [options]", program);
-//!     print!("{}", usage(brief.as_slice(), opts));
+//!     print!("{}", usage(brief, opts));
 //! }
 //!
 //! fn main() {
 //!         Err(f) => { panic!(f.to_string()) }
 //!     };
 //!     if matches.opt_present("h") {
-//!         print_usage(program.as_slice(), opts);
+//!         print_usage(program, opts);
 //!         return;
 //!     }
 //!     let output = matches.opt_str("o");
 //!     let input = if !matches.free.is_empty() {
 //!         matches.free[0].clone()
 //!     } else {
-//!         print_usage(program.as_slice(), opts);
+//!         print_usage(program, opts);
 //!         return;
 //!     };
-//!     do_work(input.as_slice(), output);
+//!     do_work(input, output);
 //! }
 //! ```
 
+
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "getopts"]
 #![unstable(feature = "rustc_private",
             reason = "use the crates.io `getopts` library instead")]
@@ -92,6 +95,7 @@
 #![feature(collections)]
 #![feature(int_uint)]
 #![feature(staged_api)]
+#![feature(core)]
 #![feature(str_words)]
 #![cfg_attr(test, feature(rustc_private))]
 
index 09fbf4935e4c1e7a86ade0c5bdb543854bb313a8..5f6bfd196f031304caa18a06c52aad0dfe8ac8c8 100644 (file)
@@ -37,7 +37,7 @@
 //! Each node label is derived directly from the int representing the node,
 //! while the edge labels are all empty strings.
 //!
-//! This example also illustrates how to use `CowVec` to return
+//! This example also illustrates how to use `Cow<[T]>` to return
 //! an owned vector or a borrowed slice as appropriate: we construct the
 //! node vector from scratch, but borrow the edge list (rather than
 //! constructing a copy of all the edges from scratch).
 //!
 //! * [DOT language](http://www.graphviz.org/doc/info/lang.html)
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "graphviz"]
 #![unstable(feature = "rustc_private")]
 #![feature(staged_api)]
@@ -502,7 +504,7 @@ pub fn suffix_line(self, suffix: LabelText) -> LabelText<'static> {
 /// that is bound by the self lifetime `'a`.
 ///
 /// The `nodes` and `edges` method each return instantiations of
-/// `CowVec` to leave implementers the freedom to create
+/// `Cow<[T]>` to leave implementers the freedom to create
 /// entirely new vectors or to pass back slices into internally owned
 /// vectors.
 pub trait GraphWalk<'a, N, E> {
index 42143b06ca0e391678583b6e9cfced390ffa897c..11aba40afad73b9a2481533ceef5e4107ab45433 100644 (file)
@@ -8,15 +8,14 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "libc"]
 #![crate_type = "rlib"]
-#![cfg_attr(not(feature = "cargo-build"),
-            unstable(feature = "libc"))]
-#![cfg_attr(not(feature = "cargo-build"), feature(staged_api))]
+#![cfg_attr(not(feature = "cargo-build"), unstable(feature = "libc"))]
+#![cfg_attr(not(feature = "cargo-build"), feature(staged_api, core, no_std))]
 #![cfg_attr(not(feature = "cargo-build"), staged_api)]
-#![cfg_attr(not(feature = "cargo-build"), feature(core))]
-#![feature(no_std)]
-#![no_std]
+#![cfg_attr(not(feature = "cargo-build"), no_std)]
 #![doc(html_logo_url = "http://www.rust-lang.org/logos/rust-logo-128x128-blk-v2.png",
        html_favicon_url = "http://www.rust-lang.org/favicon.ico",
        html_root_url = "http://doc.rust-lang.org/nightly/",
@@ -386,7 +385,8 @@ pub mod c99 {
                       target_arch = "mips",
                       target_arch = "mipsel",
                       target_arch = "powerpc",
-                      target_arch = "le32"))]
+                      target_arch = "le32",
+                      all(target_arch = "arm", not(target_os = "android"))))]
             pub mod posix88 {
                 pub type off_t = i32;
                 pub type dev_t = u64;
@@ -398,7 +398,7 @@ pub mod posix88 {
                 pub type mode_t = u32;
                 pub type ssize_t = i32;
             }
-            #[cfg(target_arch = "arm")]
+            #[cfg(all(target_arch = "arm", target_os = "android"))]
             pub mod posix88 {
                 pub type off_t = i32;
                 pub type dev_t = u32;
@@ -412,7 +412,8 @@ pub mod posix88 {
             }
             #[cfg(any(target_arch = "x86",
                       target_arch = "le32",
-                      target_arch = "powerpc"))]
+                      target_arch = "powerpc",
+                      all(target_arch = "arm", not(target_os = "android"))))]
             pub mod posix01 {
                 use types::os::arch::c95::{c_short, c_long, time_t};
                 use types::os::arch::posix88::{dev_t, gid_t, ino_t};
@@ -458,7 +459,7 @@ pub mod posix01 {
                     pub __size: [u32; 9]
                 }
             }
-            #[cfg(target_arch = "arm")]
+            #[cfg(all(target_arch = "arm", target_os = "android"))]
             pub mod posix01 {
                 use types::os::arch::c95::{c_uchar, c_uint, c_ulong, time_t};
                 use types::os::arch::c99::{c_longlong, c_ulonglong};
@@ -2203,11 +2204,11 @@ pub mod c95 {
             pub const _IOFBF : c_int = 0;
             pub const _IONBF : c_int = 4;
             pub const _IOLBF : c_int = 64;
-            pub const BUFSIZ : c_uint = 512_u32;
-            pub const FOPEN_MAX : c_uint = 20_u32;
-            pub const FILENAME_MAX : c_uint = 260_u32;
-            pub const L_tmpnam : c_uint = 16_u32;
-            pub const TMP_MAX : c_uint = 32767_u32;
+            pub const BUFSIZ : c_uint = 512;
+            pub const FOPEN_MAX : c_uint = 20;
+            pub const FILENAME_MAX : c_uint = 260;
+            pub const L_tmpnam : c_uint = 16;
+            pub const TMP_MAX : c_uint = 32767;
 
             pub const WSAEINTR: c_int = 10004;
             pub const WSAEBADF: c_int = 10009;
@@ -2584,11 +2585,11 @@ pub mod c95 {
             pub const _IOFBF : c_int = 0;
             pub const _IONBF : c_int = 2;
             pub const _IOLBF : c_int = 1;
-            pub const BUFSIZ : c_uint = 8192_u32;
-            pub const FOPEN_MAX : c_uint = 16_u32;
-            pub const FILENAME_MAX : c_uint = 4096_u32;
-            pub const L_tmpnam : c_uint = 20_u32;
-            pub const TMP_MAX : c_uint = 238328_u32;
+            pub const BUFSIZ : c_uint = 8192;
+            pub const FOPEN_MAX : c_uint = 16;
+            pub const FILENAME_MAX : c_uint = 4096;
+            pub const L_tmpnam : c_uint = 20;
+            pub const TMP_MAX : c_uint = 238328;
         }
         pub mod c99 {
         }
@@ -3450,11 +3451,11 @@ pub mod c95 {
             pub const _IOFBF : c_int = 0;
             pub const _IONBF : c_int = 2;
             pub const _IOLBF : c_int = 1;
-            pub const BUFSIZ : c_uint = 1024_u32;
-            pub const FOPEN_MAX : c_uint = 20_u32;
-            pub const FILENAME_MAX : c_uint = 1024_u32;
-            pub const L_tmpnam : c_uint = 1024_u32;
-            pub const TMP_MAX : c_uint = 308915776_u32;
+            pub const BUFSIZ : c_uint = 1024;
+            pub const FOPEN_MAX : c_uint = 20;
+            pub const FILENAME_MAX : c_uint = 1024;
+            pub const L_tmpnam : c_uint = 1024;
+            pub const TMP_MAX : c_uint = 308915776;
         }
         pub mod c99 {
         }
@@ -3858,11 +3859,11 @@ pub mod c95 {
             pub const _IOFBF : c_int = 0;
             pub const _IONBF : c_int = 2;
             pub const _IOLBF : c_int = 1;
-            pub const BUFSIZ : c_uint = 1024_u32;
-            pub const FOPEN_MAX : c_uint = 20_u32;
-            pub const FILENAME_MAX : c_uint = 1024_u32;
-            pub const L_tmpnam : c_uint = 1024_u32;
-            pub const TMP_MAX : c_uint = 308915776_u32;
+            pub const BUFSIZ : c_uint = 1024;
+            pub const FOPEN_MAX : c_uint = 20;
+            pub const FILENAME_MAX : c_uint = 1024;
+            pub const L_tmpnam : c_uint = 1024;
+            pub const TMP_MAX : c_uint = 308915776;
         }
         pub mod c99 {
         }
@@ -4236,11 +4237,11 @@ pub mod c95 {
             pub const _IOFBF : c_int = 0;
             pub const _IONBF : c_int = 2;
             pub const _IOLBF : c_int = 1;
-            pub const BUFSIZ : c_uint = 1024_u32;
-            pub const FOPEN_MAX : c_uint = 20_u32;
-            pub const FILENAME_MAX : c_uint = 1024_u32;
-            pub const L_tmpnam : c_uint = 1024_u32;
-            pub const TMP_MAX : c_uint = 308915776_u32;
+            pub const BUFSIZ : c_uint = 1024;
+            pub const FOPEN_MAX : c_uint = 20;
+            pub const FILENAME_MAX : c_uint = 1024;
+            pub const L_tmpnam : c_uint = 1024;
+            pub const TMP_MAX : c_uint = 308915776;
         }
         pub mod c99 {
         }
@@ -5002,9 +5003,36 @@ pub mod fcntl {
             use types::os::arch::c95::{c_char, c_int};
             use types::os::arch::posix88::mode_t;
 
+            mod open_shim {
+                extern {
+                    #[cfg(any(target_os = "macos",
+                              target_os = "ios"))]
+                    pub fn open(path: *const ::c_char, oflag: ::c_int, ...)
+                                -> ::c_int;
+
+                    #[cfg(not(any(target_os = "macos",
+                                  target_os = "ios")))]
+                    pub fn open(path: *const ::c_char, oflag: ::c_int, mode: ::mode_t)
+                                -> ::c_int;
+                }
+            }
+
+            #[cfg(any(target_os = "macos",
+                      target_os = "ios"))]
+            #[inline]
+            pub unsafe extern fn open(path: *const c_char, oflag: c_int, mode: mode_t) -> c_int {
+                use types::os::arch::c95::c_uint;
+                open_shim::open(path, oflag, mode as c_uint)
+            }
+
+            #[cfg(not(any(target_os = "macos",
+                          target_os = "ios")))]
+            #[inline]
+            pub unsafe extern fn open(path: *const c_char, oflag: c_int, mode: mode_t) -> c_int {
+                open_shim::open(path, oflag, mode)
+            }
+
             extern {
-                pub fn open(path: *const c_char, oflag: c_int, mode: mode_t)
-                            -> c_int;
                 pub fn creat(path: *const c_char, mode: mode_t) -> c_int;
                 pub fn fcntl(fd: c_int, cmd: c_int, ...) -> c_int;
             }
index d0105bb65776eb6d216ba43580b2f768bbd41976..3b6e1d0469148eaf404aed34b26e1c7b8dc793c7 100644 (file)
 //! they're turned off (just a load and an integer comparison). This also means that
 //! if logging is disabled, none of the components of the log will be executed.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "log"]
 #![unstable(feature = "rustc_private",
             reason = "use the crates.io `log` library instead")]
index 4a9a9bd40600b73d736244b022a68a46cab331fb..f0f861a3831a126efe176495d163f55d486b6cb1 100644 (file)
@@ -157,7 +157,7 @@ macro_rules! info {
 /// ```
 #[macro_export]
 macro_rules! debug {
-    ($($arg:tt)*) => (if cfg!(not(ndebug)) { log!(::log::DEBUG, $($arg)*) })
+    ($($arg:tt)*) => (if cfg!(debug_assertions) { log!(::log::DEBUG, $($arg)*) })
 }
 
 /// A macro to test whether a log level is enabled for the current module.
@@ -192,7 +192,7 @@ macro_rules! debug {
 macro_rules! log_enabled {
     ($lvl:expr) => ({
         let lvl = $lvl;
-        (lvl != ::log::DEBUG || cfg!(not(ndebug))) &&
+        (lvl != ::log::DEBUG || cfg!(debug_assertions)) &&
         lvl <= ::log::log_level() &&
         ::log::mod_enabled(lvl, module_path!())
     })
index 2673649f3440cc9170cff3d79e4d0cd556d418b8..d54f183707475632089a14cd933c6ed2fa69a563 100644 (file)
@@ -12,6 +12,7 @@
 
 use core::prelude::*;
 use core::num::Int;
+use core::num::wrapping::WrappingOps;
 use {Rng, SeedableRng, Rand};
 
 const KEY_WORDS    : uint =  8; // 8 words for the 256-bit key
@@ -43,10 +44,10 @@ pub struct ChaChaRng {
 
 macro_rules! quarter_round{
     ($a: expr, $b: expr, $c: expr, $d: expr) => {{
-        $a += $b; $d ^= $a; $d = $d.rotate_left(16);
-        $c += $d; $b ^= $c; $b = $b.rotate_left(12);
-        $a += $b; $d ^= $a; $d = $d.rotate_left( 8);
-        $c += $d; $b ^= $c; $b = $b.rotate_left( 7);
+        $a = $a.wrapping_add($b); $d = $d ^ $a; $d = $d.rotate_left(16);
+        $c = $c.wrapping_add($d); $b = $b ^ $c; $b = $b.rotate_left(12);
+        $a = $a.wrapping_add($b); $d = $d ^ $a; $d = $d.rotate_left( 8);
+        $c = $c.wrapping_add($d); $b = $b ^ $c; $b = $b.rotate_left( 7);
     }}
 }
 
@@ -74,7 +75,7 @@ macro_rules! double_round{
     }
 
     for i in 0..STATE_WORDS {
-        output[i] += input[i];
+        output[i] = output[i].wrapping_add(input[i]);
     }
 }
 
@@ -172,7 +173,7 @@ impl<'a> SeedableRng<&'a [u32]> for ChaChaRng {
 
     fn reseed(&mut self, seed: &'a [u32]) {
         // reset state
-        self.init(&[0u32; KEY_WORDS]);
+        self.init(&[0; KEY_WORDS]);
         // set key in place
         let key = &mut self.state[4 .. 4+KEY_WORDS];
         for (k, s) in key.iter_mut().zip(seed.iter()) {
@@ -244,7 +245,7 @@ fn test_rng_reseed() {
     fn test_rng_true_values() {
         // Test vectors 1 and 2 from
         // http://tools.ietf.org/html/draft-nir-cfrg-chacha20-poly1305-04
-        let seed : &[_] = &[0u32; 8];
+        let seed : &[_] = &[0; 8];
         let mut ra: ChaChaRng = SeedableRng::from_seed(seed);
 
         let v = (0..16).map(|_| ra.next_u32()).collect::<Vec<_>>();
@@ -284,7 +285,7 @@ fn test_rng_true_values() {
 
     #[test]
     fn test_rng_clone() {
-        let seed : &[_] = &[0u32; 8];
+        let seed : &[_] = &[0; 8];
         let mut rng: ChaChaRng = SeedableRng::from_seed(seed);
         let mut clone = rng.clone();
         for _ in 0..16 {
index e4927902cb3bb66184ad59f4c360818ee39491af..bf9d334e8a4734bf7814d31fdf5a30f49a458808 100644 (file)
@@ -109,12 +109,12 @@ fn test_exp() {
         }
     }
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_exp_invalid_lambda_zero() {
         Exp::new(0.0);
     }
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_exp_invalid_lambda_neg() {
         Exp::new(-10.0);
     }
index 38eba0cfc712f7221961113775972f80ad76cdc0..ae3724a2b431a1ca371465ced275fd5dfb13d88b 100644 (file)
@@ -356,7 +356,7 @@ fn test_chi_squared_large() {
         }
     }
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_chi_squared_invalid_dof() {
         ChiSquared::new(-1.0);
     }
index 5a85552dc384eb10536faa8520621827fe5416cd..9775507b3cd578b38abd7c1225da82d0b8162369 100644 (file)
@@ -223,7 +223,7 @@ fn ziggurat<R: Rng, P, Z>(
             mut pdf: P,
             mut zero_case: Z)
             -> f64 where P: FnMut(f64) -> f64, Z: FnMut(&mut R, f64) -> f64 {
-    static SCALE: f64 = (1u64 << 53) as f64;
+    const SCALE: f64 = (1u64 << 53) as f64;
     loop {
         // reimplement the f64 generation as an optimisation suggested
         // by the Doornik paper: we have a lot of precision-space
@@ -351,16 +351,16 @@ macro_rules! t {
            [50, 51, 52, 53, 54, 55, 56]);
     }
 
-    #[test] #[should_fail]
+    #[test] #[should_panic]
     fn test_weighted_choice_no_items() {
         WeightedChoice::<int>::new(&mut []);
     }
-    #[test] #[should_fail]
+    #[test] #[should_panic]
     fn test_weighted_choice_zero_weight() {
         WeightedChoice::new(&mut [Weighted { weight: 0, item: 0},
                                   Weighted { weight: 0, item: 1}]);
     }
-    #[test] #[should_fail]
+    #[test] #[should_panic]
     fn test_weighted_choice_weight_overflows() {
         let x = (-1) as uint / 2; // x + x + 2 is the overflow
         WeightedChoice::new(&mut [Weighted { weight: x, item: 0 },
index 83f202742d3f33da9dbdf016c32b1cbe541f93ce..ab5d03ad82557adfe8fbf28eca8dbd5d13df47e0 100644 (file)
@@ -175,7 +175,7 @@ fn test_normal() {
         }
     }
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_normal_invalid_sd() {
         Normal::new(10.0, -1.0);
     }
@@ -191,7 +191,7 @@ fn test_log_normal() {
         }
     }
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_log_normal_invalid_sd() {
         LogNormal::new(10.0, -1.0);
     }
index 6eb1d68a081aa9d48632a383bfe0315d7f994214..c5a260346e0adf17dc464bb62a57d4313d3e1e82 100644 (file)
@@ -14,6 +14,7 @@
 
 use core::prelude::{PartialOrd};
 use core::num::Int;
+use core::num::wrapping::WrappingOps;
 
 use Rng;
 use distributions::{Sample, IndependentSample};
@@ -22,8 +23,8 @@
 ///
 /// This gives a uniform distribution (assuming the RNG used to sample
 /// it is itself uniform & the `SampleRange` implementation for the
-/// given type is correct), even for edge cases like `low = 0u8`,
-/// `high = 170u8`, for which a naive modulo operation would return
+/// given type is correct), even for edge cases like `low = 0`,
+/// `high = 170`, for which a naive modulo operation would return
 /// numbers less than 85 with double the probability to those greater
 /// than 85.
 ///
@@ -97,7 +98,7 @@ impl SampleRange for $ty {
             // bijection.
 
             fn construct_range(low: $ty, high: $ty) -> Range<$ty> {
-                let range = high as $unsigned - low as $unsigned;
+                let range = (high as $unsigned).wrapping_sub(low as $unsigned);
                 let unsigned_max: $unsigned = Int::max_value();
 
                 // this is the largest number that fits into $unsigned
@@ -122,7 +123,7 @@ fn sample_range<R: Rng>(r: &Range<$ty>, rng: &mut R) -> $ty {
                     // be uniformly distributed)
                     if v < r.accept_zone as $unsigned {
                         // and return it, with some adjustments
-                        return r.low + (v % r.range as $unsigned) as $ty;
+                        return r.low.wrapping_add((v % r.range as $unsigned) as $ty);
                     }
                 }
             }
@@ -168,12 +169,12 @@ mod tests {
     use distributions::{Sample, IndependentSample};
     use super::Range as Range;
 
-    #[should_fail]
+    #[should_panic]
     #[test]
     fn test_range_bad_limits_equal() {
         Range::new(10, 10);
     }
-    #[should_fail]
+    #[should_panic]
     #[test]
     fn test_range_bad_limits_flipped() {
         Range::new(10, 5);
index 701749ff3443f6e0280ad1308001854ea645cfe2..7ea62b7fd3f413b62d35b1d365872e645d3cc4ee 100644 (file)
 
 //! The ISAAC random number generator.
 
+#![allow(non_camel_case_types)]
+
 use core::prelude::*;
 use core::slice;
 use core::iter::{range_step, repeat};
+use core::num::wrapping::Wrapping as w;
 
 use {Rng, SeedableRng, Rand};
 
-const RAND_SIZE_LEN: u32 = 8;
-const RAND_SIZE: u32 = 1 << (RAND_SIZE_LEN as uint);
-const RAND_SIZE_UINT: uint = 1 << (RAND_SIZE_LEN as uint);
+type w32 = w<u32>;
+type w64 = w<u64>;
+
+const RAND_SIZE_LEN: usize = 8;
+const RAND_SIZE: u32 = 1 << RAND_SIZE_LEN;
+const RAND_SIZE_USIZE: usize = 1 << RAND_SIZE_LEN;
 
 /// A random number generator that uses the ISAAC algorithm[1].
 ///
 #[derive(Copy)]
 pub struct IsaacRng {
     cnt: u32,
-    rsl: [u32; RAND_SIZE_UINT],
-    mem: [u32; RAND_SIZE_UINT],
-    a: u32,
-    b: u32,
-    c: u32
+    rsl: [w32; RAND_SIZE_USIZE],
+    mem: [w32; RAND_SIZE_USIZE],
+    a: w32,
+    b: w32,
+    c: w32,
 }
 
 static EMPTY: IsaacRng = IsaacRng {
     cnt: 0,
-    rsl: [0; RAND_SIZE_UINT],
-    mem: [0; RAND_SIZE_UINT],
-    a: 0, b: 0, c: 0
+    rsl: [w(0); RAND_SIZE_USIZE],
+    mem: [w(0); RAND_SIZE_USIZE],
+    a: w(0), b: w(0), c: w(0),
 };
 
 impl IsaacRng {
@@ -60,7 +66,7 @@ pub fn new_unseeded() -> IsaacRng {
     /// of `rsl` as a seed, otherwise construct one algorithmically (not
     /// randomly).
     fn init(&mut self, use_rsl: bool) {
-        let mut a = 0x9e3779b9;
+        let mut a = w(0x9e3779b9);
         let mut b = a;
         let mut c = a;
         let mut d = a;
@@ -71,14 +77,14 @@ fn init(&mut self, use_rsl: bool) {
 
         macro_rules! mix {
             () => {{
-                a^=b<<11; d+=a; b+=c;
-                b^=c>>2;  e+=b; c+=d;
-                c^=d<<8;  f+=c; d+=e;
-                d^=e>>16; g+=d; e+=f;
-                e^=f<<10; h+=e; f+=g;
-                f^=g>>4;  a+=f; g+=h;
-                g^=h<<8;  b+=g; h+=a;
-                h^=a>>9;  c+=h; a+=b;
+                a=a^(b<<11); d=d+a; b=b+c;
+                b=b^(c>>2);  e=e+b; c=c+d;
+                c=c^(d<<8);  f=f+c; d=d+e;
+                d=d^(e>>16); g=g+d; e=e+f;
+                e=e^(f<<10); h=h+e; f=f+g;
+                f=f^(g>>4);  a=a+f; g=g+h;
+                g=g^(h<<8);  b=b+g; h=h+a;
+                h=h^(a>>9);  c=c+h; a=a+b;
             }}
         }
 
@@ -89,11 +95,11 @@ macro_rules! mix {
         if use_rsl {
             macro_rules! memloop {
                 ($arr:expr) => {{
-                    for i in range_step(0, RAND_SIZE as uint, 8) {
-                        a+=$arr[i  ]; b+=$arr[i+1];
-                        c+=$arr[i+2]; d+=$arr[i+3];
-                        e+=$arr[i+4]; f+=$arr[i+5];
-                        g+=$arr[i+6]; h+=$arr[i+7];
+                    for i in range_step(0, RAND_SIZE_USIZE, 8) {
+                        a=a+$arr[i  ]; b=b+$arr[i+1];
+                        c=c+$arr[i+2]; d=d+$arr[i+3];
+                        e=e+$arr[i+4]; f=f+$arr[i+5];
+                        g=g+$arr[i+6]; h=h+$arr[i+7];
                         mix!();
                         self.mem[i  ]=a; self.mem[i+1]=b;
                         self.mem[i+2]=c; self.mem[i+3]=d;
@@ -106,7 +112,7 @@ macro_rules! memloop {
             memloop!(self.rsl);
             memloop!(self.mem);
         } else {
-            for i in range_step(0, RAND_SIZE as uint, 8) {
+            for i in range_step(0, RAND_SIZE_USIZE, 8) {
                 mix!();
                 self.mem[i  ]=a; self.mem[i+1]=b;
                 self.mem[i+2]=c; self.mem[i+3]=d;
@@ -122,31 +128,31 @@ macro_rules! memloop {
     #[inline]
     #[allow(unsigned_negation)]
     fn isaac(&mut self) {
-        self.c += 1;
+        self.c = self.c + w(1);
         // abbreviations
         let mut a = self.a;
         let mut b = self.b + self.c;
 
-        static MIDPOINT: uint = (RAND_SIZE / 2) as uint;
+        const MIDPOINT: usize = RAND_SIZE_USIZE / 2;
 
         macro_rules! ind {
-            ($x:expr) => ( self.mem[(($x >> 2) as uint & ((RAND_SIZE - 1) as uint))] )
+            ($x:expr) => ( self.mem[($x >> 2).0 as usize & (RAND_SIZE_USIZE - 1)] )
         }
 
         let r = [(0, MIDPOINT), (MIDPOINT, 0)];
-        for &(mr_offset, m2_offset) in &r {
+        for &(mr_offset, m2_offset) in r.iter() {
 
             macro_rules! rngstepp {
                 ($j:expr, $shift:expr) => {{
                     let base = $j;
-                    let mix = a << $shift as uint;
+                    let mix = a << $shift;
 
                     let x = self.mem[base  + mr_offset];
                     a = (a ^ mix) + self.mem[base + m2_offset];
                     let y = ind!(x) + a + b;
                     self.mem[base + mr_offset] = y;
 
-                    b = ind!(y >> RAND_SIZE_LEN as uint) + x;
+                    b = ind!(y >> RAND_SIZE_LEN) + x;
                     self.rsl[base + mr_offset] = b;
                 }}
             }
@@ -154,14 +160,14 @@ macro_rules! rngstepp {
             macro_rules! rngstepn {
                 ($j:expr, $shift:expr) => {{
                     let base = $j;
-                    let mix = a >> $shift as uint;
+                    let mix = a >> $shift;
 
                     let x = self.mem[base  + mr_offset];
                     a = (a ^ mix) + self.mem[base + m2_offset];
                     let y = ind!(x) + a + b;
                     self.mem[base + mr_offset] = y;
 
-                    b = ind!(y >> RAND_SIZE_LEN as uint) + x;
+                    b = ind!(y >> RAND_SIZE_LEN) + x;
                     self.rsl[base + mr_offset] = b;
                 }}
             }
@@ -207,7 +213,7 @@ fn next_u32(&mut self) -> u32 {
         // (the % is cheaply telling the optimiser that we're always
         // in bounds, without unsafe. NB. this is a power of two, so
         // it optimises to a bitwise mask).
-        self.rsl[(self.cnt % RAND_SIZE) as uint]
+        self.rsl[(self.cnt % RAND_SIZE) as usize].0
     }
 }
 
@@ -215,15 +221,15 @@ impl<'a> SeedableRng<&'a [u32]> for IsaacRng {
     fn reseed(&mut self, seed: &'a [u32]) {
         // make the seed into [seed[0], seed[1], ..., seed[seed.len()
         // - 1], 0, 0, ...], to fill rng.rsl.
-        let seed_iter = seed.iter().cloned().chain(repeat(0u32));
+        let seed_iter = seed.iter().cloned().chain(repeat(0));
 
         for (rsl_elem, seed_elem) in self.rsl.iter_mut().zip(seed_iter) {
-            *rsl_elem = seed_elem;
+            *rsl_elem = w(seed_elem);
         }
         self.cnt = 0;
-        self.a = 0;
-        self.b = 0;
-        self.c = 0;
+        self.a = w(0);
+        self.b = w(0);
+        self.c = w(0);
 
         self.init(true);
     }
@@ -246,21 +252,21 @@ fn rand<R: Rng>(other: &mut R) -> IsaacRng {
         unsafe {
             let ptr = ret.rsl.as_mut_ptr() as *mut u8;
 
-            let slice = slice::from_raw_parts_mut(ptr, (RAND_SIZE * 4) as uint);
+            let slice = slice::from_raw_parts_mut(ptr, RAND_SIZE_USIZE * 4);
             other.fill_bytes(slice);
         }
         ret.cnt = 0;
-        ret.a = 0;
-        ret.b = 0;
-        ret.c = 0;
+        ret.a = w(0);
+        ret.b = w(0);
+        ret.c = w(0);
 
         ret.init(true);
         return ret;
     }
 }
 
-const RAND_SIZE_64_LEN: uint = 8;
-const RAND_SIZE_64: uint = 1 << RAND_SIZE_64_LEN;
+const RAND_SIZE_64_LEN: usize = 8;
+const RAND_SIZE_64: usize = 1 << RAND_SIZE_64_LEN;
 
 /// A random number generator that uses ISAAC-64[1], the 64-bit
 /// variant of the ISAAC algorithm.
@@ -274,19 +280,19 @@ fn rand<R: Rng>(other: &mut R) -> IsaacRng {
 /// generator*](http://www.burtleburtle.net/bob/rand/isaacafa.html)
 #[derive(Copy)]
 pub struct Isaac64Rng {
-    cnt: uint,
-    rsl: [u64; RAND_SIZE_64],
-    mem: [u64; RAND_SIZE_64],
-    a: u64,
-    b: u64,
-    c: u64,
+    cnt: usize,
+    rsl: [w64; RAND_SIZE_64],
+    mem: [w64; RAND_SIZE_64],
+    a: w64,
+    b: w64,
+    c: w64,
 }
 
 static EMPTY_64: Isaac64Rng = Isaac64Rng {
     cnt: 0,
-    rsl: [0; RAND_SIZE_64],
-    mem: [0; RAND_SIZE_64],
-    a: 0, b: 0, c: 0,
+    rsl: [w(0); RAND_SIZE_64],
+    mem: [w(0); RAND_SIZE_64],
+    a: w(0), b: w(0), c: w(0),
 };
 
 impl Isaac64Rng {
@@ -304,7 +310,7 @@ pub fn new_unseeded() -> Isaac64Rng {
     fn init(&mut self, use_rsl: bool) {
         macro_rules! init {
             ($var:ident) => (
-                let mut $var = 0x9e3779b97f4a7c13;
+                let mut $var = w(0x9e3779b97f4a7c13);
             )
         }
         init!(a); init!(b); init!(c); init!(d);
@@ -312,14 +318,14 @@ macro_rules! init {
 
         macro_rules! mix {
             () => {{
-                a-=e; f^=h>>9;  h+=a;
-                b-=f; g^=a<<9;  a+=b;
-                c-=g; h^=b>>23; b+=c;
-                d-=h; a^=c<<15; c+=d;
-                e-=a; b^=d>>14; d+=e;
-                f-=b; c^=e<<20; e+=f;
-                g-=c; d^=f>>17; f+=g;
-                h-=d; e^=g<<14; g+=h;
+                a=a-e; f=f^(h>>9);  h=h+a;
+                b=b-f; g=g^(a<<9);  a=a+b;
+                c=c-g; h=h^(b>>23); b=b+c;
+                d=d-h; a=a^(c<<15); c=c+d;
+                e=e-a; b=b^(d>>14); d=d+e;
+                f=f-b; c=c^(e<<20); e=e+f;
+                g=g-c; d=d^(f>>17); f=f+g;
+                h=h-d; e=e^(g<<14); g=g+h;
             }}
         }
 
@@ -331,10 +337,10 @@ macro_rules! mix {
             macro_rules! memloop {
                 ($arr:expr) => {{
                     for i in (0..RAND_SIZE_64 / 8).map(|i| i * 8) {
-                        a+=$arr[i  ]; b+=$arr[i+1];
-                        c+=$arr[i+2]; d+=$arr[i+3];
-                        e+=$arr[i+4]; f+=$arr[i+5];
-                        g+=$arr[i+6]; h+=$arr[i+7];
+                        a=a+$arr[i  ]; b=b+$arr[i+1];
+                        c=c+$arr[i+2]; d=d+$arr[i+3];
+                        e=e+$arr[i+4]; f=f+$arr[i+5];
+                        g=g+$arr[i+6]; h=h+$arr[i+7];
                         mix!();
                         self.mem[i  ]=a; self.mem[i+1]=b;
                         self.mem[i+2]=c; self.mem[i+3]=d;
@@ -361,25 +367,25 @@ macro_rules! memloop {
 
     /// Refills the output buffer (`self.rsl`)
     fn isaac64(&mut self) {
-        self.c += 1;
+        self.c = self.c + w(1);
         // abbreviations
         let mut a = self.a;
         let mut b = self.b + self.c;
-        const MIDPOINT: uint =  RAND_SIZE_64 / 2;
-        const MP_VEC: [(uint, uint); 2] = [(0,MIDPOINT), (MIDPOINT, 0)];
+        const MIDPOINT: usize =  RAND_SIZE_64 / 2;
+        const MP_VEC: [(usize, usize); 2] = [(0,MIDPOINT), (MIDPOINT, 0)];
         macro_rules! ind {
             ($x:expr) => {
-                *self.mem.get_unchecked(($x as uint >> 3) & (RAND_SIZE_64 - 1))
+                *self.mem.get_unchecked((($x >> 3).0 as usize) & (RAND_SIZE_64 - 1))
             }
         }
 
-        for &(mr_offset, m2_offset) in &MP_VEC {
+        for &(mr_offset, m2_offset) in MP_VEC.iter() {
             for base in (0..MIDPOINT / 4).map(|i| i * 4) {
 
                 macro_rules! rngstepp {
                     ($j:expr, $shift:expr) => {{
                         let base = base + $j;
-                        let mix = a ^ (a << $shift as uint);
+                        let mix = a ^ (a << $shift);
                         let mix = if $j == 0 {!mix} else {mix};
 
                         unsafe {
@@ -397,7 +403,7 @@ macro_rules! rngstepp {
                 macro_rules! rngstepn {
                     ($j:expr, $shift:expr) => {{
                         let base = base + $j;
-                        let mix = a ^ (a >> $shift as uint);
+                        let mix = a ^ (a >> $shift);
                         let mix = if $j == 0 {!mix} else {mix};
 
                         unsafe {
@@ -450,7 +456,7 @@ fn next_u64(&mut self) -> u64 {
         // See corresponding location in IsaacRng.next_u32 for
         // explanation.
         debug_assert!(self.cnt < RAND_SIZE_64);
-        self.rsl[(self.cnt % RAND_SIZE_64) as uint]
+        self.rsl[(self.cnt % RAND_SIZE_64) as usize].0
     }
 }
 
@@ -458,15 +464,15 @@ impl<'a> SeedableRng<&'a [u64]> for Isaac64Rng {
     fn reseed(&mut self, seed: &'a [u64]) {
         // make the seed into [seed[0], seed[1], ..., seed[seed.len()
         // - 1], 0, 0, ...], to fill rng.rsl.
-        let seed_iter = seed.iter().cloned().chain(repeat(0u64));
+        let seed_iter = seed.iter().cloned().chain(repeat(0));
 
         for (rsl_elem, seed_elem) in self.rsl.iter_mut().zip(seed_iter) {
-            *rsl_elem = seed_elem;
+            *rsl_elem = w(seed_elem);
         }
         self.cnt = 0;
-        self.a = 0;
-        self.b = 0;
-        self.c = 0;
+        self.a = w(0);
+        self.b = w(0);
+        self.c = w(0);
 
         self.init(true);
     }
@@ -489,13 +495,13 @@ fn rand<R: Rng>(other: &mut R) -> Isaac64Rng {
         unsafe {
             let ptr = ret.rsl.as_mut_ptr() as *mut u8;
 
-            let slice = slice::from_raw_parts_mut(ptr, (RAND_SIZE_64 * 8) as uint);
+            let slice = slice::from_raw_parts_mut(ptr, RAND_SIZE_64 * 8);
             other.fill_bytes(slice);
         }
         ret.cnt = 0;
-        ret.a = 0;
-        ret.b = 0;
-        ret.c = 0;
+        ret.a = w(0);
+        ret.b = w(0);
+        ret.c = w(0);
 
         ret.init(true);
         return ret;
@@ -514,16 +520,16 @@ mod test {
     #[test]
     fn test_rng_32_rand_seeded() {
         let s = ::test::rng().gen_iter::<u32>().take(256).collect::<Vec<u32>>();
-        let mut ra: IsaacRng = SeedableRng::from_seed(&*s);
-        let mut rb: IsaacRng = SeedableRng::from_seed(&*s);
+        let mut ra: IsaacRng = SeedableRng::from_seed(&s[..]);
+        let mut rb: IsaacRng = SeedableRng::from_seed(&s[..]);
         assert!(order::equals(ra.gen_ascii_chars().take(100),
                               rb.gen_ascii_chars().take(100)));
     }
     #[test]
     fn test_rng_64_rand_seeded() {
         let s = ::test::rng().gen_iter::<u64>().take(256).collect::<Vec<u64>>();
-        let mut ra: Isaac64Rng = SeedableRng::from_seed(&*s);
-        let mut rb: Isaac64Rng = SeedableRng::from_seed(&*s);
+        let mut ra: Isaac64Rng = SeedableRng::from_seed(&s[..]);
+        let mut rb: Isaac64Rng = SeedableRng::from_seed(&s[..]);
         assert!(order::equals(ra.gen_ascii_chars().take(100),
                               rb.gen_ascii_chars().take(100)));
     }
@@ -548,7 +554,7 @@ fn test_rng_64_seeded() {
     #[test]
     fn test_rng_32_reseed() {
         let s = ::test::rng().gen_iter::<u32>().take(256).collect::<Vec<u32>>();
-        let mut r: IsaacRng = SeedableRng::from_seed(&*s);
+        let mut r: IsaacRng = SeedableRng::from_seed(&s[..]);
         let string1: String = r.gen_ascii_chars().take(100).collect();
 
         r.reseed(&s);
@@ -559,7 +565,7 @@ fn test_rng_32_reseed() {
     #[test]
     fn test_rng_64_reseed() {
         let s = ::test::rng().gen_iter::<u64>().take(256).collect::<Vec<u64>>();
-        let mut r: Isaac64Rng = SeedableRng::from_seed(&*s);
+        let mut r: Isaac64Rng = SeedableRng::from_seed(&s[..]);
         let string1: String = r.gen_ascii_chars().take(100).collect();
 
         r.reseed(&s);
index 583c658dfe0582f3b02847e71aab3d4770620237..6bc56ce9084b34591e24505f2beedabf22c587a1 100644 (file)
@@ -16,6 +16,8 @@
 //! is not recommended to use this library directly, but rather the official
 //! interface through `std::rand`.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rand"]
 #![crate_type = "rlib"]
 #![doc(html_logo_url = "http://www.rust-lang.org/logos/rust-logo-128x128-blk.png",
@@ -52,7 +54,7 @@
 use distributions::range::SampleRange;
 
 #[cfg(test)]
-static RAND_BENCH_N: u64 = 100;
+const RAND_BENCH_N: u64 = 100;
 
 pub mod distributions;
 pub mod isaac;
@@ -149,7 +151,7 @@ fn next_f64(&mut self) -> f64 {
     /// ```rust
     /// use std::rand::{thread_rng, Rng};
     ///
-    /// let mut v = [0u8; 13579];
+    /// let mut v = [0; 13579];
     /// thread_rng().fill_bytes(&mut v);
     /// println!("{:?}", v.as_slice());
     /// ```
@@ -342,7 +344,7 @@ impl<'a, R: Rng> Iterator for AsciiGenerator<'a, R> {
     type Item = char;
 
     fn next(&mut self) -> Option<char> {
-        static GEN_ASCII_STR_CHARSET: &'static [u8] =
+        const GEN_ASCII_STR_CHARSET: &'static [u8] =
             b"ABCDEFGHIJKLMNOPQRSTUVWXYZ\
               abcdefghijklmnopqrstuvwxyz\
               0123456789";
index 74d2c408060cbc2c595cd95678e4bbb409ad0468..e2a5276cc78abf8e8782dd8c7e597d58541b9b88 100644 (file)
@@ -141,7 +141,7 @@ impl Rand for char {
     #[inline]
     fn rand<R: Rng>(rng: &mut R) -> char {
         // a char is 21 bits
-        static CHAR_MASK: u32 = 0x001f_ffff;
+        const CHAR_MASK: u32 = 0x001f_ffff;
         loop {
             // Rejection sampling. About 0.2% of numbers with at most
             // 21-bits are invalid codepoints (surrogates), so this
@@ -214,7 +214,6 @@ fn rand<R: Rng>(rng: &mut R) -> Option<T> {
 
 #[cfg(test)]
 mod tests {
-    use std::prelude::v1::*;
     use std::rand::{Rng, thread_rng, Open01, Closed01};
 
     struct ConstantRng(u64);
index 06828911471466d2e1e3eb58786eb04567aacf1a..22b77a759319b8818421ed561e3ab67c41305172 100644 (file)
@@ -18,7 +18,7 @@
 
 /// How many bytes of entropy the underling RNG is allowed to generate
 /// before it is reseeded.
-static DEFAULT_GENERATION_THRESHOLD: uint = 32 * 1024;
+const DEFAULT_GENERATION_THRESHOLD: uint = 32 * 1024;
 
 /// A wrapper around any RNG which reseeds the underlying RNG after it
 /// has generated a certain number of random bytes.
@@ -212,10 +212,10 @@ fn test_rng_reseed() {
         assert_eq!(string1, string2);
     }
 
-    static FILL_BYTES_V_LEN: uint = 13579;
+    const FILL_BYTES_V_LEN: uint = 13579;
     #[test]
     fn test_rng_fill_bytes() {
-        let mut v = repeat(0u8).take(FILL_BYTES_V_LEN).collect::<Vec<_>>();
+        let mut v = repeat(0).take(FILL_BYTES_V_LEN).collect::<Vec<_>>();
         ::test::rng().fill_bytes(&mut v);
 
         // Sanity test: if we've gotten here, `fill_bytes` has not infinitely
index c52465a889907b57c4357f19d4a801677ab8b6c5..fc0a9d29ed6f2b7fcf8b7e132a7fe82c46b467d6 100644 (file)
@@ -13,7 +13,7 @@
 use std::slice;
 use std::iter::repeat;
 
-static BUF_CAPACITY: uint = 128;
+const BUF_CAPACITY: uint = 128;
 
 fn combine(seek: SeekStyle, cur: uint, end: uint, offset: i64) -> IoResult<u64> {
     // compute offset as signed and clamp to prevent overflow
@@ -140,32 +140,32 @@ mod tests {
     fn test_seekable_mem_writer() {
         let mut writer = SeekableMemWriter::new();
         assert_eq!(writer.tell(), Ok(0));
-        writer.write(&[0]).unwrap();
+        writer.write_all(&[0]).unwrap();
         assert_eq!(writer.tell(), Ok(1));
-        writer.write(&[1, 2, 3]).unwrap();
-        writer.write(&[4, 5, 6, 7]).unwrap();
+        writer.write_all(&[1, 2, 3]).unwrap();
+        writer.write_all(&[4, 5, 6, 7]).unwrap();
         assert_eq!(writer.tell(), Ok(8));
         let b: &[_] = &[0, 1, 2, 3, 4, 5, 6, 7];
         assert_eq!(writer.get_ref(), b);
 
         writer.seek(0, old_io::SeekSet).unwrap();
         assert_eq!(writer.tell(), Ok(0));
-        writer.write(&[3, 4]).unwrap();
+        writer.write_all(&[3, 4]).unwrap();
         let b: &[_] = &[3, 4, 2, 3, 4, 5, 6, 7];
         assert_eq!(writer.get_ref(), b);
 
         writer.seek(1, old_io::SeekCur).unwrap();
-        writer.write(&[0, 1]).unwrap();
+        writer.write_all(&[0, 1]).unwrap();
         let b: &[_] = &[3, 4, 2, 0, 1, 5, 6, 7];
         assert_eq!(writer.get_ref(), b);
 
         writer.seek(-1, old_io::SeekEnd).unwrap();
-        writer.write(&[1, 2]).unwrap();
+        writer.write_all(&[1, 2]).unwrap();
         let b: &[_] = &[3, 4, 2, 0, 1, 5, 6, 1, 2];
         assert_eq!(writer.get_ref(), b);
 
         writer.seek(1, old_io::SeekEnd).unwrap();
-        writer.write(&[1]).unwrap();
+        writer.write_all(&[1]).unwrap();
         let b: &[_] = &[3, 4, 2, 0, 1, 5, 6, 1, 2, 0, 1];
         assert_eq!(writer.get_ref(), b);
     }
@@ -174,7 +174,7 @@ fn test_seekable_mem_writer() {
     fn seek_past_end() {
         let mut r = SeekableMemWriter::new();
         r.seek(10, old_io::SeekSet).unwrap();
-        assert!(r.write(&[3]).is_ok());
+        assert!(r.write_all(&[3]).is_ok());
     }
 
     #[test]
@@ -190,7 +190,7 @@ fn do_bench_seekable_mem_writer(b: &mut Bencher, times: uint, len: uint) {
         b.iter(|| {
             let mut wr = SeekableMemWriter::new();
             for _ in 0..times {
-                wr.write(&src).unwrap();
+                wr.write_all(&src).unwrap();
             }
 
             let v = wr.unwrap();
index 05cd24de7368c6a831597d8e9aa4e096c916adf8..d71bcdf29243ccad490604262f3700c883672409 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 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.
 
-//! Really Bad Markup Language (rbml) is a temporary measure until we migrate
-//! the rust object metadata to a better serialization format. It is not
-//! intended to be used by users.
+//! Really Bad Markup Language (rbml) is an internal serialization format of rustc.
+//! This is not intended to be used by users.
 //!
-//! It is loosely based on the Extensible Binary Markup Language (ebml):
-//!     http://www.matroska.org/technical/specs/rfc/index.html
+//! Originally based on the Extensible Binary Markup Language
+//! (ebml; http://www.matroska.org/technical/specs/rfc/index.html),
+//! it is now a separate format tuned for the rust object metadata.
+//!
+//! # Encoding
+//!
+//! RBML document consists of the tag, length and data.
+//! The encoded data can contain multiple RBML documents concatenated.
+//!
+//! **Tags** are a hint for the following data.
+//! Tags are a number from 0x000 to 0xfff, where 0xf0 through 0xff is reserved.
+//! Tags less than 0xf0 are encoded in one literal byte.
+//! Tags greater than 0xff are encoded in two big-endian bytes,
+//! where the tag number is ORed with 0xf000. (E.g. tag 0x123 = `f1 23`)
+//!
+//! **Lengths** encode the length of the following data.
+//! It is a variable-length unsigned int, and one of the following forms:
+//!
+//! - `80` through `fe` for lengths up to 0x7e;
+//! - `40 ff` through `7f ff` for lengths up to 0x3fff;
+//! - `20 40 00` through `3f ff ff` for lengths up to 0x1fffff;
+//! - `10 20 00 00` through `1f ff ff ff` for lengths up to 0xfffffff.
+//!
+//! The "overlong" form is allowed so that the length can be encoded
+//! without the prior knowledge of the encoded data.
+//! For example, the length 0 can be represented either by `80`, `40 00`,
+//! `20 00 00` or `10 00 00 00`.
+//! The encoder tries to minimize the length if possible.
+//! Also, some predefined tags listed below are so commonly used that
+//! their lengths are omitted ("implicit length").
+//!
+//! **Data** can be either binary bytes or zero or more nested RBML documents.
+//! Nested documents cannot overflow, and should be entirely contained
+//! within a parent document.
+//!
+//! # Predefined Tags
+//!
+//! Most RBML tags are defined by the application.
+//! (For the rust object metadata, see also `rustc::metadata::common`.)
+//! RBML itself does define a set of predefined tags however,
+//! intended for the auto-serialization implementation.
+//!
+//! Predefined tags with an implicit length:
+//!
+//! - `U8`  (`00`): 1-byte unsigned integer.
+//! - `U16` (`01`): 2-byte big endian unsigned integer.
+//! - `U32` (`02`): 4-byte big endian unsigned integer.
+//! - `U64` (`03`): 8-byte big endian unsigned integer.
+//!   Any of `U*` tags can be used to encode primitive unsigned integer types,
+//!   as long as it is no greater than the actual size.
+//!   For example, `u8` can only be represented via the `U8` tag.
+//!
+//! - `I8`  (`04`): 1-byte signed integer.
+//! - `I16` (`05`): 2-byte big endian signed integer.
+//! - `I32` (`06`): 4-byte big endian signed integer.
+//! - `I64` (`07`): 8-byte big endian signed integer.
+//!   Similar to `U*` tags. Always uses two's complement encoding.
+//!
+//! - `Bool` (`08`): 1-byte boolean value, `00` for false and `01` for true.
+//!
+//! - `Char` (`09`): 4-byte big endian Unicode scalar value.
+//!   Surrogate pairs or out-of-bound values are invalid.
+//!
+//! - `F32` (`0a`): 4-byte big endian unsigned integer representing
+//!   IEEE 754 binary32 floating-point format.
+//! - `F64` (`0b`): 8-byte big endian unsigned integer representing
+//!   IEEE 754 binary64 floating-point format.
+//!
+//! - `Sub8`  (`0c`): 1-byte unsigned integer for supplementary information.
+//! - `Sub32` (`0d`): 4-byte unsigned integer for supplementary information.
+//!   Those two tags normally occur as the first subdocument of certain tags,
+//!   namely `Enum`, `Vec` and `Map`, to provide a variant or size information.
+//!   They can be used interchangably.
+//!
+//! Predefined tags with an explicit length:
+//!
+//! - `Str` (`10`): A UTF-8-encoded string.
+//!
+//! - `Enum` (`11`): An enum.
+//!   The first subdocument should be `Sub*` tags with a variant ID.
+//!   Subsequent subdocuments, if any, encode variant arguments.
+//!
+//! - `Vec` (`12`): A vector (sequence).
+//! - `VecElt` (`13`): A vector element.
+//!   The first subdocument should be `Sub*` tags with the number of elements.
+//!   Subsequent subdocuments should be `VecElt` tag per each element.
+//!
+//! - `Map` (`14`): A map (associated array).
+//! - `MapKey` (`15`): A key part of the map entry.
+//! - `MapVal` (`16`): A value part of the map entry.
+//!   The first subdocument should be `Sub*` tags with the number of entries.
+//!   Subsequent subdocuments should be an alternating sequence of
+//!   `MapKey` and `MapVal` tags per each entry.
+//!
+//! - `Opaque` (`17`): An opaque, custom-format tag.
+//!   Used to wrap ordinary custom tags or data in the auto-serialized context.
+//!   Rustc typically uses this to encode type informations.
+//!
+//! First 0x20 tags are reserved by RBML; custom tags start at 0x20.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rbml"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
@@ -64,6 +162,10 @@ pub fn get<'a>(&'a self, tag: uint) -> Doc<'a> {
         reader::get_doc(*self, tag)
     }
 
+    pub fn is_empty(&self) -> bool {
+        self.start == self.end
+    }
+
     pub fn as_str_slice<'a>(&'a self) -> &'a str {
         str::from_utf8(&self.data[self.start..self.end]).unwrap()
     }
@@ -80,41 +182,51 @@ pub struct TaggedDoc<'a> {
 
 #[derive(Copy, Debug)]
 pub enum EbmlEncoderTag {
-    EsUint,     // 0
-    EsU64,      // 1
-    EsU32,      // 2
-    EsU16,      // 3
-    EsU8,       // 4
-    EsInt,      // 5
-    EsI64,      // 6
-    EsI32,      // 7
-    EsI16,      // 8
-    EsI8,       // 9
-    EsBool,     // 10
-    EsChar,     // 11
-    EsStr,      // 12
-    EsF64,      // 13
-    EsF32,      // 14
-    EsFloat,    // 15
-    EsEnum,     // 16
-    EsEnumVid,  // 17
-    EsEnumBody, // 18
-    EsVec,      // 19
-    EsVecLen,   // 20
-    EsVecElt,   // 21
-    EsMap,      // 22
-    EsMapLen,   // 23
-    EsMapKey,   // 24
-    EsMapVal,   // 25
-
-    EsOpaque,
-
-    EsLabel, // Used only when debugging
+    // tags 00..1f are reserved for auto-serialization.
+    // first NUM_IMPLICIT_TAGS tags are implicitly sized and lengths are not encoded.
+
+    EsU8       = 0x00, // + 1 byte
+    EsU16      = 0x01, // + 2 bytes
+    EsU32      = 0x02, // + 4 bytes
+    EsU64      = 0x03, // + 8 bytes
+    EsI8       = 0x04, // + 1 byte
+    EsI16      = 0x05, // + 2 bytes
+    EsI32      = 0x06, // + 4 bytes
+    EsI64      = 0x07, // + 8 bytes
+    EsBool     = 0x08, // + 1 byte
+    EsChar     = 0x09, // + 4 bytes
+    EsF32      = 0x0a, // + 4 bytes
+    EsF64      = 0x0b, // + 8 bytes
+    EsSub8     = 0x0c, // + 1 byte
+    EsSub32    = 0x0d, // + 4 bytes
+    // 0x0e and 0x0f are reserved
+
+    EsStr      = 0x10,
+    EsEnum     = 0x11, // encodes the variant id as the first EsSub*
+    EsVec      = 0x12, // encodes the # of elements as the first EsSub*
+    EsVecElt   = 0x13,
+    EsMap      = 0x14, // encodes the # of pairs as the first EsSub*
+    EsMapKey   = 0x15,
+    EsMapVal   = 0x16,
+    EsOpaque   = 0x17,
 }
 
+const NUM_TAGS: uint = 0x1000;
+const NUM_IMPLICIT_TAGS: uint = 0x0e;
+
+static TAG_IMPLICIT_LEN: [i8; NUM_IMPLICIT_TAGS] = [
+    1, 2, 4, 8, // EsU*
+    1, 2, 4, 8, // ESI*
+    1, // EsBool
+    4, // EsChar
+    4, 8, // EsF*
+    1, 4, // EsSub*
+];
+
 #[derive(Debug)]
 pub enum Error {
     IntTooBig(uint),
+    InvalidTag(uint),
     Expected(String),
     IoError(std::old_io::IoError),
     ApplicationError(String)
@@ -138,11 +250,11 @@ pub mod reader {
 
     use serialize;
 
-    use super::{ ApplicationError, EsVec, EsMap, EsEnum, EsVecLen, EsVecElt,
-        EsMapLen, EsMapKey, EsEnumVid, EsU64, EsU32, EsU16, EsU8, EsInt, EsI64,
+    use super::{ ApplicationError, EsVec, EsMap, EsEnum, EsSub8, EsSub32,
+        EsVecElt, EsMapKey, EsU64, EsU32, EsU16, EsU8, EsI64,
         EsI32, EsI16, EsI8, EsBool, EsF64, EsF32, EsChar, EsStr, EsMapVal,
-        EsEnumBody, EsUint, EsOpaque, EsLabel, EbmlEncoderTag, Doc, TaggedDoc,
-        Error, IntTooBig, Expected };
+        EsOpaque, EbmlEncoderTag, Doc, TaggedDoc,
+        Error, IntTooBig, InvalidTag, Expected, NUM_IMPLICIT_TAGS, TAG_IMPLICIT_LEN };
 
     pub type DecodeResult<T> = Result<T, Error>;
     // rbml reading
@@ -165,25 +277,37 @@ pub struct Res {
         pub next: uint
     }
 
+    pub fn tag_at(data: &[u8], start: uint) -> DecodeResult<Res> {
+        let v = data[start] as uint;
+        if v < 0xf0 {
+            Ok(Res { val: v, next: start + 1 })
+        } else if v > 0xf0 {
+            Ok(Res { val: ((v & 0xf) << 8) | data[start + 1] as uint, next: start + 2 })
+        } else {
+            // every tag starting with byte 0xf0 is an overlong form, which is prohibited.
+            Err(InvalidTag(v))
+        }
+    }
+
     #[inline(never)]
     fn vuint_at_slow(data: &[u8], start: uint) -> DecodeResult<Res> {
         let a = data[start];
-        if a & 0x80u8 != 0u8 {
-            return Ok(Res {val: (a & 0x7fu8) as uint, next: start + 1});
+        if a & 0x80 != 0 {
+            return Ok(Res {val: (a & 0x7f) as uint, next: start + 1});
         }
-        if a & 0x40u8 != 0u8 {
-            return Ok(Res {val: ((a & 0x3fu8) as uint) << 8 |
+        if a & 0x40 != 0 {
+            return Ok(Res {val: ((a & 0x3f) as uint) << 8 |
                         (data[start + 1] as uint),
                     next: start + 2});
         }
-        if a & 0x20u8 != 0u8 {
-            return Ok(Res {val: ((a & 0x1fu8) as uint) << 16 |
+        if a & 0x20 != 0 {
+            return Ok(Res {val: ((a & 0x1f) as uint) << 16 |
                         (data[start + 1] as uint) << 8 |
                         (data[start + 2] as uint),
                     next: start + 3});
         }
-        if a & 0x10u8 != 0u8 {
-            return Ok(Res {val: ((a & 0x0fu8) as uint) << 24 |
+        if a & 0x10 != 0 {
+            return Ok(Res {val: ((a & 0x0f) as uint) << 24 |
                         (data[start + 1] as uint) << 16 |
                         (data[start + 2] as uint) << 8 |
                         (data[start + 3] as uint),
@@ -237,9 +361,17 @@ pub fn vuint_at(data: &[u8], start: uint) -> DecodeResult<Res> {
         }
     }
 
+    pub fn tag_len_at(data: &[u8], tag: Res) -> DecodeResult<Res> {
+        if tag.val < NUM_IMPLICIT_TAGS && TAG_IMPLICIT_LEN[tag.val] >= 0 {
+            Ok(Res { val: TAG_IMPLICIT_LEN[tag.val] as uint, next: tag.next })
+        } else {
+            vuint_at(data, tag.next)
+        }
+    }
+
     pub fn doc_at<'a>(data: &'a [u8], start: uint) -> DecodeResult<TaggedDoc<'a>> {
-        let elt_tag = try!(vuint_at(data, start));
-        let elt_size = try!(vuint_at(data, elt_tag.next));
+        let elt_tag = try!(tag_at(data, start));
+        let elt_size = try!(tag_len_at(data, elt_tag));
         let end = elt_size.next + elt_size.val;
         Ok(TaggedDoc {
             tag: elt_tag.val,
@@ -250,8 +382,8 @@ pub fn doc_at<'a>(data: &'a [u8], start: uint) -> DecodeResult<TaggedDoc<'a>> {
     pub fn maybe_get_doc<'a>(d: Doc<'a>, tg: uint) -> Option<Doc<'a>> {
         let mut pos = d.start;
         while pos < d.end {
-            let elt_tag = try_or!(vuint_at(d.data, pos), None);
-            let elt_size = try_or!(vuint_at(d.data, elt_tag.next), None);
+            let elt_tag = try_or!(tag_at(d.data, pos), None);
+            let elt_size = try_or!(tag_len_at(d.data, elt_tag), None);
             pos = elt_size.next + elt_size.val;
             if elt_tag.val == tg {
                 return Some(Doc { data: d.data, start: elt_size.next,
@@ -276,8 +408,8 @@ pub fn docs<F>(d: Doc, mut it: F) -> bool where
     {
         let mut pos = d.start;
         while pos < d.end {
-            let elt_tag = try_or!(vuint_at(d.data, pos), false);
-            let elt_size = try_or!(vuint_at(d.data, elt_tag.next), false);
+            let elt_tag = try_or!(tag_at(d.data, pos), false);
+            let elt_size = try_or!(tag_len_at(d.data, elt_tag), false);
             pos = elt_size.next + elt_size.val;
             let doc = Doc { data: d.data, start: elt_size.next, end: pos };
             if !it(elt_tag.val, doc) {
@@ -292,8 +424,8 @@ pub fn tagged_docs<F>(d: Doc, tg: uint, mut it: F) -> bool where
     {
         let mut pos = d.start;
         while pos < d.end {
-            let elt_tag = try_or!(vuint_at(d.data, pos), false);
-            let elt_size = try_or!(vuint_at(d.data, elt_tag.next), false);
+            let elt_tag = try_or!(tag_at(d.data, pos), false);
+            let elt_size = try_or!(tag_len_at(d.data, elt_tag), false);
             pos = elt_size.next + elt_size.val;
             if elt_tag.val == tg {
                 let doc = Doc { data: d.data, start: elt_size.next,
@@ -357,23 +489,6 @@ pub fn new(d: Doc<'doc>) -> Decoder<'doc> {
             }
         }
 
-        fn _check_label(&mut self, lbl: &str) -> DecodeResult<()> {
-            if self.pos < self.parent.end {
-                let TaggedDoc { tag: r_tag, doc: r_doc } =
-                    try!(doc_at(self.parent.data, self.pos));
-
-                if r_tag == (EsLabel as uint) {
-                    self.pos = r_doc.end;
-                    let str = r_doc.as_str_slice();
-                    if lbl != str {
-                        return Err(Expected(format!("Expected label {:?} but \
-                                                     found {:?}", lbl, str)));
-                    }
-                }
-            }
-            Ok(())
-        }
-
         fn next_doc(&mut self, exp_tag: EbmlEncoderTag) -> DecodeResult<Doc<'doc>> {
             debug!(". next_doc(exp_tag={:?})", exp_tag);
             if self.pos >= self.parent.end {
@@ -416,10 +531,66 @@ fn push_doc<T, F>(&mut self, exp_tag: EbmlEncoderTag, f: F) -> DecodeResult<T> w
             Ok(r)
         }
 
-        fn _next_uint(&mut self, exp_tag: EbmlEncoderTag) -> DecodeResult<uint> {
-            let r = doc_as_u32(try!(self.next_doc(exp_tag)));
-            debug!("_next_uint exp_tag={:?} result={:?}", exp_tag, r);
-            Ok(r as uint)
+        fn _next_sub(&mut self) -> DecodeResult<uint> {
+            // empty vector/map optimization
+            if self.parent.is_empty() {
+                return Ok(0);
+            }
+
+            let TaggedDoc { tag: r_tag, doc: r_doc } =
+                try!(doc_at(self.parent.data, self.pos));
+            let r = if r_tag == (EsSub8 as uint) {
+                doc_as_u8(r_doc) as uint
+            } else if r_tag == (EsSub32 as uint) {
+                doc_as_u32(r_doc) as uint
+            } else {
+                return Err(Expected(format!("expected EBML doc with tag {:?} or {:?} but \
+                                             found tag {:?}", EsSub8, EsSub32, r_tag)));
+            };
+            if r_doc.end > self.parent.end {
+                return Err(Expected(format!("invalid EBML, child extends to \
+                                             {:#x}, parent to {:#x}",
+                                            r_doc.end, self.parent.end)));
+            }
+            self.pos = r_doc.end;
+            debug!("_next_sub result={:?}", r);
+            Ok(r)
+        }
+
+        // variable-length unsigned integer with different tags.
+        // `first_tag` should be a tag for u8 or i8.
+        // `last_tag` should be the largest allowed integer tag with the matching signedness.
+        // all tags between them should be valid, in the order of u8, u16, u32 and u64.
+        fn _next_int(&mut self,
+                     first_tag: EbmlEncoderTag,
+                     last_tag: EbmlEncoderTag) -> DecodeResult<u64> {
+            if self.pos >= self.parent.end {
+                return Err(Expected(format!("no more documents in \
+                                             current node!")));
+            }
+
+            let TaggedDoc { tag: r_tag, doc: r_doc } =
+                try!(doc_at(self.parent.data, self.pos));
+            let r = if first_tag as uint <= r_tag && r_tag <= last_tag as uint {
+                match r_tag - first_tag as uint {
+                    0 => doc_as_u8(r_doc) as u64,
+                    1 => doc_as_u16(r_doc) as u64,
+                    2 => doc_as_u32(r_doc) as u64,
+                    3 => doc_as_u64(r_doc) as u64,
+                    _ => unreachable!(),
+                }
+            } else {
+                return Err(Expected(format!("expected EBML doc with tag {:?} through {:?} but \
+                                             found tag {:?}", first_tag, last_tag, r_tag)));
+            };
+            if r_doc.end > self.parent.end {
+                return Err(Expected(format!("invalid EBML, child extends to \
+                                             {:#x}, parent to {:#x}",
+                                            r_doc.end, self.parent.end)));
+            }
+            self.pos = r_doc.end;
+            debug!("_next_int({:?}, {:?}) result={:?}", first_tag, last_tag, r);
+            Ok(r)
         }
 
         pub fn read_opaque<R, F>(&mut self, op: F) -> DecodeResult<R> where
@@ -443,12 +614,12 @@ impl<'doc> serialize::Decoder for Decoder<'doc> {
         type Error = Error;
         fn read_nil(&mut self) -> DecodeResult<()> { Ok(()) }
 
-        fn read_u64(&mut self) -> DecodeResult<u64> { Ok(doc_as_u64(try!(self.next_doc(EsU64)))) }
-        fn read_u32(&mut self) -> DecodeResult<u32> { Ok(doc_as_u32(try!(self.next_doc(EsU32)))) }
-        fn read_u16(&mut self) -> DecodeResult<u16> { Ok(doc_as_u16(try!(self.next_doc(EsU16)))) }
-        fn read_u8 (&mut self) -> DecodeResult<u8 > { Ok(doc_as_u8 (try!(self.next_doc(EsU8 )))) }
+        fn read_u64(&mut self) -> DecodeResult<u64> { self._next_int(EsU8, EsU64) }
+        fn read_u32(&mut self) -> DecodeResult<u32> { Ok(try!(self._next_int(EsU8, EsU32)) as u32) }
+        fn read_u16(&mut self) -> DecodeResult<u16> { Ok(try!(self._next_int(EsU8, EsU16)) as u16) }
+        fn read_u8(&mut self) -> DecodeResult<u8> { Ok(doc_as_u8(try!(self.next_doc(EsU8)))) }
         fn read_uint(&mut self) -> DecodeResult<uint> {
-            let v = doc_as_u64(try!(self.next_doc(EsUint)));
+            let v = try!(self._next_int(EsU8, EsU64));
             if v > (::std::usize::MAX as u64) {
                 Err(IntTooBig(v as uint))
             } else {
@@ -456,20 +627,12 @@ fn read_uint(&mut self) -> DecodeResult<uint> {
             }
         }
 
-        fn read_i64(&mut self) -> DecodeResult<i64> {
-            Ok(doc_as_u64(try!(self.next_doc(EsI64))) as i64)
-        }
-        fn read_i32(&mut self) -> DecodeResult<i32> {
-            Ok(doc_as_u32(try!(self.next_doc(EsI32))) as i32)
-        }
-        fn read_i16(&mut self) -> DecodeResult<i16> {
-            Ok(doc_as_u16(try!(self.next_doc(EsI16))) as i16)
-        }
-        fn read_i8 (&mut self) -> DecodeResult<i8> {
-            Ok(doc_as_u8(try!(self.next_doc(EsI8 ))) as i8)
-        }
+        fn read_i64(&mut self) -> DecodeResult<i64> { Ok(try!(self._next_int(EsI8, EsI64)) as i64) }
+        fn read_i32(&mut self) -> DecodeResult<i32> { Ok(try!(self._next_int(EsI8, EsI32)) as i32) }
+        fn read_i16(&mut self) -> DecodeResult<i16> { Ok(try!(self._next_int(EsI8, EsI16)) as i16) }
+        fn read_i8(&mut self) -> DecodeResult<i8> { Ok(doc_as_u8(try!(self.next_doc(EsI8))) as i8) }
         fn read_int(&mut self) -> DecodeResult<int> {
-            let v = doc_as_u64(try!(self.next_doc(EsInt))) as i64;
+            let v = try!(self._next_int(EsI8, EsI64)) as i64;
             if v > (isize::MAX as i64) || v < (isize::MIN as i64) {
                 debug!("FIXME \\#6122: Removing this makes this function miscompile");
                 Err(IntTooBig(v as uint))
@@ -502,7 +665,6 @@ fn read_enum<T, F>(&mut self, name: &str, f: F) -> DecodeResult<T> where
             F: FnOnce(&mut Decoder<'doc>) -> DecodeResult<T>,
         {
             debug!("read_enum({})", name);
-            try!(self._check_label(name));
 
             let doc = try!(self.next_doc(EsEnum));
 
@@ -522,20 +684,10 @@ fn read_enum_variant<T, F>(&mut self, _: &[&str],
             where F: FnMut(&mut Decoder<'doc>, uint) -> DecodeResult<T>,
         {
             debug!("read_enum_variant()");
-            let idx = try!(self._next_uint(EsEnumVid));
+            let idx = try!(self._next_sub());
             debug!("  idx={}", idx);
 
-            let doc = try!(self.next_doc(EsEnumBody));
-
-            let (old_parent, old_pos) = (self.parent, self.pos);
-            self.parent = doc;
-            self.pos = self.parent.start;
-
-            let result = try!(f(self, idx));
-
-            self.parent = old_parent;
-            self.pos = old_pos;
-            Ok(result)
+            f(self, idx)
         }
 
         fn read_enum_variant_arg<T, F>(&mut self, idx: uint, f: F) -> DecodeResult<T> where
@@ -550,20 +702,10 @@ fn read_enum_struct_variant<T, F>(&mut self, _: &[&str],
             where F: FnMut(&mut Decoder<'doc>, uint) -> DecodeResult<T>,
         {
             debug!("read_enum_struct_variant()");
-            let idx = try!(self._next_uint(EsEnumVid));
+            let idx = try!(self._next_sub());
             debug!("  idx={}", idx);
 
-            let doc = try!(self.next_doc(EsEnumBody));
-
-            let (old_parent, old_pos) = (self.parent, self.pos);
-            self.parent = doc;
-            self.pos = self.parent.start;
-
-            let result = try!(f(self, idx));
-
-            self.parent = old_parent;
-            self.pos = old_pos;
-            Ok(result)
+            f(self, idx)
         }
 
         fn read_enum_struct_variant_field<T, F>(&mut self,
@@ -588,7 +730,6 @@ fn read_struct_field<T, F>(&mut self, name: &str, idx: uint, f: F) -> DecodeResu
             F: FnOnce(&mut Decoder<'doc>) -> DecodeResult<T>,
         {
             debug!("read_struct_field(name={}, idx={})", name, idx);
-            try!(self._check_label(name));
             f(self)
         }
 
@@ -652,7 +793,7 @@ fn read_seq<T, F>(&mut self, f: F) -> DecodeResult<T> where
         {
             debug!("read_seq()");
             self.push_doc(EsVec, move |d| {
-                let len = try!(d._next_uint(EsVecLen));
+                let len = try!(d._next_sub());
                 debug!("  len={}", len);
                 f(d, len)
             })
@@ -670,7 +811,7 @@ fn read_map<T, F>(&mut self, f: F) -> DecodeResult<T> where
         {
             debug!("read_map()");
             self.push_doc(EsMap, move |d| {
-                let len = try!(d._next_uint(EsMapLen));
+                let len = try!(d._next_sub());
                 debug!("  len={}", len);
                 f(d, len)
             })
@@ -701,11 +842,14 @@ pub mod writer {
     use std::num::Int;
     use std::old_io::{Writer, Seek};
     use std::old_io;
+    use std::slice::bytes;
+    use std::num::ToPrimitive;
 
-    use super::{ EsVec, EsMap, EsEnum, EsVecLen, EsVecElt, EsMapLen, EsMapKey,
-        EsEnumVid, EsU64, EsU32, EsU16, EsU8, EsInt, EsI64, EsI32, EsI16, EsI8,
-        EsBool, EsF64, EsF32, EsChar, EsStr, EsMapVal, EsEnumBody, EsUint,
-        EsOpaque, EsLabel, EbmlEncoderTag };
+    use super::{ EsVec, EsMap, EsEnum, EsSub8, EsSub32, EsVecElt, EsMapKey,
+        EsU64, EsU32, EsU16, EsU8, EsI64, EsI32, EsI16, EsI8,
+        EsBool, EsF64, EsF32, EsChar, EsStr, EsMapVal,
+        EsOpaque, NUM_IMPLICIT_TAGS, NUM_TAGS };
+    use super::io::SeekableMemWriter;
 
     use serialize;
 
@@ -713,18 +857,33 @@ pub mod writer {
     pub type EncodeResult = old_io::IoResult<()>;
 
     // rbml writing
-    pub struct Encoder<'a, W:'a> {
-        pub writer: &'a mut W,
+    pub struct Encoder<'a> {
+        pub writer: &'a mut SeekableMemWriter,
         size_positions: Vec<uint>,
+        relax_limit: u64, // do not move encoded bytes before this position
+    }
+
+    fn write_tag<W: Writer>(w: &mut W, n: uint) -> EncodeResult {
+        if n < 0xf0 {
+            w.write_all(&[n as u8])
+        } else if 0x100 <= n && n < NUM_TAGS {
+            w.write_all(&[0xf0 | (n >> 8) as u8, n as u8])
+        } else {
+            Err(old_io::IoError {
+                kind: old_io::OtherIoError,
+                desc: "invalid tag",
+                detail: Some(format!("{}", n))
+            })
+        }
     }
 
     fn write_sized_vuint<W: Writer>(w: &mut W, n: uint, size: uint) -> EncodeResult {
         match size {
-            1 => w.write_all(&[0x80u8 | (n as u8)]),
-            2 => w.write_all(&[0x40u8 | ((n >> 8) as u8), n as u8]),
-            3 => w.write_all(&[0x20u8 | ((n >> 16) as u8), (n >> 8) as u8,
+            1 => w.write_all(&[0x80 | (n as u8)]),
+            2 => w.write_all(&[0x40 | ((n >> 8) as u8), n as u8]),
+            3 => w.write_all(&[0x20 | ((n >> 16) as u8), (n >> 8) as u8,
                             n as u8]),
-            4 => w.write_all(&[0x10u8 | ((n >> 24) as u8), (n >> 16) as u8,
+            4 => w.write_all(&[0x10 | ((n >> 24) as u8), (n >> 16) as u8,
                             (n >> 8) as u8, n as u8]),
             _ => Err(old_io::IoError {
                 kind: old_io::OtherIoError,
@@ -746,31 +905,34 @@ fn write_vuint<W: Writer>(w: &mut W, n: uint) -> EncodeResult {
         })
     }
 
-    impl<'a, W: Writer + Seek> Encoder<'a, W> {
-        pub fn new(w: &'a mut W) -> Encoder<'a, W> {
+    impl<'a> Encoder<'a> {
+        pub fn new(w: &'a mut SeekableMemWriter) -> Encoder<'a> {
             Encoder {
                 writer: w,
                 size_positions: vec!(),
+                relax_limit: 0,
             }
         }
 
         /// FIXME(pcwalton): Workaround for badness in trans. DO NOT USE ME.
-        pub unsafe fn unsafe_clone(&self) -> Encoder<'a, W> {
+        pub unsafe fn unsafe_clone(&self) -> Encoder<'a> {
             Encoder {
                 writer: mem::transmute_copy(&self.writer),
                 size_positions: self.size_positions.clone(),
+                relax_limit: self.relax_limit,
             }
         }
 
         pub fn start_tag(&mut self, tag_id: uint) -> EncodeResult {
             debug!("Start tag {:?}", tag_id);
+            assert!(tag_id >= NUM_IMPLICIT_TAGS);
 
             // Write the enum ID:
-            try!(write_vuint(self.writer, tag_id));
+            try!(write_tag(self.writer, tag_id));
 
             // Write a placeholder four-byte size.
             self.size_positions.push(try!(self.writer.tell()) as uint);
-            let zeroes: &[u8] = &[0u8, 0u8, 0u8, 0u8];
+            let zeroes: &[u8] = &[0, 0, 0, 0];
             self.writer.write_all(zeroes)
         }
 
@@ -779,11 +941,29 @@ pub fn end_tag(&mut self) -> EncodeResult {
             let cur_pos = try!(self.writer.tell());
             try!(self.writer.seek(last_size_pos as i64, old_io::SeekSet));
             let size = cur_pos as uint - last_size_pos - 4;
-            try!(write_sized_vuint(self.writer, size, 4));
-            let r = try!(self.writer.seek(cur_pos as i64, old_io::SeekSet));
+
+            // relax the size encoding for small tags (bigger tags are costly to move).
+            // we should never try to move the stable positions, however.
+            const RELAX_MAX_SIZE: uint = 0x100;
+            if size <= RELAX_MAX_SIZE && last_size_pos >= self.relax_limit as uint {
+                // we can't alter the buffer in place, so have a temporary buffer
+                let mut buf = [0u8; RELAX_MAX_SIZE];
+                {
+                    let data = &self.writer.get_ref()[last_size_pos+4..cur_pos as uint];
+                    bytes::copy_memory(&mut buf, data);
+                }
+
+                // overwrite the size and data and continue
+                try!(write_vuint(self.writer, size));
+                try!(self.writer.write_all(&buf[..size]));
+            } else {
+                // overwrite the size with an overlong encoding and skip past the data
+                try!(write_sized_vuint(self.writer, size, 4));
+                try!(self.writer.seek(cur_pos as i64, old_io::SeekSet));
+            }
 
             debug!("End tag (size = {:?})", size);
-            Ok(r)
+            Ok(())
         }
 
         pub fn wr_tag<F>(&mut self, tag_id: uint, blk: F) -> EncodeResult where
@@ -795,7 +975,8 @@ pub fn wr_tag<F>(&mut self, tag_id: uint, blk: F) -> EncodeResult where
         }
 
         pub fn wr_tagged_bytes(&mut self, tag_id: uint, b: &[u8]) -> EncodeResult {
-            try!(write_vuint(self.writer, tag_id));
+            assert!(tag_id >= NUM_IMPLICIT_TAGS);
+            try!(write_tag(self.writer, tag_id));
             try!(write_vuint(self.writer, b.len()));
             self.writer.write_all(b)
         }
@@ -839,6 +1020,47 @@ pub fn wr_tagged_str(&mut self, tag_id: uint, v: &str) -> EncodeResult {
             self.wr_tagged_bytes(tag_id, v.as_bytes())
         }
 
+        // for auto-serialization
+        fn wr_tagged_raw_bytes(&mut self, tag_id: uint, b: &[u8]) -> EncodeResult {
+            try!(write_tag(self.writer, tag_id));
+            self.writer.write_all(b)
+        }
+
+        fn wr_tagged_raw_u64(&mut self, tag_id: uint, v: u64) -> EncodeResult {
+            let bytes: [u8; 8] = unsafe { mem::transmute(v.to_be()) };
+            self.wr_tagged_raw_bytes(tag_id, &bytes)
+        }
+
+        fn wr_tagged_raw_u32(&mut self, tag_id: uint, v: u32)  -> EncodeResult{
+            let bytes: [u8; 4] = unsafe { mem::transmute(v.to_be()) };
+            self.wr_tagged_raw_bytes(tag_id, &bytes)
+        }
+
+        fn wr_tagged_raw_u16(&mut self, tag_id: uint, v: u16) -> EncodeResult {
+            let bytes: [u8; 2] = unsafe { mem::transmute(v.to_be()) };
+            self.wr_tagged_raw_bytes(tag_id, &bytes)
+        }
+
+        fn wr_tagged_raw_u8(&mut self, tag_id: uint, v: u8) -> EncodeResult {
+            self.wr_tagged_raw_bytes(tag_id, &[v])
+        }
+
+        fn wr_tagged_raw_i64(&mut self, tag_id: uint, v: i64) -> EncodeResult {
+            self.wr_tagged_raw_u64(tag_id, v as u64)
+        }
+
+        fn wr_tagged_raw_i32(&mut self, tag_id: uint, v: i32) -> EncodeResult {
+            self.wr_tagged_raw_u32(tag_id, v as u32)
+        }
+
+        fn wr_tagged_raw_i16(&mut self, tag_id: uint, v: i16) -> EncodeResult {
+            self.wr_tagged_raw_u16(tag_id, v as u16)
+        }
+
+        fn wr_tagged_raw_i8(&mut self, tag_id: uint, v: i8) -> EncodeResult {
+            self.wr_tagged_raw_bytes(tag_id, &[v as u8])
+        }
+
         pub fn wr_bytes(&mut self, b: &[u8]) -> EncodeResult {
             debug!("Write {:?} bytes", b.len());
             self.writer.write_all(b)
@@ -848,38 +1070,36 @@ pub fn wr_str(&mut self, s: &str) -> EncodeResult {
             debug!("Write str: {:?}", s);
             self.writer.write_all(s.as_bytes())
         }
-    }
-
-    // FIXME (#2743): optionally perform "relaxations" on end_tag to more
-    // efficiently encode sizes; this is a fixed point iteration
-
-    // Set to true to generate more debugging in EBML code.
-    // Totally lame approach.
-    #[cfg(not(ndebug))]
-    static DEBUG: bool = true;
-    #[cfg(ndebug)]
-    static DEBUG: bool = false;
 
-    impl<'a, W: Writer + Seek> Encoder<'a, W> {
-        // used internally to emit things like the vector length and so on
-        fn _emit_tagged_uint(&mut self, t: EbmlEncoderTag, v: uint) -> EncodeResult {
-            assert!(v <= 0xFFFF_FFFF);
-            self.wr_tagged_u32(t as uint, v as u32)
+        /// Returns the current position while marking it stable, i.e.
+        /// generated bytes so far woundn't be affected by relaxation.
+        pub fn mark_stable_position(&mut self) -> u64 {
+            let pos = self.writer.tell().unwrap();
+            if self.relax_limit < pos {
+                self.relax_limit = pos;
+            }
+            pos
         }
+    }
 
-        fn _emit_label(&mut self, label: &str) -> EncodeResult {
-            // There are various strings that we have access to, such as
-            // the name of a record field, which do not actually appear in
-            // the encoded EBML (normally).  This is just for
-            // efficiency.  When debugging, though, we can emit such
-            // labels and then they will be checked by decoder to
-            // try and check panics more quickly.
-            if DEBUG { self.wr_tagged_str(EsLabel as uint, label) }
-            else { Ok(()) }
+    impl<'a> Encoder<'a> {
+        // used internally to emit things like the vector length and so on
+        fn _emit_tagged_sub(&mut self, v: uint) -> EncodeResult {
+            if let Some(v) = v.to_u8() {
+                self.wr_tagged_raw_u8(EsSub8 as uint, v)
+            } else if let Some(v) = v.to_u32() {
+                self.wr_tagged_raw_u32(EsSub32 as uint, v)
+            } else {
+                Err(old_io::IoError {
+                    kind: old_io::OtherIoError,
+                    desc: "length or variant id too big",
+                    detail: Some(format!("{}", v))
+                })
+            }
         }
 
         pub fn emit_opaque<F>(&mut self, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder) -> EncodeResult,
         {
             try!(self.start_tag(EsOpaque as uint));
             try!(f(self));
@@ -887,7 +1107,7 @@ pub fn emit_opaque<F>(&mut self, f: F) -> EncodeResult where
         }
     }
 
-    impl<'a, W: Writer + Seek> serialize::Encoder for Encoder<'a, W> {
+    impl<'a> serialize::Encoder for Encoder<'a> {
         type Error = old_io::IoError;
 
         fn emit_nil(&mut self) -> EncodeResult {
@@ -895,61 +1115,78 @@ fn emit_nil(&mut self) -> EncodeResult {
         }
 
         fn emit_uint(&mut self, v: uint) -> EncodeResult {
-            self.wr_tagged_u64(EsUint as uint, v as u64)
+            self.emit_u64(v as u64)
         }
         fn emit_u64(&mut self, v: u64) -> EncodeResult {
-            self.wr_tagged_u64(EsU64 as uint, v)
+            match v.to_u32() {
+                Some(v) => self.emit_u32(v),
+                None => self.wr_tagged_raw_u64(EsU64 as uint, v)
+            }
         }
         fn emit_u32(&mut self, v: u32) -> EncodeResult {
-            self.wr_tagged_u32(EsU32 as uint, v)
+            match v.to_u16() {
+                Some(v) => self.emit_u16(v),
+                None => self.wr_tagged_raw_u32(EsU32 as uint, v)
+            }
         }
         fn emit_u16(&mut self, v: u16) -> EncodeResult {
-            self.wr_tagged_u16(EsU16 as uint, v)
+            match v.to_u8() {
+                Some(v) => self.emit_u8(v),
+                None => self.wr_tagged_raw_u16(EsU16 as uint, v)
+            }
         }
         fn emit_u8(&mut self, v: u8) -> EncodeResult {
-            self.wr_tagged_u8(EsU8 as uint, v)
+            self.wr_tagged_raw_u8(EsU8 as uint, v)
         }
 
         fn emit_int(&mut self, v: int) -> EncodeResult {
-            self.wr_tagged_i64(EsInt as uint, v as i64)
+            self.emit_i64(v as i64)
         }
         fn emit_i64(&mut self, v: i64) -> EncodeResult {
-            self.wr_tagged_i64(EsI64 as uint, v)
+            match v.to_i32() {
+                Some(v) => self.emit_i32(v),
+                None => self.wr_tagged_raw_i64(EsI64 as uint, v)
+            }
         }
         fn emit_i32(&mut self, v: i32) -> EncodeResult {
-            self.wr_tagged_i32(EsI32 as uint, v)
+            match v.to_i16() {
+                Some(v) => self.emit_i16(v),
+                None => self.wr_tagged_raw_i32(EsI32 as uint, v)
+            }
         }
         fn emit_i16(&mut self, v: i16) -> EncodeResult {
-            self.wr_tagged_i16(EsI16 as uint, v)
+            match v.to_i8() {
+                Some(v) => self.emit_i8(v),
+                None => self.wr_tagged_raw_i16(EsI16 as uint, v)
+            }
         }
         fn emit_i8(&mut self, v: i8) -> EncodeResult {
-            self.wr_tagged_i8(EsI8 as uint, v)
+            self.wr_tagged_raw_i8(EsI8 as uint, v)
         }
 
         fn emit_bool(&mut self, v: bool) -> EncodeResult {
-            self.wr_tagged_u8(EsBool as uint, v as u8)
+            self.wr_tagged_raw_u8(EsBool as uint, v as u8)
         }
 
         fn emit_f64(&mut self, v: f64) -> EncodeResult {
             let bits = unsafe { mem::transmute(v) };
-            self.wr_tagged_u64(EsF64 as uint, bits)
+            self.wr_tagged_raw_u64(EsF64 as uint, bits)
         }
         fn emit_f32(&mut self, v: f32) -> EncodeResult {
             let bits = unsafe { mem::transmute(v) };
-            self.wr_tagged_u32(EsF32 as uint, bits)
+            self.wr_tagged_raw_u32(EsF32 as uint, bits)
         }
         fn emit_char(&mut self, v: char) -> EncodeResult {
-            self.wr_tagged_u32(EsChar as uint, v as u32)
+            self.wr_tagged_raw_u32(EsChar as uint, v as u32)
         }
 
         fn emit_str(&mut self, v: &str) -> EncodeResult {
             self.wr_tagged_str(EsStr as uint, v)
         }
 
-        fn emit_enum<F>(&mut self, name: &str, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+        fn emit_enum<F>(&mut self, _name: &str, f: F) -> EncodeResult where
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
-            try!(self._emit_label(name));
             try!(self.start_tag(EsEnum as uint));
             try!(f(self));
             self.end_tag()
@@ -960,16 +1197,14 @@ fn emit_enum_variant<F>(&mut self,
                                 v_id: uint,
                                 _: uint,
                                 f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
-            try!(self._emit_tagged_uint(EsEnumVid, v_id));
-            try!(self.start_tag(EsEnumBody as uint));
-            try!(f(self));
-            self.end_tag()
+            try!(self._emit_tagged_sub(v_id));
+            f(self)
         }
 
         fn emit_enum_variant_arg<F>(&mut self, _: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             f(self)
         }
@@ -979,7 +1214,7 @@ fn emit_enum_struct_variant<F>(&mut self,
                                        v_id: uint,
                                        cnt: uint,
                                        f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             self.emit_enum_variant(v_name, v_id, cnt, f)
         }
@@ -988,48 +1223,47 @@ fn emit_enum_struct_variant_field<F>(&mut self,
                                              _: &str,
                                              idx: uint,
                                              f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             self.emit_enum_variant_arg(idx, f)
         }
 
         fn emit_struct<F>(&mut self, _: &str, _len: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             f(self)
         }
 
-        fn emit_struct_field<F>(&mut self, name: &str, _: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+        fn emit_struct_field<F>(&mut self, _name: &str, _: uint, f: F) -> EncodeResult where
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
-            try!(self._emit_label(name));
             f(self)
         }
 
         fn emit_tuple<F>(&mut self, len: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             self.emit_seq(len, f)
         }
         fn emit_tuple_arg<F>(&mut self, idx: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             self.emit_seq_elt(idx, f)
         }
 
         fn emit_tuple_struct<F>(&mut self, _: &str, len: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             self.emit_seq(len, f)
         }
         fn emit_tuple_struct_arg<F>(&mut self, idx: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             self.emit_seq_elt(idx, f)
         }
 
         fn emit_option<F>(&mut self, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             self.emit_enum("Option", f)
         }
@@ -1037,24 +1271,28 @@ fn emit_option_none(&mut self) -> EncodeResult {
             self.emit_enum_variant("None", 0, 0, |_| Ok(()))
         }
         fn emit_option_some<F>(&mut self, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
 
             self.emit_enum_variant("Some", 1, 1, f)
         }
 
         fn emit_seq<F>(&mut self, len: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
+            if len == 0 {
+                // empty vector optimization
+                return self.wr_tagged_bytes(EsVec as uint, &[]);
+            }
 
             try!(self.start_tag(EsVec as uint));
-            try!(self._emit_tagged_uint(EsVecLen, len));
+            try!(self._emit_tagged_sub(len));
             try!(f(self));
             self.end_tag()
         }
 
         fn emit_seq_elt<F>(&mut self, _idx: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
 
             try!(self.start_tag(EsVecElt as uint));
@@ -1063,17 +1301,21 @@ fn emit_seq_elt<F>(&mut self, _idx: uint, f: F) -> EncodeResult where
         }
 
         fn emit_map<F>(&mut self, len: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
+            if len == 0 {
+                // empty map optimization
+                return self.wr_tagged_bytes(EsMap as uint, &[]);
+            }
 
             try!(self.start_tag(EsMap as uint));
-            try!(self._emit_tagged_uint(EsMapLen, len));
+            try!(self._emit_tagged_sub(len));
             try!(f(self));
             self.end_tag()
         }
 
         fn emit_map_elt_key<F>(&mut self, _idx: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
 
             try!(self.start_tag(EsMapKey as uint));
@@ -1082,7 +1324,7 @@ fn emit_map_elt_key<F>(&mut self, _idx: uint, f: F) -> EncodeResult where
         }
 
         fn emit_map_elt_val<F>(&mut self, _idx: uint, f: F) -> EncodeResult where
-            F: FnOnce(&mut Encoder<'a, W>) -> EncodeResult,
+            F: FnOnce(&mut Encoder<'a>) -> EncodeResult,
         {
             try!(self.start_tag(EsMapVal as uint));
             try!(f(self));
@@ -1182,9 +1424,9 @@ mod bench {
 
     #[bench]
     pub fn vuint_at_A_aligned(b: &mut Bencher) {
-        let data = (0i32..4*100).map(|i| {
+        let data = (0..4*100).map(|i| {
             match i % 2 {
-              0 => 0x80u8,
+              0 => 0x80,
               _ => i as u8,
             }
         }).collect::<Vec<_>>();
@@ -1200,9 +1442,9 @@ pub fn vuint_at_A_aligned(b: &mut Bencher) {
 
     #[bench]
     pub fn vuint_at_A_unaligned(b: &mut Bencher) {
-        let data = (0i32..4*100+1).map(|i| {
+        let data = (0..4*100+1).map(|i| {
             match i % 2 {
-              1 => 0x80u8,
+              1 => 0x80,
               _ => i as u8
             }
         }).collect::<Vec<_>>();
@@ -1218,11 +1460,11 @@ pub fn vuint_at_A_unaligned(b: &mut Bencher) {
 
     #[bench]
     pub fn vuint_at_D_aligned(b: &mut Bencher) {
-        let data = (0i32..4*100).map(|i| {
+        let data = (0..4*100).map(|i| {
             match i % 4 {
-              0 => 0x10u8,
+              0 => 0x10,
               3 => i as u8,
-              _ => 0u8
+              _ => 0
             }
         }).collect::<Vec<_>>();
         let mut sum = 0;
@@ -1237,11 +1479,11 @@ pub fn vuint_at_D_aligned(b: &mut Bencher) {
 
     #[bench]
     pub fn vuint_at_D_unaligned(b: &mut Bencher) {
-        let data = (0i32..4*100+1).map(|i| {
+        let data = (0..4*100+1).map(|i| {
             match i % 4 {
-              1 => 0x10u8,
+              1 => 0x10,
               0 => i as u8,
-              _ => 0u8
+              _ => 0
             }
         }).collect::<Vec<_>>();
         let mut sum = 0;
index aa51320ee7f43ee0c861beeedfb56c76f1b0f911..f424ac0cda2719077d30fd197e2fc1d2c75a85dd 100644 (file)
@@ -14,6 +14,8 @@
 //!
 //! This API is completely unstable and subject to change.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
 #![feature(unsafe_destructor)]
 #![feature(staged_api)]
 #![feature(std_misc)]
-#![feature(os)]
+#![feature(path)]
+#![feature(io)]
+#![feature(path_ext)]
+#![feature(str_words)]
 #![cfg_attr(test, feature(test))]
 
 extern crate arena;
index f635c77af9b2a1053bbc5d05f619b81d8ab60ae8..a777e1f7f75e6ad13c59cd12ae0e84ba52b20f87 100644 (file)
@@ -568,9 +568,9 @@ fn visit_variant(&mut self, v: &ast::Variant, g: &ast::Generics) {
         })
     }
 
-    // FIXME(#10894) should continue recursing
     fn visit_ty(&mut self, t: &ast::Ty) {
         run_lints!(self, check_ty, t);
+        visit::walk_ty(self, t);
     }
 
     fn visit_ident(&mut self, sp: Span, id: ast::Ident) {
index 4930eddb35a53213ebad184791eebf6c9b4d8713..081c64ecae88102920ea0bbaa03e0b4a57d16422 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
 
 use back::svh::Svh;
 
-// EBML enum definitions and utils shared by the encoder and decoder
+// RBML enum definitions and utils shared by the encoder and decoder
+//
+// 0x00..0x1f: reserved for RBML generic type tags
+// 0x20..0xef: free for use, preferred for frequent tags
+// 0xf0..0xff: internally used by RBML to encode 0x100..0xfff in two bytes
+// 0x100..0xfff: free for use, preferred for infrequent tags
 
-pub const tag_items: uint = 0x00;
+pub const tag_items: uint = 0x100; // top-level only
 
-pub const tag_paths_data_name: uint = 0x01;
+pub const tag_paths_data_name: uint = 0x20;
 
-pub const tag_def_id: uint = 0x02;
+pub const tag_def_id: uint = 0x21;
 
-pub const tag_items_data: uint = 0x03;
+pub const tag_items_data: uint = 0x22;
 
-pub const tag_items_data_item: uint = 0x04;
+pub const tag_items_data_item: uint = 0x23;
 
-pub const tag_items_data_item_family: uint = 0x05;
+pub const tag_items_data_item_family: uint = 0x24;
 
-pub const tag_items_data_item_type: uint = 0x07;
+pub const tag_items_data_item_type: uint = 0x25;
 
-pub const tag_items_data_item_symbol: uint = 0x08;
+pub const tag_items_data_item_symbol: uint = 0x26;
 
-pub const tag_items_data_item_variant: uint = 0x09;
+pub const tag_items_data_item_variant: uint = 0x27;
 
-pub const tag_items_data_parent_item: uint = 0x0a;
+pub const tag_items_data_parent_item: uint = 0x28;
 
-pub const tag_items_data_item_is_tuple_struct_ctor: uint = 0x0b;
+pub const tag_items_data_item_is_tuple_struct_ctor: uint = 0x29;
 
-pub const tag_index: uint = 0x0c;
+pub const tag_index: uint = 0x2a;
 
-pub const tag_index_buckets: uint = 0x0d;
+pub const tag_index_buckets: uint = 0x2b;
 
-pub const tag_index_buckets_bucket: uint = 0x0e;
+pub const tag_index_buckets_bucket: uint = 0x2c;
 
-pub const tag_index_buckets_bucket_elt: uint = 0x0f;
+pub const tag_index_buckets_bucket_elt: uint = 0x2d;
 
-pub const tag_index_table: uint = 0x10;
+pub const tag_index_table: uint = 0x2e;
 
-pub const tag_meta_item_name_value: uint = 0x11;
+pub const tag_meta_item_name_value: uint = 0x2f;
 
-pub const tag_meta_item_name: uint = 0x12;
+pub const tag_meta_item_name: uint = 0x30;
 
-pub const tag_meta_item_value: uint = 0x13;
+pub const tag_meta_item_value: uint = 0x31;
 
-pub const tag_attributes: uint = 0x14;
+pub const tag_attributes: uint = 0x101; // top-level only
 
-pub const tag_attribute: uint = 0x15;
+pub const tag_attribute: uint = 0x32;
 
-pub const tag_meta_item_word: uint = 0x16;
+pub const tag_meta_item_word: uint = 0x33;
 
-pub const tag_meta_item_list: uint = 0x17;
+pub const tag_meta_item_list: uint = 0x34;
 
 // The list of crates that this crate depends on
-pub const tag_crate_deps: uint = 0x18;
+pub const tag_crate_deps: uint = 0x102; // top-level only
 
 // A single crate dependency
-pub const tag_crate_dep: uint = 0x19;
+pub const tag_crate_dep: uint = 0x35;
 
-pub const tag_crate_hash: uint = 0x1a;
-pub const tag_crate_crate_name: uint = 0x1b;
+pub const tag_crate_hash: uint = 0x103; // top-level only
+pub const tag_crate_crate_name: uint = 0x104; // top-level only
 
-pub const tag_crate_dep_crate_name: uint = 0x1d;
-pub const tag_crate_dep_hash: uint = 0x1e;
+pub const tag_crate_dep_crate_name: uint = 0x36;
+pub const tag_crate_dep_hash: uint = 0x37;
 
-pub const tag_mod_impl: uint = 0x1f;
+pub const tag_mod_impl: uint = 0x38;
 
-pub const tag_item_trait_item: uint = 0x20;
+pub const tag_item_trait_item: uint = 0x39;
 
-pub const tag_item_trait_ref: uint = 0x21;
-pub const tag_item_super_trait_ref: uint = 0x22;
+pub const tag_item_trait_ref: uint = 0x3a;
 
 // discriminator value for variants
-pub const tag_disr_val: uint = 0x23;
+pub const tag_disr_val: uint = 0x3c;
 
 // used to encode ast_map::PathElem
-pub const tag_path: uint = 0x24;
-pub const tag_path_len: uint = 0x25;
-pub const tag_path_elem_mod: uint = 0x26;
-pub const tag_path_elem_name: uint = 0x27;
-pub const tag_item_field: uint = 0x28;
-pub const tag_item_field_origin: uint = 0x29;
-
-pub const tag_item_variances: uint = 0x2a;
+pub const tag_path: uint = 0x3d;
+pub const tag_path_len: uint = 0x3e;
+pub const tag_path_elem_mod: uint = 0x3f;
+pub const tag_path_elem_name: uint = 0x40;
+pub const tag_item_field: uint = 0x41;
+pub const tag_item_field_origin: uint = 0x42;
+
+pub const tag_item_variances: uint = 0x43;
 /*
   trait items contain tag_item_trait_item elements,
   impl items contain tag_item_impl_item elements, and classes
@@ -101,60 +105,59 @@ impl items contain tag_item_impl_item elements, and classes
   both, tag_item_trait_item and tag_item_impl_item have to be two
   different tags.
  */
-pub const tag_item_impl_item: uint = 0x30;
-pub const tag_item_trait_method_explicit_self: uint = 0x31;
+pub const tag_item_impl_item: uint = 0x44;
+pub const tag_item_trait_method_explicit_self: uint = 0x45;
 
 
 // Reexports are found within module tags. Each reexport contains def_ids
 // and names.
-pub const tag_items_data_item_reexport: uint = 0x38;
-pub const tag_items_data_item_reexport_def_id: uint = 0x39;
-pub const tag_items_data_item_reexport_name: uint = 0x3a;
+pub const tag_items_data_item_reexport: uint = 0x46;
+pub const tag_items_data_item_reexport_def_id: uint = 0x47;
+pub const tag_items_data_item_reexport_name: uint = 0x48;
 
 // used to encode crate_ctxt side tables
 #[derive(Copy, PartialEq, FromPrimitive)]
 #[repr(uint)]
-pub enum astencode_tag { // Reserves 0x40 -- 0x5f
-    tag_ast = 0x40,
-
-    tag_tree = 0x41,
-
-    tag_id_range = 0x42,
-
-    tag_table = 0x43,
-    tag_table_id = 0x44,
-    tag_table_val = 0x45,
-    tag_table_def = 0x46,
-    tag_table_node_type = 0x47,
-    tag_table_item_subst = 0x48,
-    tag_table_freevars = 0x49,
-    tag_table_tcache = 0x4a,
-    tag_table_param_defs = 0x4b,
-    tag_table_mutbl = 0x4c,
-    tag_table_last_use = 0x4d,
-    tag_table_spill = 0x4e,
-    tag_table_method_map = 0x4f,
-    tag_table_vtable_map = 0x50,
-    tag_table_adjustments = 0x51,
-    tag_table_moves_map = 0x52,
-    tag_table_capture_map = 0x53,
-    tag_table_closure_tys = 0x54,
-    tag_table_closure_kinds = 0x55,
-    tag_table_upvar_capture_map = 0x56,
-    tag_table_capture_modes = 0x57,
-    tag_table_object_cast_map = 0x58,
-    tag_table_const_qualif = 0x59,
+pub enum astencode_tag { // Reserves 0x50 -- 0x6f
+    tag_ast = 0x50,
+
+    tag_tree = 0x51,
+
+    tag_id_range = 0x52,
+
+    tag_table = 0x53,
+    // GAP 0x54, 0x55
+    tag_table_def = 0x56,
+    tag_table_node_type = 0x57,
+    tag_table_item_subst = 0x58,
+    tag_table_freevars = 0x59,
+    tag_table_tcache = 0x5a,
+    tag_table_param_defs = 0x5b,
+    tag_table_mutbl = 0x5c,
+    tag_table_last_use = 0x5d,
+    tag_table_spill = 0x5e,
+    tag_table_method_map = 0x5f,
+    tag_table_vtable_map = 0x60,
+    tag_table_adjustments = 0x61,
+    tag_table_moves_map = 0x62,
+    tag_table_capture_map = 0x63,
+    tag_table_closure_tys = 0x64,
+    tag_table_closure_kinds = 0x65,
+    tag_table_upvar_capture_map = 0x66,
+    tag_table_capture_modes = 0x67,
+    tag_table_object_cast_map = 0x68,
+    tag_table_const_qualif = 0x69,
 }
 
-pub const tag_item_trait_item_sort: uint = 0x60;
+pub const tag_item_trait_item_sort: uint = 0x70;
 
-pub const tag_item_trait_parent_sort: uint = 0x61;
+pub const tag_item_trait_parent_sort: uint = 0x71;
 
-pub const tag_item_impl_type_basename: uint = 0x62;
+pub const tag_item_impl_type_basename: uint = 0x72;
 
-pub const tag_crate_triple: uint = 0x66;
+pub const tag_crate_triple: uint = 0x105; // top-level only
 
-pub const tag_dylib_dependency_formats: uint = 0x67;
+pub const tag_dylib_dependency_formats: uint = 0x106; // top-level only
 
 // Language items are a top-level directory (for speed). Hierarchy:
 //
@@ -163,51 +166,47 @@ pub enum astencode_tag { // Reserves 0x40 -- 0x5f
 //   - tag_lang_items_item_id: u32
 //   - tag_lang_items_item_node_id: u32
 
-pub const tag_lang_items: uint = 0x70;
-pub const tag_lang_items_item: uint = 0x71;
-pub const tag_lang_items_item_id: uint = 0x72;
-pub const tag_lang_items_item_node_id: uint = 0x73;
-pub const tag_lang_items_missing: uint = 0x74;
+pub const tag_lang_items: uint = 0x107; // top-level only
+pub const tag_lang_items_item: uint = 0x73;
+pub const tag_lang_items_item_id: uint = 0x74;
+pub const tag_lang_items_item_node_id: uint = 0x75;
+pub const tag_lang_items_missing: uint = 0x76;
 
-pub const tag_item_unnamed_field: uint = 0x75;
-pub const tag_items_data_item_visibility: uint = 0x76;
+pub const tag_item_unnamed_field: uint = 0x77;
+pub const tag_items_data_item_visibility: uint = 0x78;
 
 pub const tag_item_method_tps: uint = 0x79;
 pub const tag_item_method_fty: uint = 0x7a;
 
 pub const tag_mod_child: uint = 0x7b;
-pub const tag_misc_info: uint = 0x7c;
-pub const tag_misc_info_crate_items: uint = 0x7d;
-
-pub const tag_item_method_provided_source: uint = 0x7e;
-pub const tag_item_impl_vtables: uint = 0x7f;
+pub const tag_misc_info: uint = 0x108; // top-level only
+pub const tag_misc_info_crate_items: uint = 0x7c;
 
-pub const tag_impls: uint = 0x80;
-pub const tag_impls_impl: uint = 0x81;
+pub const tag_item_method_provided_source: uint = 0x7d;
+pub const tag_item_impl_vtables: uint = 0x7e;
 
-pub const tag_items_data_item_inherent_impl: uint = 0x82;
-pub const tag_items_data_item_extension_impl: uint = 0x83;
+pub const tag_impls: uint = 0x109; // top-level only
+pub const tag_impls_impl: uint = 0x7f;
 
-// GAP 0x84, 0x85, 0x86
+pub const tag_items_data_item_inherent_impl: uint = 0x80;
+pub const tag_items_data_item_extension_impl: uint = 0x81;
 
-pub const tag_native_libraries: uint = 0x87;
-pub const tag_native_libraries_lib: uint = 0x88;
-pub const tag_native_libraries_name: uint = 0x89;
-pub const tag_native_libraries_kind: uint = 0x8a;
+pub const tag_native_libraries: uint = 0x10a; // top-level only
+pub const tag_native_libraries_lib: uint = 0x82;
+pub const tag_native_libraries_name: uint = 0x83;
+pub const tag_native_libraries_kind: uint = 0x84;
 
-pub const tag_plugin_registrar_fn: uint = 0x8b;
+pub const tag_plugin_registrar_fn: uint = 0x10b; // top-level only
 
-// GAP 0x8c, 0x8d
+pub const tag_method_argument_names: uint = 0x85;
+pub const tag_method_argument_name: uint = 0x86;
 
-pub const tag_method_argument_names: uint = 0x8e;
-pub const tag_method_argument_name: uint = 0x8f;
+pub const tag_reachable_extern_fns: uint = 0x10c; // top-level only
+pub const tag_reachable_extern_fn_id: uint = 0x87;
 
-pub const tag_reachable_extern_fns: uint = 0x90;
-pub const tag_reachable_extern_fn_id: uint = 0x91;
+pub const tag_items_data_item_stability: uint = 0x88;
 
-pub const tag_items_data_item_stability: uint = 0x92;
-
-pub const tag_items_data_item_repr: uint = 0x93;
+pub const tag_items_data_item_repr: uint = 0x89;
 
 #[derive(Clone, Debug)]
 pub struct LinkMeta {
@@ -215,42 +214,45 @@ pub struct LinkMeta {
     pub crate_hash: Svh,
 }
 
-// GAP 0x94...0x98
+pub const tag_struct_fields: uint = 0x10d; // top-level only
+pub const tag_struct_field: uint = 0x8a;
+pub const tag_struct_field_id: uint = 0x8b;
+
+pub const tag_attribute_is_sugared_doc: uint = 0x8c;
 
-pub const tag_struct_fields: uint = 0x99;
-pub const tag_struct_field: uint = 0x9a;
-pub const tag_struct_field_id: uint = 0x9b;
+pub const tag_items_data_region: uint = 0x8e;
 
-pub const tag_attribute_is_sugared_doc: uint = 0x9c;
+pub const tag_region_param_def: uint = 0x8f;
+pub const tag_region_param_def_ident: uint = 0x90;
+pub const tag_region_param_def_def_id: uint = 0x91;
+pub const tag_region_param_def_space: uint = 0x92;
+pub const tag_region_param_def_index: uint = 0x93;
 
-pub const tag_trait_def_bounds: uint = 0x9d;
+pub const tag_type_param_def: uint = 0x94;
 
-pub const tag_items_data_region: uint = 0x9e;
+pub const tag_item_generics: uint = 0x95;
+pub const tag_method_ty_generics: uint = 0x96;
 
-pub const tag_region_param_def: uint = 0xa0;
-pub const tag_region_param_def_ident: uint = 0xa1;
-pub const tag_region_param_def_def_id: uint = 0xa2;
-pub const tag_region_param_def_space: uint = 0xa3;
-pub const tag_region_param_def_index: uint = 0xa4;
+pub const tag_predicate: uint = 0x97;
+pub const tag_predicate_space: uint = 0x98;
+pub const tag_predicate_data: uint = 0x99;
 
-pub const tag_type_param_def: uint = 0xa5;
+pub const tag_unsafety: uint = 0x9a;
 
-pub const tag_item_generics: uint = 0xa6;
-pub const tag_method_ty_generics: uint = 0xa7;
+pub const tag_associated_type_names: uint = 0x9b;
+pub const tag_associated_type_name: uint = 0x9c;
 
-pub const tag_predicate: uint = 0xa8;
-pub const tag_predicate_space: uint = 0xa9;
-pub const tag_predicate_data: uint = 0xb0;
+pub const tag_polarity: uint = 0x9d;
 
-pub const tag_unsafety: uint = 0xb1;
+pub const tag_macro_defs: uint = 0x10e; // top-level only
+pub const tag_macro_def: uint = 0x9e;
+pub const tag_macro_def_body: uint = 0x9f;
 
-pub const tag_associated_type_names: uint = 0xb2;
-pub const tag_associated_type_name: uint = 0xb3;
+pub const tag_paren_sugar: uint = 0xa0;
 
-pub const tag_polarity: uint = 0xb4;
+pub const tag_codemap: uint = 0xa1;
+pub const tag_codemap_filemap: uint = 0xa2;
 
-pub const tag_macro_defs: uint = 0xb5;
-pub const tag_macro_def: uint = 0xb6;
-pub const tag_macro_def_body: uint = 0xb7;
+pub const tag_item_super_predicates: uint = 0xa3;
 
-pub const tag_paren_sugar: uint = 0xb8;
+pub const tag_defaulted_trait: uint = 0xa4;
index 46155925b3c72dab922b635ad1b00fd6a67d6f31..00a47ce17dae070a76d2a001265b1056563a9968 100644 (file)
 use metadata::loader;
 use metadata::loader::CratePaths;
 
+use std::path::{Path, PathBuf};
 use std::rc::Rc;
 use syntax::ast;
 use syntax::abi;
 use syntax::attr;
 use syntax::attr::AttrMetaMethods;
-use syntax::codemap::{Span, mk_sp};
+use syntax::codemap::{self, Span, mk_sp, Pos};
 use syntax::parse;
 use syntax::parse::token::InternedString;
 use syntax::parse::token;
@@ -126,7 +127,7 @@ fn register_native_lib(sess: &Session,
 // Extra info about a crate loaded for plugins or exported macros.
 struct ExtensionCrate {
     metadata: PMDSource,
-    dylib: Option<Path>,
+    dylib: Option<PathBuf>,
     target_only: bool,
 }
 
@@ -373,15 +374,17 @@ fn register_crate(&mut self,
         // Maintain a reference to the top most crate.
         let root = if root.is_some() { root } else { &crate_paths };
 
-        let cnum_map = self.resolve_crate_deps(root, lib.metadata.as_slice(), span);
+        let loader::Library { dylib, rlib, metadata } = lib;
 
-        let loader::Library{ dylib, rlib, metadata } = lib;
+        let cnum_map = self.resolve_crate_deps(root, metadata.as_slice(), span);
+        let codemap_import_info = import_codemap(self.sess.codemap(), &metadata);
 
         let cmeta = Rc::new( cstore::crate_metadata {
             name: name.to_string(),
             data: metadata,
             cnum_map: cnum_map,
             cnum: cnum,
+            codemap_import_info: codemap_import_info,
             span: span,
         });
 
@@ -490,7 +493,7 @@ fn read_extension_crate(&mut self, span: Span, info: &CrateInfo) -> ExtensionCra
         };
 
         let dylib = library.dylib.clone();
-        let register = should_link && self.existing_match(info.name.as_slice(),
+        let register = should_link && self.existing_match(&info.name,
                                                           None,
                                                           PathKind::Crate).is_none();
         let metadata = if register {
@@ -539,6 +542,7 @@ pub fn read_exported_macros(&mut self, krate: &ast::Item) -> Vec<ast::MacroDef>
                     // overridden in plugin/load.rs
                     export: false,
                     use_locally: false,
+                    allow_internal_unstable: false,
 
                     body: body,
                 });
@@ -549,7 +553,8 @@ pub fn read_exported_macros(&mut self, krate: &ast::Item) -> Vec<ast::MacroDef>
     }
 
     /// Look for a plugin registrar. Returns library path and symbol name.
-    pub fn find_plugin_registrar(&mut self, span: Span, name: &str) -> Option<(Path, String)> {
+    pub fn find_plugin_registrar(&mut self, span: Span, name: &str)
+                                 -> Option<(PathBuf, String)> {
         let ekrate = self.read_extension_crate(span, &CrateInfo {
              name: name.to_string(),
              ident: name.to_string(),
@@ -572,7 +577,7 @@ pub fn find_plugin_registrar(&mut self, span: Span, name: &str) -> Option<(Path,
             .map(|id| decoder::get_symbol(ekrate.metadata.as_slice(), id));
 
         match (ekrate.dylib.as_ref(), registrar) {
-            (Some(dylib), Some(reg)) => Some((dylib.clone(), reg)),
+            (Some(dylib), Some(reg)) => Some((dylib.to_path_buf(), reg)),
             (None, Some(_)) => {
                 let message = format!("plugin `{}` only found in rlib format, \
                                        but must be available in dylib format",
@@ -586,3 +591,131 @@ pub fn find_plugin_registrar(&mut self, span: Span, name: &str) -> Option<(Path,
         }
     }
 }
+
+/// Imports the codemap from an external crate into the codemap of the crate
+/// currently being compiled (the "local crate").
+///
+/// The import algorithm works analogous to how AST items are inlined from an
+/// external crate's metadata:
+/// For every FileMap in the external codemap an 'inline' copy is created in the
+/// local codemap. The correspondence relation between external and local
+/// FileMaps is recorded in the `ImportedFileMap` objects returned from this
+/// function. When an item from an external crate is later inlined into this
+/// crate, this correspondence information is used to translate the span
+/// information of the inlined item so that it refers the correct positions in
+/// the local codemap (see `astencode::DecodeContext::tr_span()`).
+///
+/// The import algorithm in the function below will reuse FileMaps already
+/// existing in the local codemap. For example, even if the FileMap of some
+/// source file of libstd gets imported many times, there will only ever be
+/// one FileMap object for the corresponding file in the local codemap.
+///
+/// Note that imported FileMaps do not actually contain the source code of the
+/// file they represent, just information about length, line breaks, and
+/// multibyte characters. This information is enough to generate valid debuginfo
+/// for items inlined from other crates.
+fn import_codemap(local_codemap: &codemap::CodeMap,
+                  metadata: &MetadataBlob)
+                  -> Vec<cstore::ImportedFileMap> {
+    let external_codemap = decoder::get_imported_filemaps(metadata.as_slice());
+
+    let imported_filemaps = external_codemap.into_iter().map(|filemap_to_import| {
+        // Try to find an existing FileMap that can be reused for the filemap to
+        // be imported. A FileMap is reusable if it is exactly the same, just
+        // positioned at a different offset within the codemap.
+        let reusable_filemap = {
+            local_codemap.files
+                         .borrow()
+                         .iter()
+                         .find(|fm| are_equal_modulo_startpos(&fm, &filemap_to_import))
+                         .map(|rc| rc.clone())
+        };
+
+        match reusable_filemap {
+            Some(fm) => {
+                cstore::ImportedFileMap {
+                    original_start_pos: filemap_to_import.start_pos,
+                    original_end_pos: filemap_to_import.end_pos,
+                    translated_filemap: fm
+                }
+            }
+            None => {
+                // We can't reuse an existing FileMap, so allocate a new one
+                // containing the information we need.
+                let codemap::FileMap {
+                    name,
+                    start_pos,
+                    end_pos,
+                    lines,
+                    multibyte_chars,
+                    ..
+                } = filemap_to_import;
+
+                let source_length = (end_pos - start_pos).to_usize();
+
+                // Translate line-start positions and multibyte character
+                // position into frame of reference local to file.
+                // `CodeMap::new_imported_filemap()` will then translate those
+                // coordinates to their new global frame of reference when the
+                // offset of the FileMap is known.
+                let lines = lines.into_inner().map_in_place(|pos| pos - start_pos);
+                let multibyte_chars = multibyte_chars
+                    .into_inner()
+                    .map_in_place(|mbc|
+                        codemap::MultiByteChar {
+                            pos: mbc.pos + start_pos,
+                            bytes: mbc.bytes
+                        });
+
+                let local_version = local_codemap.new_imported_filemap(name,
+                                                                       source_length,
+                                                                       lines,
+                                                                       multibyte_chars);
+                cstore::ImportedFileMap {
+                    original_start_pos: start_pos,
+                    original_end_pos: end_pos,
+                    translated_filemap: local_version
+                }
+            }
+        }
+    }).collect();
+
+    return imported_filemaps;
+
+    fn are_equal_modulo_startpos(fm1: &codemap::FileMap,
+                                 fm2: &codemap::FileMap)
+                                 -> bool {
+        if fm1.name != fm2.name {
+            return false;
+        }
+
+        let lines1 = fm1.lines.borrow();
+        let lines2 = fm2.lines.borrow();
+
+        if lines1.len() != lines2.len() {
+            return false;
+        }
+
+        for (&line1, &line2) in lines1.iter().zip(lines2.iter()) {
+            if (line1 - fm1.start_pos) != (line2 - fm2.start_pos) {
+                return false;
+            }
+        }
+
+        let multibytes1 = fm1.multibyte_chars.borrow();
+        let multibytes2 = fm2.multibyte_chars.borrow();
+
+        if multibytes1.len() != multibytes2.len() {
+            return false;
+        }
+
+        for (mb1, mb2) in multibytes1.iter().zip(multibytes2.iter()) {
+            if (mb1.bytes != mb2.bytes) ||
+               ((mb1.pos - fm1.start_pos) != (mb2.pos - fm2.start_pos)) {
+                return false;
+            }
+        }
+
+        true
+    }
+}
index f5c4cce065955659fddcfcc17c6f0d4dee2d426e..ed5783c8dba661e4a1927964362abeb0b5e9a602 100644 (file)
@@ -175,14 +175,6 @@ pub fn get_provided_trait_methods<'tcx>(tcx: &ty::ctxt<'tcx>,
     decoder::get_provided_trait_methods(cstore.intr.clone(), &*cdata, def.node, tcx)
 }
 
-pub fn get_supertraits<'tcx>(tcx: &ty::ctxt<'tcx>,
-                             def: ast::DefId)
-                             -> Vec<Rc<ty::TraitRef<'tcx>>> {
-    let cstore = &tcx.sess.cstore;
-    let cdata = cstore.get_crate_data(def.krate);
-    decoder::get_supertraits(&*cdata, def.node, tcx)
-}
-
 pub fn get_type_name_if_impl(cstore: &cstore::CStore, def: ast::DefId)
                           -> Option<ast::Name> {
     let cdata = cstore.get_crate_data(def.krate);
@@ -238,6 +230,14 @@ pub fn get_predicates<'tcx>(tcx: &ty::ctxt<'tcx>, def: ast::DefId)
     decoder::get_predicates(&*cdata, def.node, tcx)
 }
 
+pub fn get_super_predicates<'tcx>(tcx: &ty::ctxt<'tcx>, def: ast::DefId)
+                                  -> ty::GenericPredicates<'tcx>
+{
+    let cstore = &tcx.sess.cstore;
+    let cdata = cstore.get_crate_data(def.krate);
+    decoder::get_super_predicates(&*cdata, def.node, tcx)
+}
+
 pub fn get_field_type<'tcx>(tcx: &ty::ctxt<'tcx>, class_id: ast::DefId,
                             def: ast::DefId) -> ty::TypeScheme<'tcx> {
     let cstore = &tcx.sess.cstore;
@@ -407,7 +407,7 @@ pub fn is_associated_type(cstore: &cstore::CStore, def: ast::DefId) -> bool {
     decoder::is_associated_type(&*cdata, def.node)
 }
 
-pub fn is_default_trait(cstore: &cstore::CStore, def: ast::DefId) -> bool {
-    let cdata = cstore.get_crate_data(def.krate);
-    decoder::is_default_trait(&*cdata, def.node)
+pub fn is_defaulted_trait(cstore: &cstore::CStore, trait_def_id: ast::DefId) -> bool {
+    let cdata = cstore.get_crate_data(trait_def_id.krate);
+    decoder::is_defaulted_trait(&*cdata, trait_def_id.node)
 }
index a3f7d57da67486b39a976a8289743612960ef5b4..47ec31c0f1ab7d0c26b7d366282cf54d368121b9 100644 (file)
 
 use std::cell::RefCell;
 use std::rc::Rc;
+use std::path::PathBuf;
 use flate::Bytes;
 use syntax::ast;
-use syntax::codemap::Span;
+use syntax::codemap;
 use syntax::parse::token::IdentInterner;
 
 // A map from external crate numbers (as decoded from some crate file) to
@@ -41,12 +42,24 @@ pub enum MetadataBlob {
     MetadataArchive(loader::ArchiveMetadata),
 }
 
+/// Holds information about a codemap::FileMap imported from another crate.
+/// See creader::import_codemap() for more information.
+pub struct ImportedFileMap {
+    /// This FileMap's byte-offset within the codemap of its original crate
+    pub original_start_pos: codemap::BytePos,
+    /// The end of this FileMap within the codemap of its original crate
+    pub original_end_pos: codemap::BytePos,
+    /// The imported FileMap's representation within the local codemap
+    pub translated_filemap: Rc<codemap::FileMap>
+}
+
 pub struct crate_metadata {
     pub name: String,
     pub data: MetadataBlob,
     pub cnum_map: cnum_map,
     pub cnum: ast::CrateNum,
-    pub span: Span,
+    pub codemap_import_info: Vec<ImportedFileMap>,
+    pub span: codemap::Span,
 }
 
 #[derive(Copy, Debug, PartialEq, Clone)]
@@ -66,8 +79,8 @@ pub enum NativeLibraryKind {
 // must be non-None.
 #[derive(PartialEq, Clone)]
 pub struct CrateSource {
-    pub dylib: Option<(Path, PathKind)>,
-    pub rlib: Option<(Path, PathKind)>,
+    pub dylib: Option<(PathBuf, PathKind)>,
+    pub rlib: Option<(PathBuf, PathKind)>,
     pub cnum: ast::CrateNum,
 }
 
@@ -160,7 +173,7 @@ pub fn reset(&self) {
     // topological sort of all crates putting the leaves at the right-most
     // positions.
     pub fn get_used_crates(&self, prefer: LinkagePreference)
-                           -> Vec<(ast::CrateNum, Option<Path>)> {
+                           -> Vec<(ast::CrateNum, Option<PathBuf>)> {
         let mut ordering = Vec::new();
         fn visit(cstore: &CStore, cnum: ast::CrateNum,
                  ordering: &mut Vec<ast::CrateNum>) {
index 251c5e6eac70ebe7df5530dca754089ebb442a0b..dbbc17c018a2fc92b2b0c235db4750ff8db44b93 100644 (file)
@@ -22,9 +22,8 @@
 use metadata::csearch;
 use metadata::cstore;
 use metadata::tydecode::{parse_ty_data, parse_region_data, parse_def_id,
-                         parse_type_param_def_data, parse_bounds_data,
-                         parse_bare_fn_ty_data, parse_trait_ref_data,
-                         parse_predicate_data};
+                         parse_type_param_def_data, parse_bare_fn_ty_data,
+                         parse_trait_ref_data, parse_predicate_data};
 use middle::def;
 use middle::lang_items;
 use middle::subst;
@@ -34,9 +33,9 @@
 
 use std::collections::HashMap;
 use std::hash::{self, Hash, SipHasher};
-use std::num::FromPrimitive;
-use std::num::Int;
-use std::old_io;
+use std::io::prelude::*;
+use std::io;
+use std::num::{FromPrimitive, Int};
 use std::rc::Rc;
 use std::slice::bytes;
 use std::str;
@@ -260,18 +259,6 @@ fn item_trait_ref<'tcx>(doc: rbml::Doc, tcx: &ty::ctxt<'tcx>, cdata: Cmd)
     doc_trait_ref(tp, tcx, cdata)
 }
 
-fn doc_bounds<'tcx>(doc: rbml::Doc, tcx: &ty::ctxt<'tcx>, cdata: Cmd)
-                    -> ty::ParamBounds<'tcx> {
-    parse_bounds_data(doc.data, cdata.cnum, doc.start, tcx,
-                      |_, did| translate_def_id(cdata, did))
-}
-
-fn trait_def_bounds<'tcx>(doc: rbml::Doc, tcx: &ty::ctxt<'tcx>, cdata: Cmd)
-                          -> ty::ParamBounds<'tcx> {
-    let d = reader::get_doc(doc, tag_trait_def_bounds);
-    doc_bounds(d, tcx, cdata)
-}
-
 fn enum_variant_ids(item: rbml::Doc, cdata: Cmd) -> Vec<ast::DefId> {
     let mut ids: Vec<ast::DefId> = Vec::new();
     let v = tag_items_data_item_variant;
@@ -406,7 +393,6 @@ pub fn get_trait_def<'tcx>(cdata: Cmd,
 {
     let item_doc = lookup_item(item_id, cdata.data());
     let generics = doc_generics(item_doc, tcx, cdata, tag_item_generics);
-    let bounds = trait_def_bounds(item_doc, tcx, cdata);
     let unsafety = parse_unsafety(item_doc);
     let associated_type_names = parse_associated_type_names(item_doc);
     let paren_sugar = parse_paren_sugar(item_doc);
@@ -415,7 +401,6 @@ pub fn get_trait_def<'tcx>(cdata: Cmd,
         paren_sugar: paren_sugar,
         unsafety: unsafety,
         generics: generics,
-        bounds: bounds,
         trait_ref: item_trait_ref(item_doc, tcx, cdata),
         associated_type_names: associated_type_names,
     }
@@ -430,6 +415,15 @@ pub fn get_predicates<'tcx>(cdata: Cmd,
     doc_predicates(item_doc, tcx, cdata, tag_item_generics)
 }
 
+pub fn get_super_predicates<'tcx>(cdata: Cmd,
+                                  item_id: ast::NodeId,
+                                  tcx: &ty::ctxt<'tcx>)
+                                  -> ty::GenericPredicates<'tcx>
+{
+    let item_doc = lookup_item(item_id, cdata.data());
+    doc_predicates(item_doc, tcx, cdata, tag_item_super_predicates)
+}
+
 pub fn get_type<'tcx>(cdata: Cmd, id: ast::NodeId, tcx: &ty::ctxt<'tcx>)
                       -> ty::TypeScheme<'tcx>
 {
@@ -783,7 +777,7 @@ pub fn get_enum_variants<'tcx>(intr: Rc<IdentInterner>, cdata: Cmd, id: ast::Nod
             _         => { /* empty */ }
         }
         let old_disr_val = disr_val;
-        disr_val += 1;
+        disr_val = disr_val.wrapping_add(1);
         Rc::new(ty::VariantInfo {
             args: arg_tys,
             arg_names: arg_names,
@@ -971,24 +965,6 @@ pub fn get_provided_trait_methods<'tcx>(intr: Rc<IdentInterner>,
     return result;
 }
 
-/// Returns the supertraits of the given trait.
-pub fn get_supertraits<'tcx>(cdata: Cmd, id: ast::NodeId, tcx: &ty::ctxt<'tcx>)
-                             -> Vec<Rc<ty::TraitRef<'tcx>>> {
-    let mut results = Vec::new();
-    let item_doc = lookup_item(id, cdata.data());
-    reader::tagged_docs(item_doc, tag_item_super_trait_ref, |trait_doc| {
-        // NB. Only reads the ones that *aren't* builtin-bounds. See also
-        // get_trait_def() for collecting the builtin bounds.
-        // FIXME(#8559): The builtin bounds shouldn't be encoded in the first place.
-        let trait_ref = doc_trait_ref(trait_doc, tcx, cdata);
-        if tcx.lang_items.to_builtin_kind(trait_ref.def_id).is_none() {
-            results.push(trait_ref);
-        }
-        true
-    });
-    return results;
-}
-
 pub fn get_type_name_if_impl(cdata: Cmd,
                              node_id: ast::NodeId) -> Option<ast::Name> {
     let item = lookup_item(node_id, cdata.data());
@@ -1191,7 +1167,7 @@ fn get_attributes(md: rbml::Doc) -> Vec<ast::Attribute> {
 }
 
 fn list_crate_attributes(md: rbml::Doc, hash: &Svh,
-                         out: &mut old_io::Writer) -> old_io::IoResult<()> {
+                         out: &mut io::Write) -> io::Result<()> {
     try!(write!(out, "=Crate Attributes ({})=\n", *hash));
 
     let r = get_attributes(md);
@@ -1236,7 +1212,7 @@ fn docstr(doc: rbml::Doc, tag_: uint) -> String {
     return deps;
 }
 
-fn list_crate_deps(data: &[u8], out: &mut old_io::Writer) -> old_io::IoResult<()> {
+fn list_crate_deps(data: &[u8], out: &mut io::Write) -> io::Result<()> {
     try!(write!(out, "=External Dependencies=\n"));
     for dep in &get_crate_deps(data) {
         try!(write!(out, "{} {}-{}\n", dep.cnum, dep.name, dep.hash));
@@ -1275,7 +1251,7 @@ pub fn get_crate_name(data: &[u8]) -> String {
     maybe_get_crate_name(data).expect("no crate name in crate")
 }
 
-pub fn list_crate_metadata(bytes: &[u8], out: &mut old_io::Writer) -> old_io::IoResult<()> {
+pub fn list_crate_metadata(bytes: &[u8], out: &mut io::Write) -> io::Result<()> {
     let hash = get_crate_hash(bytes);
     let md = rbml::Doc::new(bytes);
     try!(list_crate_attributes(md, &hash, out));
@@ -1561,11 +1537,25 @@ pub fn is_associated_type(cdata: Cmd, id: ast::NodeId) -> bool {
     }
 }
 
+pub fn is_defaulted_trait<'tcx>(cdata: Cmd, trait_id: ast::NodeId) -> bool {
+    let trait_doc = lookup_item(trait_id, cdata.data());
+    assert!(item_family(trait_doc) == Family::Trait);
+    let defaulted_doc = reader::get_doc(trait_doc, tag_defaulted_trait);
+    reader::doc_as_u8(defaulted_doc) != 0
+}
 
-pub fn is_default_trait<'tcx>(cdata: Cmd, id: ast::NodeId) -> bool {
-    let item_doc = lookup_item(id, cdata.data());
-    match item_family(item_doc) {
-        Family::DefaultImpl => true,
-        _ => false
-    }
+pub fn get_imported_filemaps(metadata: &[u8]) -> Vec<codemap::FileMap> {
+    let crate_doc = rbml::Doc::new(metadata);
+    let cm_doc = reader::get_doc(crate_doc, tag_codemap);
+
+    let mut filemaps = vec![];
+
+    reader::tagged_docs(cm_doc, tag_codemap_filemap, |filemap_doc| {
+        let mut decoder = reader::Decoder::new(filemap_doc);
+        let filemap: codemap::FileMap = Decodable::decode(&mut decoder).unwrap();
+        filemaps.push(filemap);
+        true
+    });
+
+    return filemaps;
 }
index ee2745ca66bc59980a675bd7dd7da2f24129d447..08263eb8e6a03978478147d8ed97b3fd6c4f138a 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
@@ -46,7 +46,7 @@
 use syntax::visit::Visitor;
 use syntax::visit;
 use syntax;
-use rbml::writer;
+use rbml::writer::Encoder;
 use rbml::io::SeekableMemWriter;
 
 /// A borrowed version of `ast::InlinedItem`.
@@ -57,8 +57,6 @@ pub enum InlinedItemRef<'a> {
     IIForeignRef(&'a ast::ForeignItem)
 }
 
-pub type Encoder<'a> = writer::Encoder<'a, SeekableMemWriter>;
-
 pub type EncodeInlinedItem<'a> =
     Box<FnMut(&EncodeContext, &mut Encoder, InlinedItemRef) + 'a>;
 
@@ -115,15 +113,13 @@ fn encode_trait_ref<'a, 'tcx>(rbml_w: &mut Encoder,
     };
 
     rbml_w.start_tag(tag);
-    tyencode::enc_trait_ref(rbml_w.writer, ty_str_ctxt, trait_ref);
+    tyencode::enc_trait_ref(rbml_w, ty_str_ctxt, trait_ref);
     rbml_w.end_tag();
 }
 
 // Item info table encoding
 fn encode_family(rbml_w: &mut Encoder, c: char) {
-    rbml_w.start_tag(tag_items_data_item_family);
-    rbml_w.writer.write_all(&[c as u8]);
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_u8(tag_items_data_item_family, c as u8);
 }
 
 pub fn def_to_string(did: DefId) -> String {
@@ -157,14 +153,9 @@ fn encode_bounds_and_type<'a, 'tcx>(rbml_w: &mut Encoder,
 }
 
 fn encode_variant_id(rbml_w: &mut Encoder, vid: DefId) {
-    rbml_w.start_tag(tag_items_data_item_variant);
     let s = def_to_string(vid);
-    rbml_w.writer.write_all(s.as_bytes());
-    rbml_w.end_tag();
-
-    rbml_w.start_tag(tag_mod_child);
-    rbml_w.wr_str(&s[..]);
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_items_data_item_variant, &s[..]);
+    rbml_w.wr_tagged_str(tag_mod_child, &s[..]);
 }
 
 pub fn write_closure_type<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
@@ -176,7 +167,7 @@ pub fn write_closure_type<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
         tcx: ecx.tcx,
         abbrevs: &ecx.type_abbrevs
     };
-    tyencode::enc_closure_ty(rbml_w.writer, ty_str_ctxt, closure_type);
+    tyencode::enc_closure_ty(rbml_w, ty_str_ctxt, closure_type);
 }
 
 pub fn write_type<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
@@ -188,7 +179,7 @@ pub fn write_type<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
         tcx: ecx.tcx,
         abbrevs: &ecx.type_abbrevs
     };
-    tyencode::enc_ty(rbml_w.writer, ty_str_ctxt, typ);
+    tyencode::enc_ty(rbml_w, ty_str_ctxt, typ);
 }
 
 pub fn write_trait_ref<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
@@ -200,7 +191,7 @@ pub fn write_trait_ref<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
         tcx: ecx.tcx,
         abbrevs: &ecx.type_abbrevs
     };
-    tyencode::enc_trait_ref(rbml_w.writer, ty_str_ctxt, trait_ref);
+    tyencode::enc_trait_ref(rbml_w, ty_str_ctxt, trait_ref);
 }
 
 pub fn write_region(ecx: &EncodeContext,
@@ -212,22 +203,7 @@ pub fn write_region(ecx: &EncodeContext,
         tcx: ecx.tcx,
         abbrevs: &ecx.type_abbrevs
     };
-    tyencode::enc_region(rbml_w.writer, ty_str_ctxt, r);
-}
-
-fn encode_bounds<'a, 'tcx>(rbml_w: &mut Encoder,
-                           ecx: &EncodeContext<'a, 'tcx>,
-                           bounds: &ty::ParamBounds<'tcx>,
-                           tag: uint) {
-    rbml_w.start_tag(tag);
-
-    let ty_str_ctxt = &tyencode::ctxt { diag: ecx.diag,
-                                        ds: def_to_string,
-                                        tcx: ecx.tcx,
-                                        abbrevs: &ecx.type_abbrevs };
-    tyencode::enc_bounds(rbml_w.writer, ty_str_ctxt, bounds);
-
-    rbml_w.end_tag();
+    tyencode::enc_region(rbml_w, ty_str_ctxt, r);
 }
 
 fn encode_type<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
@@ -257,7 +233,7 @@ fn encode_method_fty<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
         tcx: ecx.tcx,
         abbrevs: &ecx.type_abbrevs
     };
-    tyencode::enc_bare_fn_ty(rbml_w.writer, ty_str_ctxt, typ);
+    tyencode::enc_bare_fn_ty(rbml_w, ty_str_ctxt, typ);
 
     rbml_w.end_tag();
 }
@@ -265,34 +241,26 @@ fn encode_method_fty<'a, 'tcx>(ecx: &EncodeContext<'a, 'tcx>,
 fn encode_symbol(ecx: &EncodeContext,
                  rbml_w: &mut Encoder,
                  id: NodeId) {
-    rbml_w.start_tag(tag_items_data_item_symbol);
     match ecx.item_symbols.borrow().get(&id) {
         Some(x) => {
             debug!("encode_symbol(id={}, str={})", id, *x);
-            rbml_w.writer.write_all(x.as_bytes());
+            rbml_w.wr_tagged_str(tag_items_data_item_symbol, x);
         }
         None => {
             ecx.diag.handler().bug(
                 &format!("encode_symbol: id not found {}", id));
         }
     }
-    rbml_w.end_tag();
 }
 
 fn encode_disr_val(_: &EncodeContext,
                    rbml_w: &mut Encoder,
                    disr_val: ty::Disr) {
-    rbml_w.start_tag(tag_disr_val);
-    let s = disr_val.to_string();
-    rbml_w.writer.write_all(s.as_bytes());
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_disr_val, &disr_val.to_string());
 }
 
 fn encode_parent_item(rbml_w: &mut Encoder, id: DefId) {
-    rbml_w.start_tag(tag_items_data_parent_item);
-    let s = def_to_string(id);
-    rbml_w.writer.write_all(s.as_bytes());
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_items_data_parent_item, &def_to_string(id));
 }
 
 fn encode_struct_fields(rbml_w: &mut Encoder,
@@ -307,10 +275,7 @@ fn encode_struct_fields(rbml_w: &mut Encoder,
         }
         encode_struct_field_family(rbml_w, f.vis);
         encode_def_id(rbml_w, f.id);
-        rbml_w.start_tag(tag_item_field_origin);
-        let s = def_to_string(origin);
-        rbml_w.writer.write_all(s.as_bytes());
-        rbml_w.end_tag();
+        rbml_w.wr_tagged_str(tag_item_field_origin, &def_to_string(origin));
         rbml_w.end_tag();
     }
 }
@@ -330,7 +295,7 @@ fn encode_enum_variant_info(ecx: &EncodeContext,
         let def_id = local_def(variant.node.id);
         index.push(entry {
             val: variant.node.id as i64,
-            pos: rbml_w.writer.tell().unwrap(),
+            pos: rbml_w.mark_stable_position(),
         });
         rbml_w.start_tag(tag_items_data_item);
         encode_def_id(rbml_w, def_id);
@@ -367,7 +332,7 @@ fn encode_enum_variant_info(ecx: &EncodeContext,
 
         ecx.tcx.map.with_path(variant.node.id, |path| encode_path(rbml_w, path));
         rbml_w.end_tag();
-        disr_val += 1;
+        disr_val = disr_val.wrapping_add(1);
         i += 1;
     }
 }
@@ -393,14 +358,11 @@ fn encode_reexported_static_method(rbml_w: &mut Encoder,
     debug!("(encode reexported static method) {}::{}",
             exp.name, token::get_name(method_name));
     rbml_w.start_tag(tag_items_data_item_reexport);
-    rbml_w.start_tag(tag_items_data_item_reexport_def_id);
-    rbml_w.wr_str(&def_to_string(method_def_id));
-    rbml_w.end_tag();
-    rbml_w.start_tag(tag_items_data_item_reexport_name);
-    rbml_w.wr_str(&format!("{}::{}",
-                          exp.name,
-                          token::get_name(method_name)));
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_items_data_item_reexport_def_id,
+                         &def_to_string(method_def_id));
+    rbml_w.wr_tagged_str(tag_items_data_item_reexport_name,
+                         &format!("{}::{}", exp.name,
+                                            token::get_name(method_name)));
     rbml_w.end_tag();
 }
 
@@ -536,12 +498,10 @@ fn encode_reexports(ecx: &EncodeContext,
                        exp.def_id.node,
                        id);
                 rbml_w.start_tag(tag_items_data_item_reexport);
-                rbml_w.start_tag(tag_items_data_item_reexport_def_id);
-                rbml_w.wr_str(&def_to_string(exp.def_id));
-                rbml_w.end_tag();
-                rbml_w.start_tag(tag_items_data_item_reexport_name);
-                rbml_w.wr_str(exp.name.as_str());
-                rbml_w.end_tag();
+                rbml_w.wr_tagged_str(tag_items_data_item_reexport_def_id,
+                                     &def_to_string(exp.def_id));
+                rbml_w.wr_tagged_str(tag_items_data_item_reexport_name,
+                                     exp.name.as_str());
                 rbml_w.end_tag();
                 encode_reexported_static_methods(ecx, rbml_w, path.clone(), exp);
             }
@@ -569,15 +529,12 @@ fn encode_info_for_mod(ecx: &EncodeContext,
 
     // Encode info about all the module children.
     for item in &md.items {
-        rbml_w.start_tag(tag_mod_child);
-        rbml_w.wr_str(&def_to_string(local_def(item.id)));
-        rbml_w.end_tag();
+        rbml_w.wr_tagged_str(tag_mod_child,
+                             &def_to_string(local_def(item.id)));
 
         each_auxiliary_node_id(&**item, |auxiliary_node_id| {
-            rbml_w.start_tag(tag_mod_child);
-            rbml_w.wr_str(&def_to_string(local_def(
-                        auxiliary_node_id)));
-            rbml_w.end_tag();
+            rbml_w.wr_tagged_str(tag_mod_child,
+                                 &def_to_string(local_def(auxiliary_node_id)));
             true
         });
 
@@ -587,9 +544,8 @@ fn encode_info_for_mod(ecx: &EncodeContext,
                    token::get_ident(ident),
                    did, ecx.tcx.map.node_to_string(did));
 
-            rbml_w.start_tag(tag_mod_impl);
-            rbml_w.wr_str(&def_to_string(local_def(did)));
-            rbml_w.end_tag();
+            rbml_w.wr_tagged_str(tag_mod_impl,
+                                 &def_to_string(local_def(did)));
         }
     }
 
@@ -618,67 +574,56 @@ fn encode_struct_field_family(rbml_w: &mut Encoder,
 }
 
 fn encode_visibility(rbml_w: &mut Encoder, visibility: ast::Visibility) {
-    rbml_w.start_tag(tag_items_data_item_visibility);
     let ch = match visibility {
         ast::Public => 'y',
         ast::Inherited => 'i',
     };
-    rbml_w.wr_str(&ch.to_string());
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_u8(tag_items_data_item_visibility, ch as u8);
 }
 
 fn encode_explicit_self(rbml_w: &mut Encoder,
                         explicit_self: &ty::ExplicitSelfCategory) {
-    rbml_w.start_tag(tag_item_trait_method_explicit_self);
+    let tag = tag_item_trait_method_explicit_self;
 
     // Encode the base self type.
     match *explicit_self {
         ty::StaticExplicitSelfCategory => {
-            rbml_w.writer.write_all(&[ 's' as u8 ]);
+            rbml_w.wr_tagged_bytes(tag, &['s' as u8]);
         }
         ty::ByValueExplicitSelfCategory => {
-            rbml_w.writer.write_all(&[ 'v' as u8 ]);
+            rbml_w.wr_tagged_bytes(tag, &['v' as u8]);
         }
         ty::ByBoxExplicitSelfCategory => {
-            rbml_w.writer.write_all(&[ '~' as u8 ]);
+            rbml_w.wr_tagged_bytes(tag, &['~' as u8]);
         }
         ty::ByReferenceExplicitSelfCategory(_, m) => {
             // FIXME(#4846) encode custom lifetime
-            rbml_w.writer.write_all(&['&' as u8]);
-            encode_mutability(rbml_w, m);
+            let ch = encode_mutability(m);
+            rbml_w.wr_tagged_bytes(tag, &['&' as u8, ch]);
         }
     }
 
-    rbml_w.end_tag();
-
-    fn encode_mutability(rbml_w: &mut Encoder,
-                         m: ast::Mutability) {
+    fn encode_mutability(m: ast::Mutability) -> u8 {
         match m {
-            ast::MutImmutable => { rbml_w.writer.write_all(&[ 'i' as u8 ]); }
-            ast::MutMutable => { rbml_w.writer.write_all(&[ 'm' as u8 ]); }
+            ast::MutImmutable => 'i' as u8,
+            ast::MutMutable => 'm' as u8,
         }
     }
 }
 
 fn encode_item_sort(rbml_w: &mut Encoder, sort: char) {
-    rbml_w.start_tag(tag_item_trait_item_sort);
-    rbml_w.writer.write_all(&[ sort as u8 ]);
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_u8(tag_item_trait_item_sort, sort as u8);
 }
 
 fn encode_parent_sort(rbml_w: &mut Encoder, sort: char) {
-    rbml_w.start_tag(tag_item_trait_parent_sort);
-    rbml_w.writer.write_all(&[ sort as u8 ]);
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_u8(tag_item_trait_parent_sort, sort as u8);
 }
 
 fn encode_provided_source(rbml_w: &mut Encoder,
                           source_opt: Option<DefId>) {
     if let Some(source) = source_opt {
-        rbml_w.start_tag(tag_item_method_provided_source);
-        let s = def_to_string(source);
-        rbml_w.writer.write_all(s.as_bytes());
-        rbml_w.end_tag();
+        rbml_w.wr_tagged_str(tag_item_method_provided_source,
+                             &def_to_string(source));
     }
 }
 
@@ -697,10 +642,11 @@ fn encode_info_for_struct(ecx: &EncodeContext,
         let nm = field.name;
         let id = field.id.node;
 
-        index.push(entry {val: id as i64, pos: rbml_w.writer.tell().unwrap()});
+        let pos = rbml_w.mark_stable_position();
+        index.push(entry {val: id as i64, pos: pos});
         global_index.push(entry {
             val: id as i64,
-            pos: rbml_w.writer.tell().unwrap(),
+            pos: pos,
         });
         rbml_w.start_tag(tag_items_data_item);
         debug!("encode_info_for_struct: doing {} {}",
@@ -726,7 +672,7 @@ fn encode_info_for_struct_ctor(ecx: &EncodeContext,
                                struct_id: NodeId) {
     index.push(entry {
         val: ctor_id as i64,
-        pos: rbml_w.writer.tell().unwrap(),
+        pos: rbml_w.mark_stable_position(),
     });
 
     rbml_w.start_tag(tag_items_data_item);
@@ -747,8 +693,7 @@ fn encode_info_for_struct_ctor(ecx: &EncodeContext,
     // indicate that this is a tuple struct ctor, because downstream users will normally want
     // the tuple struct definition, but without this there is no way for them to tell that
     // they actually have a ctor rather than a normal function
-    rbml_w.start_tag(tag_items_data_item_is_tuple_struct_ctor);
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_bytes(tag_items_data_item_is_tuple_struct_ctor, &[]);
 
     rbml_w.end_tag();
 }
@@ -768,9 +713,10 @@ fn encode_generics<'a, 'tcx>(rbml_w: &mut Encoder,
         tcx: ecx.tcx,
         abbrevs: &ecx.type_abbrevs
     };
+
     for param in generics.types.iter() {
         rbml_w.start_tag(tag_type_param_def);
-        tyencode::enc_type_param_def(rbml_w.writer, ty_str_ctxt, param);
+        tyencode::enc_type_param_def(rbml_w, ty_str_ctxt, param);
         rbml_w.end_tag();
     }
 
@@ -798,18 +744,42 @@ fn encode_generics<'a, 'tcx>(rbml_w: &mut Encoder,
         rbml_w.end_tag();
     }
 
+    encode_predicates_in_current_doc(rbml_w, ecx, predicates);
+
+    rbml_w.end_tag();
+}
+
+fn encode_predicates_in_current_doc<'a,'tcx>(rbml_w: &mut Encoder,
+                                             ecx: &EncodeContext<'a,'tcx>,
+                                             predicates: &ty::GenericPredicates<'tcx>)
+{
+    let ty_str_ctxt = &tyencode::ctxt {
+        diag: ecx.diag,
+        ds: def_to_string,
+        tcx: ecx.tcx,
+        abbrevs: &ecx.type_abbrevs
+    };
+
     for (space, _, predicate) in predicates.predicates.iter_enumerated() {
         rbml_w.start_tag(tag_predicate);
 
         rbml_w.wr_tagged_u8(tag_predicate_space, space as u8);
 
         rbml_w.start_tag(tag_predicate_data);
-        tyencode::enc_predicate(rbml_w.writer, ty_str_ctxt, predicate);
+        tyencode::enc_predicate(rbml_w, ty_str_ctxt, predicate);
         rbml_w.end_tag();
 
         rbml_w.end_tag();
     }
+}
 
+fn encode_predicates<'a,'tcx>(rbml_w: &mut Encoder,
+                              ecx: &EncodeContext<'a,'tcx>,
+                              predicates: &ty::GenericPredicates<'tcx>,
+                              tag: uint)
+{
+    rbml_w.start_tag(tag);
+    encode_predicates_in_current_doc(rbml_w, ecx, predicates);
     rbml_w.end_tag();
 }
 
@@ -919,12 +889,13 @@ fn encode_method_argument_names(rbml_w: &mut Encoder,
                                 decl: &ast::FnDecl) {
     rbml_w.start_tag(tag_method_argument_names);
     for arg in &decl.inputs {
-        rbml_w.start_tag(tag_method_argument_name);
+        let tag = tag_method_argument_name;
         if let ast::PatIdent(_, ref path1, _) = arg.pat.node {
             let name = token::get_ident(path1.node);
-            rbml_w.writer.write_all(name.as_bytes());
+            rbml_w.wr_tagged_bytes(tag, name.as_bytes());
+        } else {
+            rbml_w.wr_tagged_bytes(tag, &[]);
         }
-        rbml_w.end_tag();
     }
     rbml_w.end_tag();
 }
@@ -1002,11 +973,11 @@ fn encode_info_for_item(ecx: &EncodeContext,
                         vis: ast::Visibility) {
     let tcx = ecx.tcx;
 
-    fn add_to_index(item: &ast::Item, rbml_w: &Encoder,
+    fn add_to_index(item: &ast::Item, rbml_w: &mut Encoder,
                     index: &mut Vec<entry<i64>>) {
         index.push(entry {
             val: item.id as i64,
-            pos: rbml_w.writer.tell().unwrap(),
+            pos: rbml_w.mark_stable_position(),
         });
     }
 
@@ -1091,9 +1062,8 @@ fn add_to_index(item: &ast::Item, rbml_w: &Encoder,
 
         // Encode all the items in this module.
         for foreign_item in &fm.items {
-            rbml_w.start_tag(tag_mod_child);
-            rbml_w.wr_str(&def_to_string(local_def(foreign_item.id)));
-            rbml_w.end_tag();
+            rbml_w.wr_tagged_str(tag_mod_child,
+                                 &def_to_string(local_def(foreign_item.id)));
         }
         encode_visibility(rbml_w, vis);
         encode_stability(rbml_w, stab);
@@ -1263,7 +1233,7 @@ fn add_to_index(item: &ast::Item, rbml_w: &Encoder,
 
             index.push(entry {
                 val: trait_item_def_id.def_id().node as i64,
-                pos: rbml_w.writer.tell().unwrap(),
+                pos: rbml_w.mark_stable_position(),
             });
 
             let trait_item_type =
@@ -1318,8 +1288,11 @@ fn add_to_index(item: &ast::Item, rbml_w: &Encoder,
         let trait_predicates = ty::lookup_predicates(tcx, def_id);
         encode_unsafety(rbml_w, trait_def.unsafety);
         encode_paren_sugar(rbml_w, trait_def.paren_sugar);
+        encode_defaulted(rbml_w, ty::trait_has_default_impl(tcx, def_id));
         encode_associated_type_names(rbml_w, &trait_def.associated_type_names);
         encode_generics(rbml_w, ecx, &trait_def.generics, &trait_predicates, tag_item_generics);
+        encode_predicates(rbml_w, ecx, &ty::lookup_super_predicates(tcx, def_id),
+                          tag_item_super_predicates);
         encode_trait_ref(rbml_w, ecx, &*trait_def.trait_ref, tag_item_trait_ref);
         encode_name(rbml_w, item.ident.name);
         encode_attributes(rbml_w, &item.attrs);
@@ -1339,14 +1312,11 @@ fn add_to_index(item: &ast::Item, rbml_w: &Encoder,
             }
             rbml_w.end_tag();
 
-            rbml_w.start_tag(tag_mod_child);
-            rbml_w.wr_str(&def_to_string(method_def_id.def_id()));
-            rbml_w.end_tag();
+            rbml_w.wr_tagged_str(tag_mod_child,
+                                 &def_to_string(method_def_id.def_id()));
         }
         encode_path(rbml_w, path.clone());
 
-        encode_bounds(rbml_w, ecx, &trait_def.bounds, tag_trait_def_bounds);
-
         // Encode the implementations of this trait.
         encode_extension_implementations(ecx, rbml_w, def_id);
 
@@ -1362,7 +1332,7 @@ fn add_to_index(item: &ast::Item, rbml_w: &Encoder,
 
             index.push(entry {
                 val: item_def_id.def_id().node as i64,
-                pos: rbml_w.writer.tell().unwrap(),
+                pos: rbml_w.mark_stable_position(),
             });
 
             rbml_w.start_tag(tag_items_data_item);
@@ -1467,7 +1437,7 @@ fn encode_info_for_foreign_item(ecx: &EncodeContext,
                                 abi: abi::Abi) {
     index.push(entry {
         val: nitem.id as i64,
-        pos: rbml_w.writer.tell().unwrap(),
+        pos: rbml_w.mark_stable_position(),
     });
 
     rbml_w.start_tag(tag_items_data_item);
@@ -1567,7 +1537,7 @@ fn encode_info_for_items(ecx: &EncodeContext,
     rbml_w.start_tag(tag_items_data);
     index.push(entry {
         val: ast::CRATE_NODE_ID as i64,
-        pos: rbml_w.writer.tell().unwrap(),
+        pos: rbml_w.mark_stable_position(),
     });
     encode_info_for_mod(ecx,
                         rbml_w,
@@ -1607,7 +1577,7 @@ fn encode_index<T, F>(rbml_w: &mut Encoder, index: Vec<entry<T>>, mut write_fn:
     let mut bucket_locs = Vec::new();
     rbml_w.start_tag(tag_index_buckets);
     for bucket in &buckets {
-        bucket_locs.push(rbml_w.writer.tell().unwrap());
+        bucket_locs.push(rbml_w.mark_stable_position());
         rbml_w.start_tag(tag_index_buckets_bucket);
         for elt in bucket {
             rbml_w.start_tag(tag_index_buckets_bucket_elt);
@@ -1642,21 +1612,15 @@ fn encode_meta_item(rbml_w: &mut Encoder, mi: &ast::MetaItem) {
     match mi.node {
       ast::MetaWord(ref name) => {
         rbml_w.start_tag(tag_meta_item_word);
-        rbml_w.start_tag(tag_meta_item_name);
-        rbml_w.writer.write_all(name.as_bytes());
-        rbml_w.end_tag();
+        rbml_w.wr_tagged_str(tag_meta_item_name, name);
         rbml_w.end_tag();
       }
       ast::MetaNameValue(ref name, ref value) => {
         match value.node {
           ast::LitStr(ref value, _) => {
             rbml_w.start_tag(tag_meta_item_name_value);
-            rbml_w.start_tag(tag_meta_item_name);
-            rbml_w.writer.write_all(name.as_bytes());
-            rbml_w.end_tag();
-            rbml_w.start_tag(tag_meta_item_value);
-            rbml_w.writer.write_all(value.as_bytes());
-            rbml_w.end_tag();
+            rbml_w.wr_tagged_str(tag_meta_item_name, name);
+            rbml_w.wr_tagged_str(tag_meta_item_value, value);
             rbml_w.end_tag();
           }
           _ => {/* FIXME (#623): encode other variants */ }
@@ -1664,9 +1628,7 @@ fn encode_meta_item(rbml_w: &mut Encoder, mi: &ast::MetaItem) {
       }
       ast::MetaList(ref name, ref items) => {
         rbml_w.start_tag(tag_meta_item_list);
-        rbml_w.start_tag(tag_meta_item_name);
-        rbml_w.writer.write_all(name.as_bytes());
-        rbml_w.end_tag();
+        rbml_w.wr_tagged_str(tag_meta_item_name, name);
         for inner_item in items {
             encode_meta_item(rbml_w, &**inner_item);
         }
@@ -1699,6 +1661,11 @@ fn encode_paren_sugar(rbml_w: &mut Encoder, paren_sugar: bool) {
     rbml_w.wr_tagged_u8(tag_paren_sugar, byte);
 }
 
+fn encode_defaulted(rbml_w: &mut Encoder, is_defaulted: bool) {
+    let byte: u8 = if is_defaulted {1} else {0};
+    rbml_w.wr_tagged_u8(tag_defaulted_trait, byte);
+}
+
 fn encode_associated_type_names(rbml_w: &mut Encoder, names: &[ast::Name]) {
     rbml_w.start_tag(tag_associated_type_names);
     for &name in names {
@@ -1760,22 +1727,9 @@ fn encode_lang_items(ecx: &EncodeContext, rbml_w: &mut Encoder) {
         if let Some(id) = def_id {
             if id.krate == ast::LOCAL_CRATE {
                 rbml_w.start_tag(tag_lang_items_item);
-
-                rbml_w.start_tag(tag_lang_items_item_id);
-                {
-                    let wr: &mut SeekableMemWriter = rbml_w.writer;
-                    wr.write_be_u32(i as u32);
-                }
-                rbml_w.end_tag();   // tag_lang_items_item_id
-
-                rbml_w.start_tag(tag_lang_items_item_node_id);
-                {
-                    let wr: &mut SeekableMemWriter = rbml_w.writer;
-                    wr.write_be_u32(id.node as u32);
-                }
-                rbml_w.end_tag();   // tag_lang_items_item_node_id
-
-                rbml_w.end_tag();   // tag_lang_items_item
+                rbml_w.wr_tagged_u32(tag_lang_items_item_id, i as u32);
+                rbml_w.wr_tagged_u32(tag_lang_items_item_node_id, id.node as u32);
+                rbml_w.end_tag();
             }
         }
     }
@@ -1796,15 +1750,8 @@ fn encode_native_libraries(ecx: &EncodeContext, rbml_w: &mut Encoder) {
             cstore::NativeStatic => {} // these libraries are not propagated
             cstore::NativeFramework | cstore::NativeUnknown => {
                 rbml_w.start_tag(tag_native_libraries_lib);
-
-                rbml_w.start_tag(tag_native_libraries_kind);
-                rbml_w.writer.write_be_u32(kind as u32);
-                rbml_w.end_tag();
-
-                rbml_w.start_tag(tag_native_libraries_name);
-                rbml_w.writer.write_all(lib.as_bytes());
-                rbml_w.end_tag();
-
+                rbml_w.wr_tagged_u32(tag_native_libraries_kind, kind as u32);
+                rbml_w.wr_tagged_str(tag_native_libraries_name, lib);
                 rbml_w.end_tag();
             }
         }
@@ -1820,6 +1767,28 @@ fn encode_plugin_registrar_fn(ecx: &EncodeContext, rbml_w: &mut Encoder) {
     }
 }
 
+fn encode_codemap(ecx: &EncodeContext, rbml_w: &mut Encoder) {
+    rbml_w.start_tag(tag_codemap);
+    let codemap = ecx.tcx.sess.codemap();
+
+    for filemap in &codemap.files.borrow()[..] {
+
+        if filemap.lines.borrow().len() == 0 || filemap.is_imported() {
+            // No need to export empty filemaps, as they can't contain spans
+            // that need translation.
+            // Also no need to re-export imported filemaps, as any downstream
+            // crate will import them from their original source.
+            continue;
+        }
+
+        rbml_w.start_tag(tag_codemap_filemap);
+        filemap.encode(rbml_w);
+        rbml_w.end_tag();
+    }
+
+    rbml_w.end_tag();
+}
+
 /// Serialize the text of the exported macros
 fn encode_macro_defs(rbml_w: &mut Encoder,
                      krate: &ast::Crate) {
@@ -1830,9 +1799,8 @@ fn encode_macro_defs(rbml_w: &mut Encoder,
         encode_name(rbml_w, def.ident.name);
         encode_attributes(rbml_w, &def.attrs);
 
-        rbml_w.start_tag(tag_macro_def_body);
-        rbml_w.wr_str(&pprust::tts_to_string(&def.body));
-        rbml_w.end_tag();
+        rbml_w.wr_tagged_str(tag_macro_def_body,
+                             &pprust::tts_to_string(&def.body));
 
         rbml_w.end_tag();
     }
@@ -1917,15 +1885,12 @@ fn encode_misc_info(ecx: &EncodeContext,
     rbml_w.start_tag(tag_misc_info);
     rbml_w.start_tag(tag_misc_info_crate_items);
     for item in &krate.module.items {
-        rbml_w.start_tag(tag_mod_child);
-        rbml_w.wr_str(&def_to_string(local_def(item.id)));
-        rbml_w.end_tag();
+        rbml_w.wr_tagged_str(tag_mod_child,
+                             &def_to_string(local_def(item.id)));
 
         each_auxiliary_node_id(&**item, |auxiliary_node_id| {
-            rbml_w.start_tag(tag_mod_child);
-            rbml_w.wr_str(&def_to_string(local_def(
-                        auxiliary_node_id)));
-            rbml_w.end_tag();
+            rbml_w.wr_tagged_str(tag_mod_child,
+                                 &def_to_string(local_def(auxiliary_node_id)));
             true
         });
     }
@@ -1956,35 +1921,25 @@ fn encode_reachable_extern_fns(ecx: &EncodeContext, rbml_w: &mut Encoder) {
 fn encode_crate_dep(rbml_w: &mut Encoder,
                     dep: decoder::CrateDep) {
     rbml_w.start_tag(tag_crate_dep);
-    rbml_w.start_tag(tag_crate_dep_crate_name);
-    rbml_w.writer.write_all(dep.name.as_bytes());
-    rbml_w.end_tag();
-    rbml_w.start_tag(tag_crate_dep_hash);
-    rbml_w.writer.write_all(dep.hash.as_str().as_bytes());
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_crate_dep_crate_name, &dep.name);
+    rbml_w.wr_tagged_str(tag_crate_dep_hash, dep.hash.as_str());
     rbml_w.end_tag();
 }
 
 fn encode_hash(rbml_w: &mut Encoder, hash: &Svh) {
-    rbml_w.start_tag(tag_crate_hash);
-    rbml_w.writer.write_all(hash.as_str().as_bytes());
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_crate_hash, hash.as_str());
 }
 
 fn encode_crate_name(rbml_w: &mut Encoder, crate_name: &str) {
-    rbml_w.start_tag(tag_crate_crate_name);
-    rbml_w.writer.write_all(crate_name.as_bytes());
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_crate_crate_name, crate_name);
 }
 
 fn encode_crate_triple(rbml_w: &mut Encoder, triple: &str) {
-    rbml_w.start_tag(tag_crate_triple);
-    rbml_w.writer.write_all(triple.as_bytes());
-    rbml_w.end_tag();
+    rbml_w.wr_tagged_str(tag_crate_triple, triple);
 }
 
 fn encode_dylib_dependency_formats(rbml_w: &mut Encoder, ecx: &EncodeContext) {
-    rbml_w.start_tag(tag_dylib_dependency_formats);
+    let tag = tag_dylib_dependency_formats;
     match ecx.tcx.dependency_formats.borrow().get(&config::CrateTypeDylib) {
         Some(arr) => {
             let s = arr.iter().enumerate().filter_map(|(i, slot)| {
@@ -1993,21 +1948,28 @@ fn encode_dylib_dependency_formats(rbml_w: &mut Encoder, ecx: &EncodeContext) {
                     cstore::RequireStatic => "s",
                 })).to_string())
             }).collect::<Vec<String>>();
-            rbml_w.writer.write_all(s.connect(",").as_bytes());
+            rbml_w.wr_tagged_str(tag, &s.connect(","));
+        }
+        None => {
+            rbml_w.wr_tagged_str(tag, "");
         }
-        None => {}
     }
-    rbml_w.end_tag();
 }
 
 // NB: Increment this as you change the metadata encoding version.
 #[allow(non_upper_case_globals)]
-pub const metadata_encoding_version : &'static [u8] = &[b'r', b'u', b's', b't', 0, 0, 0, 1 ];
+pub const metadata_encoding_version : &'static [u8] = &[b'r', b'u', b's', b't', 0, 0, 0, 2 ];
 
 pub fn encode_metadata(parms: EncodeParams, krate: &ast::Crate) -> Vec<u8> {
     let mut wr = SeekableMemWriter::new();
     encode_metadata_inner(&mut wr, parms, krate);
+
+    // RBML compacts the encoded bytes whenever appropriate,
+    // so there are some garbages left after the end of the data.
+    let metalen = wr.tell().unwrap() as uint;
     let mut v = wr.unwrap();
+    v.truncate(metalen);
+    assert_eq!(v.len(), metalen);
 
     // And here we run into yet another obscure archive bug: in which metadata
     // loaded from archives may have trailing garbage bytes. Awhile back one of
@@ -2044,6 +2006,7 @@ struct Stats {
         lang_item_bytes: u64,
         native_lib_bytes: u64,
         plugin_registrar_fn_bytes: u64,
+        codemap_bytes: u64,
         macro_defs_bytes: u64,
         impl_bytes: u64,
         misc_bytes: u64,
@@ -2058,6 +2021,7 @@ struct Stats {
         lang_item_bytes: 0,
         native_lib_bytes: 0,
         plugin_registrar_fn_bytes: 0,
+        codemap_bytes: 0,
         macro_defs_bytes: 0,
         impl_bytes: 0,
         misc_bytes: 0,
@@ -2089,7 +2053,7 @@ struct Stats {
         reachable: reachable,
      };
 
-    let mut rbml_w = writer::Encoder::new(wr);
+    let mut rbml_w = Encoder::new(wr);
 
     encode_crate_name(&mut rbml_w, &ecx.link_meta.crate_name);
     encode_crate_triple(&mut rbml_w,
@@ -2123,6 +2087,11 @@ struct Stats {
     encode_plugin_registrar_fn(&ecx, &mut rbml_w);
     stats.plugin_registrar_fn_bytes = rbml_w.writer.tell().unwrap() - i;
 
+    // Encode codemap
+    i = rbml_w.writer.tell().unwrap();
+    encode_codemap(&ecx, &mut rbml_w);
+    stats.codemap_bytes = rbml_w.writer.tell().unwrap() - i;
+
     // Encode macro definitions
     i = rbml_w.writer.tell().unwrap();
     encode_macro_defs(&mut rbml_w, krate);
@@ -2167,6 +2136,7 @@ struct Stats {
         println!("       lang item bytes: {}", stats.lang_item_bytes);
         println!("          native bytes: {}", stats.native_lib_bytes);
         println!("plugin registrar bytes: {}", stats.plugin_registrar_fn_bytes);
+        println!("         codemap bytes: {}", stats.codemap_bytes);
         println!("       macro def bytes: {}", stats.macro_defs_bytes);
         println!("            impl bytes: {}", stats.impl_bytes);
         println!("            misc bytes: {}", stats.misc_bytes);
@@ -2180,7 +2150,7 @@ struct Stats {
 // Get the encoded string for a type
 pub fn encoded_ty<'tcx>(tcx: &ty::ctxt<'tcx>, t: Ty<'tcx>) -> String {
     let mut wr = SeekableMemWriter::new();
-    tyencode::enc_ty(&mut wr, &tyencode::ctxt {
+    tyencode::enc_ty(&mut Encoder::new(&mut wr), &tyencode::ctxt {
         diag: tcx.sess.diagnostic(),
         ds: def_to_string,
         tcx: tcx,
index a8d39f95739326174f2f3714ef3085173ffcbfa4..22a4a6fc978dc055a9a79ae360b03c0d51feca7e 100644 (file)
@@ -14,9 +14,9 @@
 
 use std::collections::HashSet;
 use std::env;
-use std::os;
-use std::old_io::fs::PathExtensions;
-use std::old_io::fs;
+use std::fs;
+use std::io::prelude::*;
+use std::path::{Path, PathBuf};
 
 use util::fs as myfs;
 use session::search_paths::{SearchPaths, PathKind};
@@ -50,20 +50,20 @@ pub fn for_each_lib_search_path<F>(&self, mut f: F) where
                 FileMatches => found = true,
                 FileDoesntMatch => ()
             }
-            visited_dirs.insert(path.as_vec().to_vec());
+            visited_dirs.insert(path.to_path_buf());
         }
 
         debug!("filesearch: searching lib path");
         let tlib_path = make_target_lib_path(self.sysroot,
                                              self.triple);
-        if !visited_dirs.contains(tlib_path.as_vec()) {
+        if !visited_dirs.contains(&tlib_path) {
             match f(&tlib_path, PathKind::All) {
                 FileMatches => found = true,
                 FileDoesntMatch => ()
             }
         }
 
-        visited_dirs.insert(tlib_path.as_vec().to_vec());
+        visited_dirs.insert(tlib_path);
         // Try RUST_PATH
         if !found {
             let rustpath = rust_path();
@@ -71,10 +71,10 @@ pub fn for_each_lib_search_path<F>(&self, mut f: F) where
                 let tlib_path = make_rustpkg_lib_path(
                     self.sysroot, path, self.triple);
                 debug!("is {} in visited_dirs? {}", tlib_path.display(),
-                        visited_dirs.contains(&tlib_path.as_vec().to_vec()));
+                        visited_dirs.contains(&tlib_path));
 
-                if !visited_dirs.contains(tlib_path.as_vec()) {
-                    visited_dirs.insert(tlib_path.as_vec().to_vec());
+                if !visited_dirs.contains(&tlib_path) {
+                    visited_dirs.insert(tlib_path.clone());
                     // Don't keep searching the RUST_PATH if one match turns up --
                     // if we did, we'd get a "multiple matching crates" error
                     match f(&tlib_path, PathKind::All) {
@@ -88,7 +88,7 @@ pub fn for_each_lib_search_path<F>(&self, mut f: F) where
         }
     }
 
-    pub fn get_lib_path(&self) -> Path {
+    pub fn get_lib_path(&self) -> PathBuf {
         make_target_lib_path(self.sysroot, self.triple)
     }
 
@@ -97,11 +97,13 @@ pub fn search<F>(&self, mut pick: F)
     {
         self.for_each_lib_search_path(|lib_search_path, kind| {
             debug!("searching {}", lib_search_path.display());
-            match fs::readdir(lib_search_path) {
+            match fs::read_dir(lib_search_path) {
                 Ok(files) => {
+                    let files = files.filter_map(|p| p.ok().map(|s| s.path()))
+                                     .collect::<Vec<_>>();
                     let mut rslt = FileDoesntMatch;
-                    fn is_rlib(p: & &Path) -> bool {
-                        p.extension_str() == Some("rlib")
+                    fn is_rlib(p: &Path) -> bool {
+                        p.extension().and_then(|s| s.to_str()) == Some("rlib")
                     }
                     // Reading metadata out of rlibs is faster, and if we find both
                     // an rlib and a dylib we only read one of the files of
@@ -143,68 +145,69 @@ pub fn new(sysroot: &'a Path,
     }
 
     // Returns a list of directories where target-specific dylibs might be located.
-    pub fn get_dylib_search_paths(&self) -> Vec<Path> {
+    pub fn get_dylib_search_paths(&self) -> Vec<PathBuf> {
         let mut paths = Vec::new();
         self.for_each_lib_search_path(|lib_search_path, _| {
-            paths.push(lib_search_path.clone());
+            paths.push(lib_search_path.to_path_buf());
             FileDoesntMatch
         });
         paths
     }
 
     // Returns a list of directories where target-specific tool binaries are located.
-    pub fn get_tools_search_paths(&self) -> Vec<Path> {
-        let mut p = Path::new(self.sysroot);
-        p.push(find_libdir(self.sysroot));
-        p.push(rustlibdir());
-        p.push(self.triple);
+    pub fn get_tools_search_paths(&self) -> Vec<PathBuf> {
+        let mut p = PathBuf::new(self.sysroot);
+        p.push(&find_libdir(self.sysroot));
+        p.push(&rustlibdir());
+        p.push(&self.triple);
         p.push("bin");
         vec![p]
     }
 }
 
-pub fn relative_target_lib_path(sysroot: &Path, target_triple: &str) -> Path {
-    let mut p = Path::new(find_libdir(sysroot));
+pub fn relative_target_lib_path(sysroot: &Path, target_triple: &str) -> PathBuf {
+    let mut p = PathBuf::new(&find_libdir(sysroot));
     assert!(p.is_relative());
-    p.push(rustlibdir());
+    p.push(&rustlibdir());
     p.push(target_triple);
     p.push("lib");
     p
 }
 
 fn make_target_lib_path(sysroot: &Path,
-                        target_triple: &str) -> Path {
+                        target_triple: &str) -> PathBuf {
     sysroot.join(&relative_target_lib_path(sysroot, target_triple))
 }
 
 fn make_rustpkg_lib_path(sysroot: &Path,
                          dir: &Path,
-                         triple: &str) -> Path {
-    let mut p = dir.join(find_libdir(sysroot));
+                         triple: &str) -> PathBuf {
+    let mut p = dir.join(&find_libdir(sysroot));
     p.push(triple);
     p
 }
 
-pub fn get_or_default_sysroot() -> Path {
+pub fn get_or_default_sysroot() -> PathBuf {
     // Follow symlinks.  If the resolved path is relative, make it absolute.
-    fn canonicalize(path: Option<Path>) -> Option<Path> {
-        path.and_then(|path|
+    fn canonicalize(path: Option<PathBuf>) -> Option<PathBuf> {
+        path.and_then(|path| {
             match myfs::realpath(&path) {
                 Ok(canon) => Some(canon),
                 Err(e) => panic!("failed to get realpath: {}", e),
-            })
+            }
+        })
     }
 
-    match canonicalize(os::self_exe_name()) {
+    match canonicalize(env::current_exe().ok()) {
         Some(mut p) => { p.pop(); p.pop(); p }
         None => panic!("can't determine value for sysroot")
     }
 }
 
 #[cfg(windows)]
-static PATH_ENTRY_SEPARATOR: &'static str = ";";
+const PATH_ENTRY_SEPARATOR: char = ';';
 #[cfg(not(windows))]
-static PATH_ENTRY_SEPARATOR: &'static str = ":";
+const PATH_ENTRY_SEPARATOR: char = ':';
 
 /// Returns RUST_PATH as a string, without default paths added
 pub fn get_rust_path() -> Option<String> {
@@ -216,16 +219,16 @@ pub fn get_rust_path() -> Option<String> {
 /// $HOME/.rust
 /// DIR/.rust for any DIR that's the current working directory
 /// or an ancestor of it
-pub fn rust_path() -> Vec<Path> {
-    let mut env_rust_path: Vec<Path> = match get_rust_path() {
+pub fn rust_path() -> Vec<PathBuf> {
+    let mut env_rust_path: Vec<PathBuf> = match get_rust_path() {
         Some(env_path) => {
             let env_path_components =
                 env_path.split(PATH_ENTRY_SEPARATOR);
-            env_path_components.map(|s| Path::new(s)).collect()
+            env_path_components.map(|s| PathBuf::new(s)).collect()
         }
         None => Vec::new()
     };
-    let mut cwd = os::getcwd().unwrap();
+    let cwd = env::current_dir().unwrap();
     // now add in default entries
     let cwd_dot_rust = cwd.join(".rust");
     if !env_rust_path.contains(&cwd_dot_rust) {
@@ -234,17 +237,15 @@ pub fn rust_path() -> Vec<Path> {
     if !env_rust_path.contains(&cwd) {
         env_rust_path.push(cwd.clone());
     }
-    loop {
-        if { let f = cwd.filename(); f.is_none() || f.unwrap() == b".." } {
-            break
-        }
-        cwd.set_filename(".rust");
-        if !env_rust_path.contains(&cwd) && cwd.exists() {
-            env_rust_path.push(cwd.clone());
+    let mut cur = &*cwd;
+    while let Some(parent) = cur.parent() {
+        let candidate = parent.join(".rust");
+        if !env_rust_path.contains(&candidate) && candidate.exists() {
+            env_rust_path.push(candidate.clone());
         }
-        cwd.pop();
+        cur = parent;
     }
-    if let Some(h) = os::homedir() {
+    if let Some(h) = env::home_dir() {
         let p = h.join(".rust");
         if !env_rust_path.contains(&p) && p.exists() {
             env_rust_path.push(p);
@@ -267,7 +268,7 @@ fn find_libdir(sysroot: &Path) -> String {
 
     match option_env!("CFG_LIBDIR_RELATIVE") {
         Some(libdir) if libdir != "lib" => return libdir.to_string(),
-        _ => if sysroot.join(primary_libdir_name()).join(rustlibdir()).exists() {
+        _ => if sysroot.join(&primary_libdir_name()).join(&rustlibdir()).exists() {
             return primary_libdir_name();
         } else {
             return secondary_libdir_name();
index 07082d818769c44ba1d2cf25e5528b396fe1f346..8486bf782b00bc1048a34ad6b0020de7be49c3f9 100644 (file)
 use syntax::codemap::Span;
 use syntax::diagnostic::SpanHandler;
 use util::fs;
+use util::common;
 use rustc_back::target::Target;
 
-use std::ffi::CString;
 use std::cmp;
 use std::collections::HashMap;
-use std::old_io::fs::PathExtensions;
-use std::old_io;
+use std::io::prelude::*;
+use std::io;
+use std::path::{Path, PathBuf};
 use std::ptr;
 use std::slice;
 use std::time::Duration;
 use flate;
 
 pub struct CrateMismatch {
-    path: Path,
+    path: PathBuf,
     got: String,
 }
 
@@ -262,8 +263,8 @@ pub struct Context<'a> {
 }
 
 pub struct Library {
-    pub dylib: Option<(Path, PathKind)>,
-    pub rlib: Option<(Path, PathKind)>,
+    pub dylib: Option<(PathBuf, PathKind)>,
+    pub rlib: Option<(PathBuf, PathKind)>,
     pub metadata: MetadataBlob,
 }
 
@@ -275,12 +276,12 @@ pub struct ArchiveMetadata {
 
 pub struct CratePaths {
     pub ident: String,
-    pub dylib: Option<Path>,
-    pub rlib: Option<Path>
+    pub dylib: Option<PathBuf>,
+    pub rlib: Option<PathBuf>
 }
 
 impl CratePaths {
-    fn paths(&self) -> Vec<Path> {
+    fn paths(&self) -> Vec<PathBuf> {
         match (&self.dylib, &self.rlib) {
             (&None,    &None)              => vec!(),
             (&Some(ref p), &None) |
@@ -353,7 +354,7 @@ pub fn report_load_errs(&mut self) {
             }
         }
         if self.rejected_via_kind.len() > 0 {
-            self.sess.span_help(self.span, "please recompile this crate using \
+            self.sess.fileline_help(self.span, "please recompile this crate using \
                                             --crate-type lib");
             let mismatches = self.rejected_via_kind.iter();
             for (i, &CrateMismatch { ref path, .. }) in mismatches.enumerate() {
@@ -400,7 +401,7 @@ fn find_library_crate(&mut self) -> Option<Library> {
         //
         // The goal of this step is to look at as little metadata as possible.
         self.filesearch.search(|path, kind| {
-            let file = match path.filename_str() {
+            let file = match path.file_name().and_then(|s| s.to_str()) {
                 None => return FileDoesntMatch,
                 Some(file) => file,
             };
@@ -416,7 +417,7 @@ fn find_library_crate(&mut self) -> Option<Library> {
                 if file.starts_with(&staticlib_prefix[..]) &&
                    file.ends_with(".a") {
                     staticlibs.push(CrateMismatch {
-                        path: path.clone(),
+                        path: path.to_path_buf(),
                         got: "static".to_string()
                     });
                 }
@@ -506,9 +507,9 @@ fn find_library_crate(&mut self) -> Option<Library> {
     // read the metadata from it if `*slot` is `None`. If the metadata couldn't
     // be read, it is assumed that the file isn't a valid rust library (no
     // errors are emitted).
-    fn extract_one(&mut self, m: HashMap<Path, PathKind>, flavor: &str,
-                   slot: &mut Option<MetadataBlob>) -> Option<(Path, PathKind)> {
-        let mut ret = None::<(Path, PathKind)>;
+    fn extract_one(&mut self, m: HashMap<PathBuf, PathKind>, flavor: &str,
+                   slot: &mut Option<MetadataBlob>) -> Option<(PathBuf, PathKind)> {
+        let mut ret = None::<(PathBuf, PathKind)>;
         let mut error = 0;
 
         if slot.is_some() {
@@ -587,7 +588,7 @@ fn crate_matches(&mut self, crate_data: &[u8], libpath: &Path) -> bool {
         if triple != self.triple {
             info!("Rejecting via crate triple: expected {} got {}", self.triple, triple);
             self.rejected_via_triple.push(CrateMismatch {
-                path: libpath.clone(),
+                path: libpath.to_path_buf(),
                 got: triple.to_string()
             });
             return false;
@@ -599,7 +600,7 @@ fn crate_matches(&mut self, crate_data: &[u8], libpath: &Path) -> bool {
                 if *myhash != hash {
                     info!("Rejecting via hash: expected {} got {}", *myhash, hash);
                     self.rejected_via_hash.push(CrateMismatch {
-                        path: libpath.clone(),
+                        path: libpath.to_path_buf(),
                         got: myhash.as_str().to_string()
                     });
                     false
@@ -627,13 +628,13 @@ fn find_commandline_library(&mut self, locs: &[String]) -> Option<Library> {
         let mut rlibs = HashMap::new();
         let mut dylibs = HashMap::new();
         {
-            let locs = locs.iter().map(|l| Path::new(&l[..])).filter(|loc| {
+            let locs = locs.iter().map(|l| PathBuf::new(&l[..])).filter(|loc| {
                 if !loc.exists() {
                     sess.err(&format!("extern location for {} does not exist: {}",
                                      self.crate_name, loc.display()));
                     return false;
                 }
-                let file = match loc.filename_str() {
+                let file = match loc.file_name().and_then(|s| s.to_str()) {
                     Some(file) => file,
                     None => {
                         sess.err(&format!("extern location for {} is not a file: {}",
@@ -658,7 +659,7 @@ fn find_commandline_library(&mut self, locs: &[String]) -> Option<Library> {
             // Now that we have an iterator of good candidates, make sure
             // there's at most one rlib and at most one dylib.
             for loc in locs {
-                if loc.filename_str().unwrap().ends_with(".rlib") {
+                if loc.file_name().unwrap().to_str().unwrap().ends_with(".rlib") {
                     rlibs.insert(fs::realpath(&loc).unwrap(),
                                  PathKind::ExternFlag);
                 } else {
@@ -714,7 +715,7 @@ fn get_metadata_section(is_osx: bool, filename: &Path) -> Result<MetadataBlob, S
     let dur = Duration::span(|| {
         ret = Some(get_metadata_section_imp(is_osx, filename));
     });
-    info!("reading {} => {}ms", filename.filename_display(),
+    info!("reading {:?} => {}ms", filename.file_name().unwrap(),
           dur.num_milliseconds());
     return ret.unwrap();;
 }
@@ -723,7 +724,7 @@ fn get_metadata_section_imp(is_osx: bool, filename: &Path) -> Result<MetadataBlo
     if !filename.exists() {
         return Err(format!("no such file: '{}'", filename.display()));
     }
-    if filename.filename_str().unwrap().ends_with(".rlib") {
+    if filename.file_name().unwrap().to_str().unwrap().ends_with(".rlib") {
         // Use ArchiveRO for speed here, it's backed by LLVM and uses mmap
         // internally to read the file. We also avoid even using a memcpy by
         // just keeping the archive along while the metadata is in use.
@@ -742,7 +743,7 @@ fn get_metadata_section_imp(is_osx: bool, filename: &Path) -> Result<MetadataBlo
         };
     }
     unsafe {
-        let buf = CString::new(filename.as_vec()).unwrap();
+        let buf = common::path2cstr(filename);
         let mb = llvm::LLVMRustCreateMemoryBufferWithContentsOfFile(buf.as_ptr());
         if mb as int == 0 {
             return Err(format!("error reading library: '{}'",
@@ -811,7 +812,7 @@ pub fn read_meta_section_name(is_osx: bool) -> &'static str {
 
 // A diagnostic function for dumping crate metadata to an output stream
 pub fn list_file_metadata(is_osx: bool, path: &Path,
-                          out: &mut old_io::Writer) -> old_io::IoResult<()> {
+                          out: &mut io::Write) -> io::Result<()> {
     match get_metadata_section(is_osx, path) {
         Ok(bytes) => decoder::list_crate_metadata(bytes.as_slice(), out),
         Err(msg) => {
index d25dc4f58a5dfa6181472a12ff73c75237c69155..3714e3b8c73da6a7cc4ca9eecb641743c7751388 100644 (file)
@@ -84,7 +84,7 @@ fn visit_item(&mut self, item: &ast::Item) {
                 }
                 "plugin" => {
                     self.sess.span_err(attr.span, "#[plugin] on `extern crate` is deprecated");
-                    self.sess.span_help(attr.span, &format!("use a crate attribute instead, \
+                    self.sess.fileline_help(attr.span, &format!("use a crate attribute instead, \
                                                             i.e. #![plugin({})]",
                                                             item.ident.as_str()));
                 }
@@ -166,6 +166,9 @@ fn load_macros<'b>(&mut self,
                 Some(sel) => sel.contains_key(&name),
             };
             def.export = reexport.contains_key(&name);
+            def.allow_internal_unstable = attr::contains_name(&def.attrs,
+                                                              "allow_internal_unstable");
+            debug!("load_macros: loaded: {:?}", def);
             self.macros.push(def);
         }
 
index baecfb7eb22c5ec6cb95898ee8ca45f60e93f003..b33839f33e8203d7a08a8ea0be86294b9f47ec33 100644 (file)
@@ -555,11 +555,9 @@ fn parse_ty_<'a, 'tcx, F>(st: &mut PState<'a, 'tcx>, conv: &mut F) -> Ty<'tcx> w
       'k' => {
           assert_eq!(next(st), '[');
           let did = parse_def_(st, ClosureSource, conv);
-          let region = parse_region_(st, conv);
           let substs = parse_substs_(st, conv);
           assert_eq!(next(st), ']');
-          return ty::mk_closure(st.tcx, did,
-                  st.tcx.mk_region(region), st.tcx.mk_substs(substs));
+          return ty::mk_closure(st.tcx, did, st.tcx.mk_substs(substs));
       }
       'P' => {
           assert_eq!(next(st), '[');
index 76a365259aa5713a3eb952a9a3eadfffeefb0bba..86f1605b8bfaa706fa0de0f511703893d3f1c9a6 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
@@ -27,9 +27,9 @@
 use syntax::diagnostic::SpanHandler;
 use syntax::parse::token;
 
-use rbml::io::SeekableMemWriter;
+use rbml::writer::Encoder;
 
-macro_rules! mywrite { ($($arg:tt)*) => ({ write!($($arg)*); }) }
+macro_rules! mywrite { ($w:expr, $($arg:tt)*) => ({ write!($w.writer, $($arg)*); }) }
 
 pub struct ctxt<'a, 'tcx: 'a> {
     pub diag: &'a SpanHandler,
@@ -49,12 +49,14 @@ pub struct ty_abbrev {
 
 pub type abbrev_map<'tcx> = RefCell<FnvHashMap<Ty<'tcx>, ty_abbrev>>;
 
-pub fn enc_ty<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>, t: Ty<'tcx>) {
+pub fn enc_ty<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>, t: Ty<'tcx>) {
     match cx.abbrevs.borrow_mut().get(&t) {
-        Some(a) => { w.write_all(a.s.as_bytes()); return; }
+        Some(a) => { w.writer.write_all(a.s.as_bytes()); return; }
         None => {}
     }
-    let pos = w.tell().unwrap();
+
+    // type abbreviations needs a stable position
+    let pos = w.mark_stable_position();
 
     match t.sty {
         ty::ty_bool => mywrite!(w, "b"),
@@ -139,9 +141,8 @@ pub fn enc_ty<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>, t: Ty<'t
             enc_substs(w, cx, substs);
             mywrite!(w, "]");
         }
-        ty::ty_closure(def, region, substs) => {
+        ty::ty_closure(def, substs) => {
             mywrite!(w, "k[{}|", (cx.ds)(def));
-            enc_region(w, cx, *region);
             enc_substs(w, cx, substs);
             mywrite!(w, "]");
         }
@@ -155,7 +156,7 @@ pub fn enc_ty<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>, t: Ty<'t
         }
     }
 
-    let end = w.tell().unwrap();
+    let end = w.mark_stable_position();
     let len = end - pos;
     fn estimate_sz(u: u64) -> u64 {
         let mut n = u;
@@ -172,21 +173,21 @@ fn estimate_sz(u: u64) -> u64 {
     }
 }
 
-fn enc_mutability(w: &mut SeekableMemWriter, mt: ast::Mutability) {
+fn enc_mutability(w: &mut Encoder, mt: ast::Mutability) {
     match mt {
         ast::MutImmutable => (),
         ast::MutMutable => mywrite!(w, "m"),
     }
 }
 
-fn enc_mt<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+fn enc_mt<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                     mt: ty::mt<'tcx>) {
     enc_mutability(w, mt.mutbl);
     enc_ty(w, cx, mt.ty);
 }
 
-fn enc_opt<T, F>(w: &mut SeekableMemWriter, t: Option<T>, enc_f: F) where
-    F: FnOnce(&mut SeekableMemWriter, T),
+fn enc_opt<T, F>(w: &mut Encoder, t: Option<T>, enc_f: F) where
+    F: FnOnce(&mut Encoder, T),
 {
     match t {
         None => mywrite!(w, "n"),
@@ -197,11 +198,11 @@ fn enc_opt<T, F>(w: &mut SeekableMemWriter, t: Option<T>, enc_f: F) where
     }
 }
 
-fn enc_vec_per_param_space<'a, 'tcx, T, F>(w: &mut SeekableMemWriter,
+fn enc_vec_per_param_space<'a, 'tcx, T, F>(w: &mut Encoder,
                                            cx: &ctxt<'a, 'tcx>,
                                            v: &VecPerParamSpace<T>,
                                            mut op: F) where
-    F: FnMut(&mut SeekableMemWriter, &ctxt<'a, 'tcx>, &T),
+    F: FnMut(&mut Encoder, &ctxt<'a, 'tcx>, &T),
 {
     for &space in &subst::ParamSpace::all() {
         mywrite!(w, "[");
@@ -212,14 +213,14 @@ fn enc_vec_per_param_space<'a, 'tcx, T, F>(w: &mut SeekableMemWriter,
     }
 }
 
-pub fn enc_substs<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+pub fn enc_substs<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                             substs: &subst::Substs<'tcx>) {
     enc_region_substs(w, cx, &substs.regions);
     enc_vec_per_param_space(w, cx, &substs.types,
                             |w, cx, &ty| enc_ty(w, cx, ty));
 }
 
-fn enc_region_substs(w: &mut SeekableMemWriter, cx: &ctxt, substs: &subst::RegionSubsts) {
+fn enc_region_substs(w: &mut Encoder, cx: &ctxt, substs: &subst::RegionSubsts) {
     match *substs {
         subst::ErasedRegions => {
             mywrite!(w, "e");
@@ -232,7 +233,7 @@ fn enc_region_substs(w: &mut SeekableMemWriter, cx: &ctxt, substs: &subst::Regio
     }
 }
 
-pub fn enc_region(w: &mut SeekableMemWriter, cx: &ctxt, r: ty::Region) {
+pub fn enc_region(w: &mut Encoder, cx: &ctxt, r: ty::Region) {
     match r {
         ty::ReLateBound(id, br) => {
             mywrite!(w, "b[{}|", id.depth);
@@ -271,7 +272,7 @@ pub fn enc_region(w: &mut SeekableMemWriter, cx: &ctxt, r: ty::Region) {
     }
 }
 
-fn enc_scope(w: &mut SeekableMemWriter, _cx: &ctxt, scope: region::CodeExtent) {
+fn enc_scope(w: &mut Encoder, _cx: &ctxt, scope: region::CodeExtent) {
     match scope {
         region::CodeExtent::Misc(node_id) => mywrite!(w, "M{}", node_id),
         region::CodeExtent::Remainder(region::BlockRemainder {
@@ -280,12 +281,12 @@ fn enc_scope(w: &mut SeekableMemWriter, _cx: &ctxt, scope: region::CodeExtent) {
     }
 }
 
-fn enc_destruction_scope_data(w: &mut SeekableMemWriter,
+fn enc_destruction_scope_data(w: &mut Encoder,
                               d: region::DestructionScopeData) {
     mywrite!(w, "{}", d.node_id);
 }
 
-fn enc_bound_region(w: &mut SeekableMemWriter, cx: &ctxt, br: ty::BoundRegion) {
+fn enc_bound_region(w: &mut Encoder, cx: &ctxt, br: ty::BoundRegion) {
     match br {
         ty::BrAnon(idx) => {
             mywrite!(w, "a{}|", idx);
@@ -304,40 +305,40 @@ fn enc_bound_region(w: &mut SeekableMemWriter, cx: &ctxt, br: ty::BoundRegion) {
     }
 }
 
-pub fn enc_trait_ref<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+pub fn enc_trait_ref<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                                s: &ty::TraitRef<'tcx>) {
     mywrite!(w, "{}|", (cx.ds)(s.def_id));
     enc_substs(w, cx, s.substs);
 }
 
-fn enc_unsafety(w: &mut SeekableMemWriter, p: ast::Unsafety) {
+fn enc_unsafety(w: &mut Encoder, p: ast::Unsafety) {
     match p {
         ast::Unsafety::Normal => mywrite!(w, "n"),
         ast::Unsafety::Unsafe => mywrite!(w, "u"),
     }
 }
 
-fn enc_abi(w: &mut SeekableMemWriter, abi: Abi) {
+fn enc_abi(w: &mut Encoder, abi: Abi) {
     mywrite!(w, "[");
     mywrite!(w, "{}", abi.name());
     mywrite!(w, "]")
 }
 
-pub fn enc_bare_fn_ty<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+pub fn enc_bare_fn_ty<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                                 ft: &ty::BareFnTy<'tcx>) {
     enc_unsafety(w, ft.unsafety);
     enc_abi(w, ft.abi);
     enc_fn_sig(w, cx, &ft.sig);
 }
 
-pub fn enc_closure_ty<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+pub fn enc_closure_ty<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                                 ft: &ty::ClosureTy<'tcx>) {
     enc_unsafety(w, ft.unsafety);
     enc_fn_sig(w, cx, &ft.sig);
     enc_abi(w, ft.abi);
 }
 
-fn enc_fn_sig<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+fn enc_fn_sig<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                         fsig: &ty::PolyFnSig<'tcx>) {
     mywrite!(w, "[");
     for ty in &fsig.0.inputs {
@@ -359,7 +360,7 @@ fn enc_fn_sig<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
     }
 }
 
-pub fn enc_builtin_bounds(w: &mut SeekableMemWriter, _cx: &ctxt, bs: &ty::BuiltinBounds) {
+pub fn enc_builtin_bounds(w: &mut Encoder, _cx: &ctxt, bs: &ty::BuiltinBounds) {
     for bound in bs {
         match bound {
             ty::BoundSend => mywrite!(w, "S"),
@@ -372,7 +373,7 @@ pub fn enc_builtin_bounds(w: &mut SeekableMemWriter, _cx: &ctxt, bs: &ty::Builti
     mywrite!(w, ".");
 }
 
-pub fn enc_existential_bounds<'a,'tcx>(w: &mut SeekableMemWriter,
+pub fn enc_existential_bounds<'a,'tcx>(w: &mut Encoder,
                                        cx: &ctxt<'a,'tcx>,
                                        bs: &ty::ExistentialBounds<'tcx>) {
     let param_bounds = ty::ParamBounds { trait_bounds: vec!(),
@@ -382,7 +383,7 @@ pub fn enc_existential_bounds<'a,'tcx>(w: &mut SeekableMemWriter,
     enc_bounds(w, cx, &param_bounds);
 }
 
-pub fn enc_bounds<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+pub fn enc_bounds<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                             bs: &ty::ParamBounds<'tcx>) {
     enc_builtin_bounds(w, cx, &bs.builtin_bounds);
 
@@ -401,7 +402,7 @@ pub fn enc_bounds<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
     mywrite!(w, ".");
 }
 
-pub fn enc_region_bounds<'a, 'tcx>(w: &mut SeekableMemWriter,
+pub fn enc_region_bounds<'a, 'tcx>(w: &mut Encoder,
                             cx: &ctxt<'a, 'tcx>,
                             rs: &[ty::Region]) {
     for &r in rs {
@@ -412,7 +413,7 @@ pub fn enc_region_bounds<'a, 'tcx>(w: &mut SeekableMemWriter,
     mywrite!(w, ".");
 }
 
-pub fn enc_type_param_def<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tcx>,
+pub fn enc_type_param_def<'a, 'tcx>(w: &mut Encoder, cx: &ctxt<'a, 'tcx>,
                                     v: &ty::TypeParameterDef<'tcx>) {
     mywrite!(w, "{}:{}|{}|{}|",
              token::get_name(v.name), (cx.ds)(v.def_id),
@@ -421,7 +422,7 @@ pub fn enc_type_param_def<'a, 'tcx>(w: &mut SeekableMemWriter, cx: &ctxt<'a, 'tc
     enc_object_lifetime_default(w, cx, v.object_lifetime_default);
 }
 
-fn enc_object_lifetime_default<'a, 'tcx>(w: &mut SeekableMemWriter,
+fn enc_object_lifetime_default<'a, 'tcx>(w: &mut Encoder,
                                          cx: &ctxt<'a, 'tcx>,
                                          default: Option<ty::ObjectLifetimeDefault>)
 {
@@ -435,7 +436,7 @@ fn enc_object_lifetime_default<'a, 'tcx>(w: &mut SeekableMemWriter,
     }
 }
 
-pub fn enc_predicate<'a, 'tcx>(w: &mut SeekableMemWriter,
+pub fn enc_predicate<'a, 'tcx>(w: &mut Encoder,
                                cx: &ctxt<'a, 'tcx>,
                                p: &ty::Predicate<'tcx>)
 {
@@ -466,7 +467,7 @@ pub fn enc_predicate<'a, 'tcx>(w: &mut SeekableMemWriter,
     }
 }
 
-fn enc_projection_predicate<'a, 'tcx>(w: &mut SeekableMemWriter,
+fn enc_projection_predicate<'a, 'tcx>(w: &mut Encoder,
                                       cx: &ctxt<'a, 'tcx>,
                                       data: &ty::ProjectionPredicate<'tcx>) {
     enc_trait_ref(w, cx, &*data.projection_ty.trait_ref);
index 5983829ed8fbef20e56b6124b2a1e868201aaf0d..9d712c7c0fcc800d2e60e61363eb7f9f08c39ae3 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
 use std::old_io::Seek;
 use std::num::FromPrimitive;
 use std::rc::Rc;
+use std::cell::Cell;
 
-use rbml::io::SeekableMemWriter;
-use rbml::{reader, writer};
+use rbml::reader;
+use rbml::writer::Encoder;
 use rbml;
 use serialize;
 use serialize::{Decodable, Decoder, DecoderHelpers, Encodable};
 use serialize::{EncoderHelpers};
 
+#[cfg(test)] use rbml::io::SeekableMemWriter;
 #[cfg(test)] use syntax::parse;
 #[cfg(test)] use syntax::print::pprust;
 
@@ -57,7 +59,9 @@ struct DecodeContext<'a, 'b, 'tcx: 'a> {
     tcx: &'a ty::ctxt<'tcx>,
     cdata: &'b cstore::crate_metadata,
     from_id_range: ast_util::IdRange,
-    to_id_range: ast_util::IdRange
+    to_id_range: ast_util::IdRange,
+    // Cache the last used filemap for translating spans as an optimization.
+    last_filemap_index: Cell<usize>,
 }
 
 trait tr {
@@ -68,8 +72,6 @@ trait tr_intern {
     fn tr_intern(&self, dcx: &DecodeContext) -> ast::DefId;
 }
 
-pub type Encoder<'a> = writer::Encoder<'a, SeekableMemWriter>;
-
 // ______________________________________________________________________
 // Top-level methods.
 
@@ -121,6 +123,8 @@ fn new_span(&self, span: Span) -> Span {
     }
 }
 
+/// Decodes an item from its AST in the cdata's metadata and adds it to the
+/// ast-map.
 pub fn decode_inlined_item<'tcx>(cdata: &cstore::crate_metadata,
                                  tcx: &ty::ctxt<'tcx>,
                                  path: Vec<ast_map::PathElem>,
@@ -144,7 +148,8 @@ pub fn decode_inlined_item<'tcx>(cdata: &cstore::crate_metadata,
             cdata: cdata,
             tcx: tcx,
             from_id_range: from_id_range,
-            to_id_range: to_id_range
+            to_id_range: to_id_range,
+            last_filemap_index: Cell::new(0)
         };
         let raw_ii = decode_ast(ast_doc);
         let ii = ast_map::map_decoded_item(&dcx.tcx.map, path, raw_ii, dcx);
@@ -205,7 +210,9 @@ impl<'a, 'b, 'tcx> DecodeContext<'a, 'b, 'tcx> {
     pub fn tr_id(&self, id: ast::NodeId) -> ast::NodeId {
         // from_id_range should be non-empty
         assert!(!self.from_id_range.empty());
-        (id - self.from_id_range.min + self.to_id_range.min)
+        // Use wrapping arithmetic because otherwise it introduces control flow.
+        // Maybe we should just have the control flow? -- aatch
+        (id.wrapping_sub(self.from_id_range.min).wrapping_add(self.to_id_range.min))
     }
 
     /// Translates an EXTERNAL def-id, converting the crate number from the one used in the encoded
@@ -233,8 +240,47 @@ pub fn tr_intern_def_id(&self, did: ast::DefId) -> ast::DefId {
         assert_eq!(did.krate, ast::LOCAL_CRATE);
         ast::DefId { krate: ast::LOCAL_CRATE, node: self.tr_id(did.node) }
     }
-    pub fn tr_span(&self, _span: Span) -> Span {
-        codemap::DUMMY_SP // FIXME (#1972): handle span properly
+
+    /// Translates a `Span` from an extern crate to the corresponding `Span`
+    /// within the local crate's codemap. `creader::import_codemap()` will
+    /// already have allocated any additionally needed FileMaps in the local
+    /// codemap as a side-effect of creating the crate_metadata's
+    /// `codemap_import_info`.
+    pub fn tr_span(&self, span: Span) -> Span {
+        let imported_filemaps = &self.cdata.codemap_import_info[..];
+
+        let filemap_index = {
+            // Optimize for the case that most spans within a translated item
+            // originate from the same filemap.
+            let last_filemap_index = self.last_filemap_index.get();
+
+            if span.lo >= imported_filemaps[last_filemap_index].original_start_pos &&
+               span.hi <= imported_filemaps[last_filemap_index].original_end_pos {
+                last_filemap_index
+            } else {
+                let mut a = 0;
+                let mut b = imported_filemaps.len();
+
+                while b - a > 1 {
+                    let m = (a + b) / 2;
+                    if imported_filemaps[m].original_start_pos > span.lo {
+                        b = m;
+                    } else {
+                        a = m;
+                    }
+                }
+
+                self.last_filemap_index.set(a);
+                a
+            }
+        };
+
+        let lo = (span.lo - imported_filemaps[filemap_index].original_start_pos) +
+                  imported_filemaps[filemap_index].translated_filemap.start_pos;
+        let hi = (span.hi - imported_filemaps[filemap_index].original_start_pos) +
+                  imported_filemaps[filemap_index].translated_filemap.start_pos;
+
+        codemap::mk_sp(lo, hi)
     }
 }
 
@@ -414,9 +460,8 @@ fn decode_ast(par_doc: rbml::Doc) -> ast::InlinedItem {
 // ______________________________________________________________________
 // Encoding and decoding of ast::def
 
-fn decode_def(dcx: &DecodeContext, doc: rbml::Doc) -> def::Def {
-    let mut dsr = reader::Decoder::new(doc);
-    let def: def::Def = Decodable::decode(&mut dsr).unwrap();
+fn decode_def(dcx: &DecodeContext, dsr: &mut reader::Decoder) -> def::Def {
+    let def: def::Def = Decodable::decode(dsr).unwrap();
     def.tr(dcx)
 }
 
@@ -911,7 +956,7 @@ fn emit_trait_ref<'b>(&mut self, ecx: &e::EncodeContext<'b, 'tcx>,
     fn emit_type_param_def<'b>(&mut self, ecx: &e::EncodeContext<'b, 'tcx>,
                                type_param_def: &ty::TypeParameterDef<'tcx>) {
         self.emit_opaque(|this| {
-            Ok(tyencode::enc_type_param_def(this.writer,
+            Ok(tyencode::enc_type_param_def(this,
                                          &ecx.ty_str_ctxt(),
                                          type_param_def))
         });
@@ -920,7 +965,7 @@ fn emit_type_param_def<'b>(&mut self, ecx: &e::EncodeContext<'b, 'tcx>,
     fn emit_predicate<'b>(&mut self, ecx: &e::EncodeContext<'b, 'tcx>,
                           predicate: &ty::Predicate<'tcx>) {
         self.emit_opaque(|this| {
-            Ok(tyencode::enc_predicate(this.writer,
+            Ok(tyencode::enc_predicate(this,
                                        &ecx.ty_str_ctxt(),
                                        predicate))
         });
@@ -954,20 +999,20 @@ fn emit_type_scheme<'b>(&mut self,
 
     fn emit_existential_bounds<'b>(&mut self, ecx: &e::EncodeContext<'b,'tcx>,
                                    bounds: &ty::ExistentialBounds<'tcx>) {
-        self.emit_opaque(|this| Ok(tyencode::enc_existential_bounds(this.writer,
+        self.emit_opaque(|this| Ok(tyencode::enc_existential_bounds(this,
                                                                     &ecx.ty_str_ctxt(),
                                                                     bounds)));
     }
 
     fn emit_builtin_bounds(&mut self, ecx: &e::EncodeContext, bounds: &ty::BuiltinBounds) {
-        self.emit_opaque(|this| Ok(tyencode::enc_builtin_bounds(this.writer,
+        self.emit_opaque(|this| Ok(tyencode::enc_builtin_bounds(this,
                                                                 &ecx.ty_str_ctxt(),
                                                                 bounds)));
     }
 
     fn emit_substs<'b>(&mut self, ecx: &e::EncodeContext<'b, 'tcx>,
                        substs: &subst::Substs<'tcx>) {
-        self.emit_opaque(|this| Ok(tyencode::enc_substs(this.writer,
+        self.emit_opaque(|this| Ok(tyencode::enc_substs(this,
                                                            &ecx.ty_str_ctxt(),
                                                            substs)));
     }
@@ -1115,7 +1160,7 @@ fn tag<F>(&mut self,
     }
 
     fn id(&mut self, id: ast::NodeId) {
-        self.wr_tagged_u64(c::tag_table_id as uint, id as u64);
+        id.encode(self).unwrap();
     }
 }
 
@@ -1152,51 +1197,44 @@ fn encode_side_tables_for_id(ecx: &e::EncodeContext,
     if let Some(def) = tcx.def_map.borrow().get(&id).map(|d| d.full_def()) {
         rbml_w.tag(c::tag_table_def, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| def.encode(rbml_w).unwrap());
+            def.encode(rbml_w).unwrap();
         })
     }
 
     if let Some(ty) = tcx.node_types.borrow().get(&id) {
         rbml_w.tag(c::tag_table_node_type, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_ty(ecx, *ty);
-            })
+            rbml_w.emit_ty(ecx, *ty);
         })
     }
 
     if let Some(item_substs) = tcx.item_substs.borrow().get(&id) {
         rbml_w.tag(c::tag_table_item_subst, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_substs(ecx, &item_substs.substs);
-            })
+            rbml_w.emit_substs(ecx, &item_substs.substs);
         })
     }
 
     if let Some(fv) = tcx.freevars.borrow().get(&id) {
         rbml_w.tag(c::tag_table_freevars, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_from_vec(fv, |rbml_w, fv_entry| {
-                    Ok(encode_freevar_entry(rbml_w, fv_entry))
-                });
-            })
+            rbml_w.emit_from_vec(fv, |rbml_w, fv_entry| {
+                Ok(encode_freevar_entry(rbml_w, fv_entry))
+            });
         });
 
         for freevar in fv {
             rbml_w.tag(c::tag_table_upvar_capture_map, |rbml_w| {
                 rbml_w.id(id);
-                rbml_w.tag(c::tag_table_val, |rbml_w| {
-                    let var_id = freevar.def.def_id().node;
-                    let upvar_id = ty::UpvarId {
-                        var_id: var_id,
-                        closure_expr_id: id
-                    };
-                    let upvar_capture = tcx.upvar_capture_map.borrow()[upvar_id].clone();
-                    var_id.encode(rbml_w);
-                    upvar_capture.encode(rbml_w);
-                })
+
+                let var_id = freevar.def.def_id().node;
+                let upvar_id = ty::UpvarId {
+                    var_id: var_id,
+                    closure_expr_id: id
+                };
+                let upvar_capture = tcx.upvar_capture_map.borrow()[upvar_id].clone();
+                var_id.encode(rbml_w);
+                upvar_capture.encode(rbml_w);
             })
         }
     }
@@ -1205,18 +1243,14 @@ fn encode_side_tables_for_id(ecx: &e::EncodeContext,
     if let Some(type_scheme) = tcx.tcache.borrow().get(&lid) {
         rbml_w.tag(c::tag_table_tcache, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_type_scheme(ecx, type_scheme.clone());
-            })
+            rbml_w.emit_type_scheme(ecx, type_scheme.clone());
         })
     }
 
     if let Some(type_param_def) = tcx.ty_param_defs.borrow().get(&id) {
         rbml_w.tag(c::tag_table_param_defs, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_type_param_def(ecx, type_param_def)
-            })
+            rbml_w.emit_type_param_def(ecx, type_param_def)
         })
     }
 
@@ -1224,18 +1258,14 @@ fn encode_side_tables_for_id(ecx: &e::EncodeContext,
     if let Some(method) = tcx.method_map.borrow().get(&method_call) {
         rbml_w.tag(c::tag_table_method_map, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                encode_method_callee(ecx, rbml_w, method_call.adjustment, method)
-            })
+            encode_method_callee(ecx, rbml_w, method_call.adjustment, method)
         })
     }
 
     if let Some(trait_ref) = tcx.object_cast_map.borrow().get(&id) {
         rbml_w.tag(c::tag_table_object_cast_map, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_trait_ref(ecx, &*trait_ref.0);
-            })
+            rbml_w.emit_trait_ref(ecx, &*trait_ref.0);
         })
     }
 
@@ -1246,9 +1276,7 @@ fn encode_side_tables_for_id(ecx: &e::EncodeContext,
                 if let Some(method) = tcx.method_map.borrow().get(&method_call) {
                     rbml_w.tag(c::tag_table_method_map, |rbml_w| {
                         rbml_w.id(id);
-                        rbml_w.tag(c::tag_table_val, |rbml_w| {
-                            encode_method_callee(ecx, rbml_w, method_call.adjustment, method)
-                        })
+                        encode_method_callee(ecx, rbml_w, method_call.adjustment, method)
                     })
                 }
             }
@@ -1259,10 +1287,8 @@ fn encode_side_tables_for_id(ecx: &e::EncodeContext,
                     if let Some(method) = tcx.method_map.borrow().get(&method_call) {
                         rbml_w.tag(c::tag_table_method_map, |rbml_w| {
                             rbml_w.id(id);
-                            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                                encode_method_callee(ecx, rbml_w,
-                                                     method_call.adjustment, method)
-                            })
+                            encode_method_callee(ecx, rbml_w,
+                                                 method_call.adjustment, method)
                         })
                     }
                 }
@@ -1274,36 +1300,28 @@ fn encode_side_tables_for_id(ecx: &e::EncodeContext,
 
         rbml_w.tag(c::tag_table_adjustments, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_auto_adjustment(ecx, adjustment);
-            })
+            rbml_w.emit_auto_adjustment(ecx, adjustment);
         })
     }
 
     if let Some(closure_type) = tcx.closure_tys.borrow().get(&ast_util::local_def(id)) {
         rbml_w.tag(c::tag_table_closure_tys, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                rbml_w.emit_closure_type(ecx, closure_type);
-            })
+            rbml_w.emit_closure_type(ecx, closure_type);
         })
     }
 
     if let Some(closure_kind) = tcx.closure_kinds.borrow().get(&ast_util::local_def(id)) {
         rbml_w.tag(c::tag_table_closure_kinds, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                encode_closure_kind(rbml_w, *closure_kind)
-            })
+            encode_closure_kind(rbml_w, *closure_kind)
         })
     }
 
     for &qualif in tcx.const_qualif_map.borrow().get(&id).iter() {
         rbml_w.tag(c::tag_table_const_qualif, |rbml_w| {
             rbml_w.id(id);
-            rbml_w.tag(c::tag_table_val, |rbml_w| {
-                qualif.encode(rbml_w).unwrap()
-            })
+            qualif.encode(rbml_w).unwrap()
         })
     }
 }
@@ -1831,13 +1849,14 @@ fn decode_side_tables(dcx: &DecodeContext,
                       ast_doc: rbml::Doc) {
     let tbl_doc = ast_doc.get(c::tag_table as uint);
     reader::docs(tbl_doc, |tag, entry_doc| {
-        let id0 = entry_doc.get(c::tag_table_id as uint).as_int();
-        let id = dcx.tr_id(id0 as ast::NodeId);
+        let mut entry_dsr = reader::Decoder::new(entry_doc);
+        let id0: ast::NodeId = Decodable::decode(&mut entry_dsr).unwrap();
+        let id = dcx.tr_id(id0);
 
         debug!(">> Side table document with tag 0x{:x} \
                 found for id {} (orig {})",
                tag, id, id0);
-        let decoded_tag: Option<c::astencode_tag> = FromPrimitive::from_uint(tag);
+        let decoded_tag: Option<c::astencode_tag> = FromPrimitive::from_usize(tag);
         match decoded_tag {
             None => {
                 dcx.tcx.sess.bug(
@@ -1845,13 +1864,11 @@ fn decode_side_tables(dcx: &DecodeContext,
                             tag));
             }
             Some(value) => {
-                let val_doc = entry_doc.get(c::tag_table_val as uint);
-                let mut val_dsr = reader::Decoder::new(val_doc);
-                let val_dsr = &mut val_dsr;
+                let val_dsr = &mut entry_dsr;
 
                 match value {
                     c::tag_table_def => {
-                        let def = decode_def(dcx, val_doc);
+                        let def = decode_def(dcx, val_dsr);
                         dcx.tcx.def_map.borrow_mut().insert(id, def::PathResolution {
                             base_def: def,
                             // This doesn't matter cross-crate.
@@ -1995,7 +2012,7 @@ fn mk_ctxt() -> parse::ParseSess {
 fn roundtrip(in_item: Option<P<ast::Item>>) {
     let in_item = in_item.unwrap();
     let mut wr = SeekableMemWriter::new();
-    encode_item_ast(&mut writer::Encoder::new(&mut wr), &*in_item);
+    encode_item_ast(&mut Encoder::new(&mut wr), &*in_item);
     let rbml_doc = rbml::Doc::new(wr.get_ref());
     let out_item = decode_item_ast(rbml_doc);
 
index 8401d25024d3577e7fa4921445d7d03a0694393b..497022ac6ac49b3eb87ebfccf0a499db4722f8ba 100644 (file)
@@ -307,8 +307,9 @@ fn visit_expr(&mut self, ex: &ast::Expr) {
                             match const_eval::eval_const_expr_partial(self.tcx, ex, None) {
                                 Ok(_) => {}
                                 Err(msg) => {
-                                    span_err!(self.tcx.sess, ex.span, E0020,
-                                              "{} in a constant expression", msg)
+                                    span_err!(self.tcx.sess, msg.span, E0020,
+                                              "{} in a constant expression",
+                                              msg.description())
                                 }
                             }
                         }
index c409c8fb13f14502437aa2d1c9813b1365624f9d..40bba6fb0ac7cde29edb64d4533206971b2971b7 100644 (file)
@@ -13,7 +13,8 @@
 use self::WitnessPreference::*;
 
 use middle::const_eval::{compare_const_vals, const_bool, const_float, const_val};
-use middle::const_eval::{const_expr_to_pat, eval_const_expr, lookup_const_by_id};
+use middle::const_eval::{eval_const_expr, eval_const_expr_partial};
+use middle::const_eval::{const_expr_to_pat, lookup_const_by_id};
 use middle::def::*;
 use middle::expr_use_visitor::{ConsumeMode, Delegate, ExprUseVisitor, Init};
 use middle::expr_use_visitor::{JustWrite, LoanCause, MutateMode};
@@ -229,13 +230,6 @@ fn check_expr(cx: &mut MatchCheckCtxt, ex: &ast::Expr) {
     }
 }
 
-fn is_expr_const_nan(tcx: &ty::ctxt, expr: &ast::Expr) -> bool {
-    match eval_const_expr(tcx, expr) {
-        const_float(f) => f.is_nan(),
-        _ => false
-    }
-}
-
 fn check_for_bindings_named_the_same_as_variants(cx: &MatchCheckCtxt, pat: &Pat) {
     ast_util::walk_pat(pat, |p| {
         match p.node {
@@ -252,7 +246,7 @@ fn check_for_bindings_named_the_same_as_variants(cx: &MatchCheckCtxt, pat: &Pat)
                                 "pattern binding `{}` is named the same as one \
                                  of the variants of the type `{}`",
                                 &token::get_ident(ident.node), ty_to_string(cx.tcx, pat_ty));
-                            span_help!(cx.tcx.sess, p.span,
+                            fileline_help!(cx.tcx.sess, p.span,
                                 "if you meant to match on a variant, \
                                  consider making the path in the pattern qualified: `{}::{}`",
                                 ty_to_string(cx.tcx, pat_ty), &token::get_ident(ident.node));
@@ -269,13 +263,26 @@ fn check_for_bindings_named_the_same_as_variants(cx: &MatchCheckCtxt, pat: &Pat)
 // Check that we do not match against a static NaN (#6804)
 fn check_for_static_nan(cx: &MatchCheckCtxt, pat: &Pat) {
     ast_util::walk_pat(pat, |p| {
-        match p.node {
-            ast::PatLit(ref expr) if is_expr_const_nan(cx.tcx, &**expr) => {
-                span_warn!(cx.tcx.sess, p.span, E0003,
-                    "unmatchable NaN in pattern, \
-                        use the is_nan method in a guard instead");
+        if let ast::PatLit(ref expr) = p.node {
+            match eval_const_expr_partial(cx.tcx, &**expr, None) {
+                Ok(const_float(f)) if f.is_nan() => {
+                    span_warn!(cx.tcx.sess, p.span, E0003,
+                               "unmatchable NaN in pattern, \
+                                use the is_nan method in a guard instead");
+                }
+                Ok(_) => {}
+
+                Err(err) => {
+                    let subspan = p.span.lo <= err.span.lo && err.span.hi <= p.span.hi;
+                    cx.tcx.sess.span_err(err.span,
+                                         &format!("constant evaluation error: {}",
+                                                  err.description()));
+                    if !subspan {
+                        cx.tcx.sess.span_note(p.span,
+                                              "in pattern here")
+                    }
+                }
             }
-            _ => ()
         }
         true
     });
index 0c9f9d2a5301aa2b94caf89aca8fba87f6c10006..f215b59a6cd0eda1bad552523440ab5c66c31eb6 100644 (file)
@@ -25,6 +25,8 @@
 use syntax::ptr::P;
 use syntax::{ast_map, ast_util, codemap};
 
+use std::borrow::{Cow, IntoCow};
+use std::num::wrapping::OverflowingOps;
 use std::cmp::Ordering;
 use std::collections::hash_map::Entry::Vacant;
 use std::{i8, i16, i32, i64};
@@ -77,7 +79,7 @@ fn variant_expr<'a>(variants: &'a [P<ast::Variant>], id: ast::NodeId)
             None => {}
         }
         let expr_id = match csearch::maybe_get_item_ast(tcx, enum_def,
-            box |a, b, c, d| astencode::decode_inlined_item(a, b, c, d)) {
+            Box::new(|a, b, c, d| astencode::decode_inlined_item(a, b, c, d))) {
             csearch::FoundAst::Found(&ast::IIItem(ref item)) => match item.node {
                 ast::ItemEnum(ast::EnumDef { ref variants }, _) => {
                     // NOTE this doesn't do the right thing, it compares inlined
@@ -117,7 +119,7 @@ pub fn lookup_const_by_id<'a>(tcx: &'a ty::ctxt, def_id: ast::DefId)
             None => {}
         }
         let expr_id = match csearch::maybe_get_item_ast(tcx, def_id,
-            box |a, b, c, d| astencode::decode_inlined_item(a, b, c, d)) {
+            Box::new(|a, b, c, d| astencode::decode_inlined_item(a, b, c, d))) {
             csearch::FoundAst::Found(&ast::IIItem(ref item)) => match item.node {
                 ast::ItemConst(_, ref const_expr) => Some(const_expr.id),
                 _ => None
@@ -202,35 +204,153 @@ pub fn const_expr_to_pat(tcx: &ty::ctxt, expr: &Expr, span: Span) -> P<ast::Pat>
 pub fn eval_const_expr(tcx: &ty::ctxt, e: &Expr) -> const_val {
     match eval_const_expr_partial(tcx, e, None) {
         Ok(r) => r,
-        Err(s) => tcx.sess.span_fatal(e.span, &s[..])
+        Err(s) => tcx.sess.span_fatal(s.span, &s.description())
     }
 }
 
+
+#[derive(Clone)]
+pub struct ConstEvalErr {
+    pub span: Span,
+    pub kind: ErrKind,
+}
+
+#[derive(Clone)]
+pub enum ErrKind {
+    CannotCast,
+    CannotCastTo(&'static str),
+    InvalidOpForBools(ast::BinOp_),
+    InvalidOpForFloats(ast::BinOp_),
+    InvalidOpForIntUint(ast::BinOp_),
+    InvalidOpForUintInt(ast::BinOp_),
+    NegateOnString,
+    NegateOnBoolean,
+    NegateOnBinary,
+    NotOnFloat,
+    NotOnString,
+    NotOnBinary,
+
+    AddiWithOverflow(i64, i64),
+    SubiWithOverflow(i64, i64),
+    MuliWithOverflow(i64, i64),
+    AdduWithOverflow(u64, u64),
+    SubuWithOverflow(u64, u64),
+    MuluWithOverflow(u64, u64),
+    DivideByZero,
+    DivideWithOverflow,
+    ModuloByZero,
+    ModuloWithOverflow,
+    MissingStructField,
+    NonConstPath,
+    NonConstStruct,
+    TupleIndexOutOfBounds,
+
+    MiscBinaryOp,
+    MiscCatchAll,
+}
+
+impl ConstEvalErr {
+    pub fn description(&self) -> Cow<str> {
+        use self::ErrKind::*;
+        match self.kind {
+            CannotCast => "can't cast this type".into_cow(),
+            CannotCastTo(s) => format!("can't cast this type to {}", s).into_cow(),
+            InvalidOpForBools(_) =>  "can't do this op on bools".into_cow(),
+            InvalidOpForFloats(_) => "can't do this op on floats".into_cow(),
+            InvalidOpForIntUint(..) => "can't do this op on an int and uint".into_cow(),
+            InvalidOpForUintInt(..) => "can't do this op on a uint and int".into_cow(),
+            NegateOnString => "negate on string".into_cow(),
+            NegateOnBoolean => "negate on boolean".into_cow(),
+            NegateOnBinary => "negate on binary literal".into_cow(),
+            NotOnFloat => "not on float or string".into_cow(),
+            NotOnString => "not on float or string".into_cow(),
+            NotOnBinary => "not on binary literal".into_cow(),
+
+            AddiWithOverflow(..) => "attempted to add with overflow".into_cow(),
+            SubiWithOverflow(..) => "attempted to sub with overflow".into_cow(),
+            MuliWithOverflow(..) => "attempted to mul with overflow".into_cow(),
+            AdduWithOverflow(..) => "attempted to add with overflow".into_cow(),
+            SubuWithOverflow(..) => "attempted to sub with overflow".into_cow(),
+            MuluWithOverflow(..) => "attempted to mul with overflow".into_cow(),
+            DivideByZero         => "attempted to divide by zero".into_cow(),
+            DivideWithOverflow   => "attempted to divide with overflow".into_cow(),
+            ModuloByZero         => "attempted remainder with a divisor of zero".into_cow(),
+            ModuloWithOverflow   => "attempted remainder with overflow".into_cow(),
+            MissingStructField  => "nonexistent struct field".into_cow(),
+            NonConstPath        => "non-constant path in constant expr".into_cow(),
+            NonConstStruct      => "non-constant struct in constant expr".into_cow(),
+            TupleIndexOutOfBounds => "tuple index out of bounds".into_cow(),
+
+            MiscBinaryOp => "bad operands for binary".into_cow(),
+            MiscCatchAll => "unsupported constant expr".into_cow(),
+        }
+    }
+}
+
+macro_rules! signal {
+    ($e:expr, $ctor:ident) => {
+        return Err(ConstEvalErr { span: $e.span, kind: ErrKind::$ctor })
+    };
+
+    ($e:expr, $ctor:ident($($arg:expr),*)) => {
+        return Err(ConstEvalErr { span: $e.span, kind: ErrKind::$ctor($($arg),*) })
+    }
+}
+
+fn checked_add_int(e: &Expr, a: i64, b: i64) -> Result<const_val, ConstEvalErr> {
+    let (ret, oflo) = a.overflowing_add(b);
+    if !oflo { Ok(const_int(ret)) } else { signal!(e, AddiWithOverflow(a, b)) }
+}
+fn checked_sub_int(e: &Expr, a: i64, b: i64) -> Result<const_val, ConstEvalErr> {
+    let (ret, oflo) = a.overflowing_sub(b);
+    if !oflo { Ok(const_int(ret)) } else { signal!(e, SubiWithOverflow(a, b)) }
+}
+fn checked_mul_int(e: &Expr, a: i64, b: i64) -> Result<const_val, ConstEvalErr> {
+    let (ret, oflo) = a.overflowing_mul(b);
+    if !oflo { Ok(const_int(ret)) } else { signal!(e, MuliWithOverflow(a, b)) }
+}
+
+fn checked_add_uint(e: &Expr, a: u64, b: u64) -> Result<const_val, ConstEvalErr> {
+    let (ret, oflo) = a.overflowing_add(b);
+    if !oflo { Ok(const_uint(ret)) } else { signal!(e, AdduWithOverflow(a, b)) }
+}
+fn checked_sub_uint(e: &Expr, a: u64, b: u64) -> Result<const_val, ConstEvalErr> {
+    let (ret, oflo) = a.overflowing_sub(b);
+    if !oflo { Ok(const_uint(ret)) } else { signal!(e, SubuWithOverflow(a, b)) }
+}
+fn checked_mul_uint(e: &Expr, a: u64, b: u64) -> Result<const_val, ConstEvalErr> {
+    let (ret, oflo) = a.overflowing_mul(b);
+    if !oflo { Ok(const_uint(ret)) } else { signal!(e, MuluWithOverflow(a, b)) }
+}
+
+
 pub fn eval_const_expr_partial<'tcx>(tcx: &ty::ctxt<'tcx>,
                                      e: &Expr,
                                      ty_hint: Option<Ty<'tcx>>)
-                                     -> Result<const_val, String> {
-    fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
+                                     -> Result<const_val, ConstEvalErr> {
+    fn fromb(b: bool) -> const_val { const_int(b as i64) }
 
     let ety = ty_hint.or_else(|| ty::expr_ty_opt(tcx, e));
 
-    match e.node {
+    let result = match e.node {
       ast::ExprUnary(ast::UnNeg, ref inner) => {
-        match eval_const_expr_partial(tcx, &**inner, ety) {
-          Ok(const_float(f)) => Ok(const_float(-f)),
-          Ok(const_int(i)) => Ok(const_int(-i)),
-          Ok(const_uint(i)) => Ok(const_uint(-i)),
-          Ok(const_str(_)) => Err("negate on string".to_string()),
-          Ok(const_bool(_)) => Err("negate on boolean".to_string()),
-          ref err => ((*err).clone())
+        match try!(eval_const_expr_partial(tcx, &**inner, ety)) {
+          const_float(f) => const_float(-f),
+          const_int(i) => const_int(-i),
+          const_uint(i) => const_uint(-i),
+          const_str(_) => signal!(e, NegateOnString),
+          const_bool(_) => signal!(e, NegateOnBoolean),
+          const_binary(_) => signal!(e, NegateOnBinary),
         }
       }
       ast::ExprUnary(ast::UnNot, ref inner) => {
-        match eval_const_expr_partial(tcx, &**inner, ety) {
-          Ok(const_int(i)) => Ok(const_int(!i)),
-          Ok(const_uint(i)) => Ok(const_uint(!i)),
-          Ok(const_bool(b)) => Ok(const_bool(!b)),
-          _ => Err("not on float or string".to_string())
+        match try!(eval_const_expr_partial(tcx, &**inner, ety)) {
+          const_int(i) => const_int(!i),
+          const_uint(i) => const_uint(!i),
+          const_bool(b) => const_bool(!b),
+          const_str(_) => signal!(e, NotOnString),
+          const_float(_) => signal!(e, NotOnFloat),
+          const_binary(_) => signal!(e, NotOnBinary),
         }
       }
       ast::ExprBinary(op, ref a, ref b) => {
@@ -238,25 +358,25 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
             ast::BiShl | ast::BiShr => Some(tcx.types.uint),
             _ => ety
         };
-        match (eval_const_expr_partial(tcx, &**a, ety),
-               eval_const_expr_partial(tcx, &**b, b_ty)) {
-          (Ok(const_float(a)), Ok(const_float(b))) => {
+        match (try!(eval_const_expr_partial(tcx, &**a, ety)),
+               try!(eval_const_expr_partial(tcx, &**b, b_ty))) {
+          (const_float(a), const_float(b)) => {
             match op.node {
-              ast::BiAdd => Ok(const_float(a + b)),
-              ast::BiSub => Ok(const_float(a - b)),
-              ast::BiMul => Ok(const_float(a * b)),
-              ast::BiDiv => Ok(const_float(a / b)),
-              ast::BiRem => Ok(const_float(a % b)),
+              ast::BiAdd => const_float(a + b),
+              ast::BiSub => const_float(a - b),
+              ast::BiMul => const_float(a * b),
+              ast::BiDiv => const_float(a / b),
+              ast::BiRem => const_float(a % b),
               ast::BiEq => fromb(a == b),
               ast::BiLt => fromb(a < b),
               ast::BiLe => fromb(a <= b),
               ast::BiNe => fromb(a != b),
               ast::BiGe => fromb(a >= b),
               ast::BiGt => fromb(a > b),
-              _ => Err("can't do this op on floats".to_string())
+              _ => signal!(e, InvalidOpForFloats(op.node))
             }
           }
-          (Ok(const_int(a)), Ok(const_int(b))) => {
+          (const_int(a), const_int(b)) => {
             let is_a_min_value = || {
                 let int_ty = match ty::expr_ty_opt(tcx, e).map(|ty| &ty.sty) {
                     Some(&ty::ty_int(int_ty)) => int_ty,
@@ -276,32 +396,32 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
                 }
             };
             match op.node {
-              ast::BiAdd => Ok(const_int(a + b)),
-              ast::BiSub => Ok(const_int(a - b)),
-              ast::BiMul => Ok(const_int(a * b)),
+              ast::BiAdd => try!(checked_add_int(e, a, b)),
+              ast::BiSub => try!(checked_sub_int(e, a, b)),
+              ast::BiMul => try!(checked_mul_int(e, a, b)),
               ast::BiDiv => {
                   if b == 0 {
-                      Err("attempted to divide by zero".to_string())
+                      signal!(e, DivideByZero);
                   } else if b == -1 && is_a_min_value() {
-                      Err("attempted to divide with overflow".to_string())
+                      signal!(e, DivideWithOverflow);
                   } else {
-                      Ok(const_int(a / b))
+                      const_int(a / b)
                   }
               }
               ast::BiRem => {
                   if b == 0 {
-                      Err("attempted remainder with a divisor of zero".to_string())
+                      signal!(e, ModuloByZero)
                   } else if b == -1 && is_a_min_value() {
-                      Err("attempted remainder with overflow".to_string())
+                      signal!(e, ModuloWithOverflow)
                   } else {
-                      Ok(const_int(a % b))
+                      const_int(a % b)
                   }
               }
-              ast::BiAnd | ast::BiBitAnd => Ok(const_int(a & b)),
-              ast::BiOr | ast::BiBitOr => Ok(const_int(a | b)),
-              ast::BiBitXor => Ok(const_int(a ^ b)),
-              ast::BiShl => Ok(const_int(a << b as uint)),
-              ast::BiShr => Ok(const_int(a >> b as uint)),
+              ast::BiAnd | ast::BiBitAnd => const_int(a & b),
+              ast::BiOr | ast::BiBitOr => const_int(a | b),
+              ast::BiBitXor => const_int(a ^ b),
+              ast::BiShl => const_int(a << b as uint),
+              ast::BiShr => const_int(a >> b as uint),
               ast::BiEq => fromb(a == b),
               ast::BiLt => fromb(a < b),
               ast::BiLe => fromb(a <= b),
@@ -310,25 +430,20 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
               ast::BiGt => fromb(a > b)
             }
           }
-          (Ok(const_uint(a)), Ok(const_uint(b))) => {
+          (const_uint(a), const_uint(b)) => {
             match op.node {
-              ast::BiAdd => Ok(const_uint(a + b)),
-              ast::BiSub => Ok(const_uint(a - b)),
-              ast::BiMul => Ok(const_uint(a * b)),
-              ast::BiDiv if b == 0 => {
-                  Err("attempted to divide by zero".to_string())
-              }
-              ast::BiDiv => Ok(const_uint(a / b)),
-              ast::BiRem if b == 0 => {
-                  Err("attempted remainder with a divisor of \
-                       zero".to_string())
-              }
-              ast::BiRem => Ok(const_uint(a % b)),
-              ast::BiAnd | ast::BiBitAnd => Ok(const_uint(a & b)),
-              ast::BiOr | ast::BiBitOr => Ok(const_uint(a | b)),
-              ast::BiBitXor => Ok(const_uint(a ^ b)),
-              ast::BiShl => Ok(const_uint(a << b as uint)),
-              ast::BiShr => Ok(const_uint(a >> b as uint)),
+              ast::BiAdd => try!(checked_add_uint(e, a, b)),
+              ast::BiSub => try!(checked_sub_uint(e, a, b)),
+              ast::BiMul => try!(checked_mul_uint(e, a, b)),
+              ast::BiDiv if b == 0 => signal!(e, DivideByZero),
+              ast::BiDiv => const_uint(a / b),
+              ast::BiRem if b == 0 => signal!(e, ModuloByZero),
+              ast::BiRem => const_uint(a % b),
+              ast::BiAnd | ast::BiBitAnd => const_uint(a & b),
+              ast::BiOr | ast::BiBitOr => const_uint(a | b),
+              ast::BiBitXor => const_uint(a ^ b),
+              ast::BiShl => const_uint(a << b as uint),
+              ast::BiShr => const_uint(a >> b as uint),
               ast::BiEq => fromb(a == b),
               ast::BiLt => fromb(a < b),
               ast::BiLe => fromb(a <= b),
@@ -338,22 +453,22 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
             }
           }
           // shifts can have any integral type as their rhs
-          (Ok(const_int(a)), Ok(const_uint(b))) => {
+          (const_int(a), const_uint(b)) => {
             match op.node {
-              ast::BiShl => Ok(const_int(a << b as uint)),
-              ast::BiShr => Ok(const_int(a >> b as uint)),
-              _ => Err("can't do this op on an int and uint".to_string())
+              ast::BiShl => const_int(a << b as uint),
+              ast::BiShr => const_int(a >> b as uint),
+              _ => signal!(e, InvalidOpForIntUint(op.node)),
             }
           }
-          (Ok(const_uint(a)), Ok(const_int(b))) => {
+          (const_uint(a), const_int(b)) => {
             match op.node {
-              ast::BiShl => Ok(const_uint(a << b as uint)),
-              ast::BiShr => Ok(const_uint(a >> b as uint)),
-              _ => Err("can't do this op on a uint and int".to_string())
+              ast::BiShl => const_uint(a << b as uint),
+              ast::BiShr => const_uint(a >> b as uint),
+              _ => signal!(e, InvalidOpForUintInt(op.node)),
             }
           }
-          (Ok(const_bool(a)), Ok(const_bool(b))) => {
-            Ok(const_bool(match op.node {
+          (const_bool(a), const_bool(b)) => {
+            const_bool(match op.node {
               ast::BiAnd => a && b,
               ast::BiOr => a || b,
               ast::BiBitXor => a ^ b,
@@ -361,10 +476,11 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
               ast::BiBitOr => a | b,
               ast::BiEq => a == b,
               ast::BiNe => a != b,
-              _ => return Err("can't do this op on bools".to_string())
-             }))
+              _ => signal!(e, InvalidOpForBools(op.node)),
+             })
           }
-          _ => Err("bad operands for binary".to_string())
+
+          _ => signal!(e, MiscBinaryOp),
         }
       }
       ast::ExprCast(ref base, ref target_ty) => {
@@ -379,7 +495,10 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
         // Prefer known type to noop, but always have a type hint.
         let base_hint = ty::expr_ty_opt(tcx, &**base).unwrap_or(ety);
         let val = try!(eval_const_expr_partial(tcx, &**base, Some(base_hint)));
-        cast_const(val, ety)
+        match cast_const(val, ety) {
+            Ok(val) => val,
+            Err(kind) => return Err(ConstEvalErr { span: e.span, kind: kind }),
+        }
       }
       ast::ExprPath(..) => {
           let opt_def = tcx.def_map.borrow().get(&e.id).map(|d| d.full_def());
@@ -406,19 +525,19 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
           };
           let const_expr = match const_expr {
               Some(actual_e) => actual_e,
-              None => return Err("non-constant path in constant expr".to_string())
+              None => signal!(e, NonConstPath)
           };
           let ety = ety.or_else(|| const_ty.and_then(|ty| ast_ty_to_prim_ty(tcx, ty)));
-          eval_const_expr_partial(tcx, const_expr, ety)
+          try!(eval_const_expr_partial(tcx, const_expr, ety))
       }
       ast::ExprLit(ref lit) => {
-          Ok(lit_to_const(&**lit, ety))
+          lit_to_const(&**lit, ety)
       }
-      ast::ExprParen(ref e)     => eval_const_expr_partial(tcx, &**e, ety),
+      ast::ExprParen(ref e) => try!(eval_const_expr_partial(tcx, &**e, ety)),
       ast::ExprBlock(ref block) => {
         match block.expr {
-            Some(ref expr) => eval_const_expr_partial(tcx, &**expr, ety),
-            None => Ok(const_int(0i64))
+            Some(ref expr) => try!(eval_const_expr_partial(tcx, &**expr, ety)),
+            None => const_int(0)
         }
       }
       ast::ExprTupField(ref base, index) => {
@@ -426,13 +545,13 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
         if let Some(&ast::ExprTup(ref fields)) = lookup_const(tcx, &**base).map(|s| &s.node) {
             // Check that the given index is within bounds and evaluate its value
             if fields.len() > index.node {
-                return eval_const_expr_partial(tcx, &*fields[index.node], None)
+                return eval_const_expr_partial(tcx, &*fields[index.node], None);
             } else {
-                return Err("tuple index out of bounds".to_string())
+                signal!(e, TupleIndexOutOfBounds);
             }
         }
 
-        Err("non-constant struct in constant expr".to_string())
+        signal!(e, NonConstStruct);
       }
       ast::ExprField(ref base, field_name) => {
         // Get the base expression if it is a struct and it is constant
@@ -441,19 +560,21 @@ fn fromb(b: bool) -> Result<const_val, String> { Ok(const_int(b as i64)) }
             // Check that the given field exists and evaluate it
             if let Some(f) = fields.iter().find(|f|
                                            f.ident.node.as_str() == field_name.node.as_str()) {
-                return eval_const_expr_partial(tcx, &*f.expr, None)
+                return eval_const_expr_partial(tcx, &*f.expr, None);
             } else {
-                return Err("nonexistent struct field".to_string())
+                signal!(e, MissingStructField);
             }
         }
 
-        Err("non-constant struct in constant expr".to_string())
+        signal!(e, NonConstStruct);
       }
-      _ => Err("unsupported constant expr".to_string())
-    }
+      _ => signal!(e, MiscCatchAll)
+    };
+
+    Ok(result)
 }
 
-fn cast_const(val: const_val, ty: Ty) -> Result<const_val, String> {
+fn cast_const(val: const_val, ty: Ty) -> Result<const_val, ErrKind> {
     macro_rules! define_casts {
         ($($ty_pat:pat => (
             $intermediate_ty:ty,
@@ -466,11 +587,10 @@ macro_rules! define_casts {
                     const_uint(u) => Ok($const_type(u as $intermediate_ty as $target_ty)),
                     const_int(i) => Ok($const_type(i as $intermediate_ty as $target_ty)),
                     const_float(f) => Ok($const_type(f as $intermediate_ty as $target_ty)),
-                    _ => Err(concat!("can't cast this type to ",
-                                     stringify!($const_type)).to_string())
+                    _ => Err(ErrKind::CannotCastTo(stringify!($const_type))),
                 }
             },)*
-            _ => Err("can't cast this type".to_string())
+            _ => Err(ErrKind::CannotCast),
         })
     }
 
@@ -544,15 +664,15 @@ pub fn compare_lit_exprs<'tcx>(tcx: &ty::ctxt<'tcx>,
                                -> Option<Ordering> {
     let a = match eval_const_expr_partial(tcx, a, ty_hint) {
         Ok(a) => a,
-        Err(s) => {
-            tcx.sess.span_err(a.span, &s[..]);
+        Err(e) => {
+            tcx.sess.span_err(a.span, &e.description());
             return None;
         }
     };
     let b = match eval_const_expr_partial(tcx, b, ty_hint) {
         Ok(b) => b,
-        Err(s) => {
-            tcx.sess.span_err(b.span, &s[..]);
+        Err(e) => {
+            tcx.sess.span_err(b.span, &e.description());
             return None;
         }
     };
index 1718df702553f0f94886f0b365fd880ad55ad439..a1ce8d18184e3e47af087755ad6192fff48bc8c9 100644 (file)
@@ -19,7 +19,7 @@
 use middle::cfg;
 use middle::cfg::CFGIndex;
 use middle::ty;
-use std::old_io;
+use std::io;
 use std::usize;
 use std::iter::repeat;
 use syntax::ast;
@@ -103,7 +103,7 @@ fn has_bitset_for_nodeid(&self, n: ast::NodeId) -> bool {
 impl<'a, 'tcx, O:DataFlowOperator> pprust::PpAnn for DataFlowContext<'a, 'tcx, O> {
     fn pre(&self,
            ps: &mut pprust::State,
-           node: pprust::AnnNode) -> old_io::IoResult<()> {
+           node: pprust::AnnNode) -> io::Result<()> {
         let id = match node {
             pprust::NodeIdent(_) | pprust::NodeName(_) => 0,
             pprust::NodeExpr(expr) => expr.id,
@@ -205,7 +205,7 @@ pub fn new(tcx: &'a ty::ctxt<'tcx>,
                oper: O,
                id_range: IdRange,
                bits_per_id: uint) -> DataFlowContext<'a, 'tcx, O> {
-        let words_per_id = (bits_per_id + usize::BITS - 1) / usize::BITS;
+        let words_per_id = (bits_per_id + usize::BITS as usize - 1) / usize::BITS as usize;
         let num_nodes = cfg.graph.all_nodes().len();
 
         debug!("DataFlowContext::new(analysis_name: {}, id_range={:?}, \
@@ -377,7 +377,7 @@ fn each_bit<F>(&self, words: &[uint], mut f: F) -> bool where
 
         for (word_index, &word) in words.iter().enumerate() {
             if word != 0 {
-                let base_index = word_index * usize::BITS;
+                let base_index = word_index * usize::BITS as usize;
                 for offset in 0..usize::BITS {
                     let bit = 1 << offset;
                     if (word & bit) != 0 {
@@ -390,7 +390,7 @@ fn each_bit<F>(&self, words: &[uint], mut f: F) -> bool where
                         // whether the bit_index is greater than the
                         // actual value the user specified and stop
                         // iterating if so.
-                        let bit_index = base_index + offset;
+                        let bit_index = base_index + offset as usize;
                         if bit_index >= self.bits_per_id {
                             return true;
                         } else if !f(bit_index) {
@@ -485,13 +485,15 @@ pub fn propagate(&mut self, cfg: &cfg::CFG, blk: &ast::Block) {
 
         debug!("Dataflow result for {}:", self.analysis_name);
         debug!("{}", {
-            self.pretty_print_to(box old_io::stderr(), blk).unwrap();
+            let mut v = Vec::new();
+            self.pretty_print_to(box &mut v, blk).unwrap();
+            println!("{}", String::from_utf8(v).unwrap());
             ""
         });
     }
 
-    fn pretty_print_to(&self, wr: Box<old_io::Writer+'static>,
-                       blk: &ast::Block) -> old_io::IoResult<()> {
+    fn pretty_print_to<'b>(&self, wr: Box<io::Write + 'b>,
+                           blk: &ast::Block) -> io::Result<()> {
         let mut ps = pprust::rust_printer_annotated(wr, self);
         try!(ps.cbox(pprust::indent_unit));
         try!(ps.ibox(0));
@@ -609,8 +611,8 @@ fn bitwise<Op:BitwiseOperator>(out_vec: &mut [uint],
 fn set_bit(words: &mut [uint], bit: uint) -> bool {
     debug!("set_bit: words={} bit={}",
            mut_bits_to_string(words), bit_str(bit));
-    let word = bit / usize::BITS;
-    let bit_in_word = bit % usize::BITS;
+    let word = bit / usize::BITS as usize;
+    let bit_in_word = bit % usize::BITS as usize;
     let bit_mask = 1 << bit_in_word;
     debug!("word={} bit_in_word={} bit_mask={}", word, bit_in_word, word);
     let oldv = words[word];
index 7584a2e44cc7c0b3316be2718c153705e530ec03..063845c6c34255df36dcf0dad2fc04c8bb2c39d3 100644 (file)
@@ -74,7 +74,7 @@ pub fn simplify_type(tcx: &ty::ctxt,
             let def_id = tcx.lang_items.owned_box().unwrap();
             Some(StructSimplifiedType(def_id))
         }
-        ty::ty_closure(def_id, _, _) => {
+        ty::ty_closure(def_id, _) => {
             Some(ClosureSimplifiedType(def_id))
         }
         ty::ty_tup(ref tys) => {
index b782a655d89ff11155bf156793000776a9c6bbed..be94a73df37ba82d7b4c02c4427b8a58588ef67b 100644 (file)
@@ -503,15 +503,14 @@ pub fn super_tys<'tcx, C>(this: &C,
             Ok(ty::mk_struct(tcx, a_id, tcx.mk_substs(substs)))
         }
 
-        (&ty::ty_closure(a_id, a_region, a_substs),
-         &ty::ty_closure(b_id, b_region, b_substs))
+        (&ty::ty_closure(a_id, a_substs),
+         &ty::ty_closure(b_id, b_substs))
           if a_id == b_id => {
             // All ty_closure types with the same id represent
             // the (anonymous) type of the same closure expression. So
             // all of their regions should be equated.
-            let region = try!(this.equate().regions(*a_region, *b_region));
             let substs = try!(this.substs_variances(None, a_substs, b_substs));
-            Ok(ty::mk_closure(tcx, a_id, tcx.mk_region(region), tcx.mk_substs(substs)))
+            Ok(ty::mk_closure(tcx, a_id, tcx.mk_substs(substs)))
         }
 
         (&ty::ty_uniq(a_inner), &ty::ty_uniq(b_inner)) => {
index da4df813030c3ab504f228b24935a4f1d5b4a79f..a7f5c2c843711b6aec3a2d2a6fec0ae25156ab56 100644 (file)
@@ -444,7 +444,7 @@ fn report_generic_bound_failure(&self,
                 // Does the required lifetime have a nice name we can print?
                 span_err!(self.tcx.sess, origin.span(), E0309,
                     "{} may not live long enough", labeled_user_string);
-                self.tcx.sess.span_help(
+                self.tcx.sess.fileline_help(
                     origin.span(),
                     &format!(
                         "consider adding an explicit lifetime bound `{}: {}`...",
@@ -456,7 +456,7 @@ fn report_generic_bound_failure(&self,
                 // Does the required lifetime have a nice name we can print?
                 span_err!(self.tcx.sess, origin.span(), E0310,
                     "{} may not live long enough", labeled_user_string);
-                self.tcx.sess.span_help(
+                self.tcx.sess.fileline_help(
                     origin.span(),
                     &format!(
                         "consider adding an explicit lifetime bound `{}: 'static`...",
@@ -468,7 +468,7 @@ fn report_generic_bound_failure(&self,
                 span_err!(self.tcx.sess, origin.span(), E0311,
                         "{} may not live long enough",
                         labeled_user_string);
-                self.tcx.sess.span_help(
+                self.tcx.sess.fileline_help(
                     origin.span(),
                     &format!(
                         "consider adding an explicit lifetime bound for `{}`",
index 43cd1fc8edbac83b87300390c0678087cb335dee..6211fde79198af387731e8c3840abedef50a42b3 100644 (file)
 
 use std::borrow::Cow;
 use std::collections::hash_map::Entry::Vacant;
-use std::old_io::{self, File};
 use std::env;
+use std::fs::File;
+use std::io;
+use std::io::prelude::*;
 use std::sync::atomic::{AtomicBool, Ordering, ATOMIC_BOOL_INIT};
 use syntax::ast;
 
@@ -256,10 +258,11 @@ fn target(&self, edge: &Edge) -> Node {
 
 fn dump_region_constraints_to<'a, 'tcx:'a >(tcx: &'a ty::ctxt<'tcx>,
                                             map: &ConstraintMap<'tcx>,
-                                            path: &str) -> old_io::IoResult<()> {
+                                            path: &str) -> io::Result<()> {
     debug!("dump_region_constraints map (len: {}) path: {}", map.len(), path);
     let g = ConstraintGraph::new(tcx, format!("region_constraints"), map);
-    let mut f = File::create(&Path::new(path));
     debug!("dump_region_constraints calling render");
-    dot::render(&g, &mut f)
+    let mut v = Vec::new();
+    dot::render(&g, &mut v).unwrap();
+    File::create(path).and_then(|mut f| f.write_all(&v))
 }
index 56c5928a132b14cd56ac92d19588bc227c912c55..3525d46a1f2f1ee02070a104642ac10e03676be3 100644 (file)
@@ -71,7 +71,7 @@ pub fn items<'a>(&'a self) -> Enumerate<slice::Iter<'a, Option<ast::DefId>>> {
     }
 
     pub fn item_name(index: uint) -> &'static str {
-        let item: Option<LangItem> = FromPrimitive::from_uint(index);
+        let item: Option<LangItem> = FromPrimitive::from_usize(index);
         match item {
             $( Some($variant) => $name, )*
             None => "???"
index 5cb034667cc64ad9ffa982e4f753f37f63b8edc2..892452ccc1c29d3b348a94ec1880a33baa562c55 100644 (file)
@@ -540,9 +540,9 @@ struct Specials {
     clean_exit_var: Variable
 }
 
-static ACC_READ: u32 = 1;
-static ACC_WRITE: u32 = 2;
-static ACC_USE: u32 = 4;
+const ACC_READ: u32 = 1;
+const ACC_WRITE: u32 = 2;
+const ACC_USE: u32 = 4;
 
 struct Liveness<'a, 'tcx: 'a> {
     ir: &'a mut IrMaps<'a, 'tcx>,
@@ -1496,7 +1496,7 @@ impl<'a, 'tcx> Liveness<'a, 'tcx> {
     fn fn_ret(&self, id: NodeId) -> ty::PolyFnOutput<'tcx> {
         let fn_ty = ty::node_id_to_type(self.ir.tcx, id);
         match fn_ty.sty {
-            ty::ty_closure(closure_def_id, _, substs) =>
+            ty::ty_closure(closure_def_id, substs) =>
                 self.ir.tcx.closure_type(closure_def_id, substs).sig.output(),
             _ =>
                 ty::ty_fn_ret(fn_ty),
index c4446b87855ca622d6a5ebd4fcca78f7ca0b9042..1f02f13a4a17823312e934e27c912d5e8a7e45e0 100644 (file)
@@ -607,7 +607,7 @@ pub fn cat_def(&self,
           def::DefUpvar(var_id, fn_node_id) => {
               let ty = try!(self.node_ty(fn_node_id));
               match ty.sty {
-                  ty::ty_closure(closure_id, _, _) => {
+                  ty::ty_closure(closure_id, _) => {
                       match self.typer.closure_kind(closure_id) {
                           Some(kind) => {
                               self.cat_upvar(id, span, var_id, fn_node_id, kind)
index 7db1138ac72f6e58a168ce6ca3fb08719141208b..b4db3aba7867dc72cbaec8a3519dd07c5725a32f 100644 (file)
@@ -320,8 +320,10 @@ fn to_code_extent(&self) -> Option<CodeExtent> {
 
 #[derive(Debug, Copy)]
 pub struct Context {
+    /// the scope that contains any new variables declared
     var_parent: InnermostDeclaringBlock,
 
+    /// region parent of expressions etc
     parent: InnermostEnclosingExpr,
 }
 
index ddac6cc75143ba85ab176ab3a5d89b013f2884c0..3599ba5a0f779a4c2eb2f5ff0bd5a604ab65f017 100644 (file)
@@ -362,8 +362,6 @@ pub fn check_item(tcx: &ty::ctxt, item: &ast::Item, warn_about_defns: bool,
 /// Helper for discovering nodes to check for stability
 pub fn check_expr(tcx: &ty::ctxt, e: &ast::Expr,
                   cb: &mut FnMut(ast::DefId, Span, &Option<Stability>)) {
-    if is_internal(tcx, e.span) { return; }
-
     let span;
     let id = match e.node {
         ast::ExprMethodCall(i, _, _) => {
@@ -527,12 +525,13 @@ pub fn check_pat(tcx: &ty::ctxt, pat: &ast::Pat,
 fn maybe_do_stability_check(tcx: &ty::ctxt, id: ast::DefId, span: Span,
                             cb: &mut FnMut(ast::DefId, Span, &Option<Stability>)) {
     if !is_staged_api(tcx, id) { return  }
+    if is_internal(tcx, span) { return }
     let ref stability = lookup(tcx, id);
     cb(id, span, stability);
 }
 
 fn is_internal(tcx: &ty::ctxt, span: Span) -> bool {
-    tcx.sess.codemap().span_is_internal(span)
+    tcx.sess.codemap().span_allows_unstable(span)
 }
 
 fn is_staged_api(tcx: &ty::ctxt, id: DefId) -> bool {
index 5a5639c701291f54716eba3b701e76f8bc825786..f46cac308287ba769d34378ddc19421d5aee3233 100644 (file)
@@ -280,7 +280,11 @@ pub struct VtableBuiltinData<N> {
 /// for the object type `Foo`.
 #[derive(PartialEq,Eq,Clone)]
 pub struct VtableObjectData<'tcx> {
+    /// the object type `Foo`.
     pub object_ty: Ty<'tcx>,
+
+    /// `Foo` upcast to the obligation trait. This will be some supertrait of `Foo`.
+    pub upcast_trait_ref: ty::PolyTraitRef<'tcx>,
 }
 
 /// Creates predicate obligations from the generic bounds.
index 64835a666faef46d6fe23c518d88108d5dbe7663..881487a2dad1150b6e9423075c14fbfb042258db 100644 (file)
@@ -22,7 +22,7 @@
 
 use middle::subst::{self, SelfSpace, TypeSpace};
 use middle::traits;
-use middle::ty::{self, Ty};
+use middle::ty::{self, ToPolyTraitRef, Ty};
 use std::rc::Rc;
 use syntax::ast;
 use util::ppaux::Repr;
@@ -128,9 +128,12 @@ fn supertraits_reference_self<'tcx>(tcx: &ty::ctxt<'tcx>,
 {
     let trait_def = ty::lookup_trait_def(tcx, trait_def_id);
     let trait_ref = trait_def.trait_ref.clone();
-    let predicates = ty::predicates_for_trait_ref(tcx, &ty::Binder(trait_ref));
+    let trait_ref = trait_ref.to_poly_trait_ref();
+    let predicates = ty::lookup_super_predicates(tcx, trait_def_id);
     predicates
+        .predicates
         .into_iter()
+        .map(|predicate| predicate.subst_supertrait(tcx, &trait_ref))
         .any(|predicate| {
             match predicate {
                 ty::Predicate::Trait(ref data) => {
index 7d4febb38e678186ff6b5380f55e53ec20bb1a2c..b9a863f4fe46f51738edc029115ad6dca2304fe6 100644 (file)
@@ -154,7 +154,7 @@ fn consider_unification_despite_ambiguity<'cx,'tcx>(selcx: &mut SelectionContext
     debug!("consider_unification_despite_ambiguity: self_ty.sty={:?}",
            self_ty.sty);
     match self_ty.sty {
-        ty::ty_closure(closure_def_id, _, substs) => {
+        ty::ty_closure(closure_def_id, substs) => {
             let closure_typer = selcx.closure_typer();
             let closure_type = closure_typer.closure_type(closure_def_id, substs);
             let ty::Binder((_, ret_type)) =
index d8c62780a781fa124bbb02ca0ea3b0dc35a673a5..7dfbccea0dccd160f4c8ecfb6a0470083d6c28c1 100644 (file)
@@ -293,7 +293,7 @@ fn consider_unification_despite_ambiguity(&mut self, obligation: &TraitObligatio
         // lifetimes can appear inside the self-type.
         let self_ty = self.infcx.shallow_resolve(obligation.self_ty());
         let (closure_def_id, substs) = match self_ty.sty {
-            ty::ty_closure(id, _, ref substs) => (id, substs.clone()),
+            ty::ty_closure(id, ref substs) => (id, substs.clone()),
             _ => { return; }
         };
         assert!(!substs.has_escaping_regions());
@@ -1054,7 +1054,7 @@ fn assemble_closure_candidates(&mut self,
 
         let self_ty = self.infcx.shallow_resolve(obligation.self_ty());
         let (closure_def_id, substs) = match self_ty.sty {
-            ty::ty_closure(id, _, ref substs) => (id, substs.clone()),
+            ty::ty_closure(id, ref substs) => (id, substs.clone()),
             ty::ty_infer(ty::TyVar(_)) => {
                 debug!("assemble_unboxed_closure_candidates: ambiguous self-type");
                 candidates.ambiguous = true;
@@ -1260,19 +1260,11 @@ fn assemble_candidates_from_object_ty(&mut self,
                poly_trait_ref.repr(self.tcx()));
 
         // see whether the object trait can be upcast to the trait we are looking for
-        let obligation_def_id = obligation.predicate.def_id();
-        let upcast_trait_ref = match util::upcast(self.tcx(), poly_trait_ref, obligation_def_id) {
-            Some(r) => r,
-            None => { return; }
-        };
-
-        debug!("assemble_candidates_from_object_ty: upcast_trait_ref={}",
-               upcast_trait_ref.repr(self.tcx()));
-
-        // check whether the upcast version of the trait-ref matches what we are looking for
-        if let Ok(()) = self.infcx.probe(|_| self.match_poly_trait_ref(obligation,
-                                                                       upcast_trait_ref.clone())) {
-            debug!("assemble_candidates_from_object_ty: matched, pushing candidate");
+        let upcast_trait_refs = self.upcast(poly_trait_ref, obligation);
+        if upcast_trait_refs.len() > 1 {
+            // can be upcast in many ways; need more type information
+            candidates.ambiguous = true;
+        } else if upcast_trait_refs.len() == 1 {
             candidates.vec.push(ObjectCandidate);
         }
     }
@@ -1455,9 +1447,9 @@ fn builtin_bound(&mut self,
                             let principal =
                                 data.principal_trait_ref_with_self_ty(self.tcx(),
                                                                       self.tcx().types.err);
+                            let desired_def_id = obligation.predicate.def_id();
                             for tr in util::supertraits(self.tcx(), principal) {
-                                let td = ty::lookup_trait_def(self.tcx(), tr.def_id());
-                                if td.bounds.builtin_bounds.contains(&bound) {
+                                if tr.def_id() == desired_def_id {
                                     return Ok(If(Vec::new()))
                                 }
                             }
@@ -1533,7 +1525,7 @@ fn builtin_bound(&mut self,
             // (T1, ..., Tn) -- meets any bound that all of T1...Tn meet
             ty::ty_tup(ref tys) => Ok(If(tys.clone())),
 
-            ty::ty_closure(def_id, _, substs) => {
+            ty::ty_closure(def_id, substs) => {
                 // FIXME -- This case is tricky. In the case of by-ref
                 // closures particularly, we need the results of
                 // inference to decide how to reflect the type of each
@@ -1687,7 +1679,7 @@ fn constituent_types_for_ty(&self, t: Ty<'tcx>) -> Option<Vec<Ty<'tcx>>> {
                 Some(tys.clone())
             }
 
-            ty::ty_closure(def_id, _, substs) => {
+            ty::ty_closure(def_id, substs) => {
                 assert_eq!(def_id.krate, ast::LOCAL_CRATE);
 
                 match self.closure_typer.closure_upvars(def_id, substs) {
@@ -1700,6 +1692,13 @@ fn constituent_types_for_ty(&self, t: Ty<'tcx>) -> Option<Vec<Ty<'tcx>>> {
                 }
             }
 
+            // for `PhantomData<T>`, we pass `T`
+            ty::ty_struct(def_id, substs)
+                if Some(def_id) == self.tcx().lang_items.phantom_data() =>
+            {
+                Some(substs.types.get_slice(TypeSpace).to_vec())
+            }
+
             ty::ty_struct(def_id, substs) => {
                 Some(ty::struct_fields(self.tcx(), def_id, substs).iter()
                      .map(|f| f.mt.ty)
@@ -2063,20 +2062,15 @@ fn confirm_object_candidate(&mut self,
             }
         };
 
-        let obligation_def_id = obligation.predicate.def_id();
-        let upcast_trait_ref = match util::upcast(self.tcx(),
-                                                  poly_trait_ref.clone(),
-                                                  obligation_def_id) {
-            Some(r) => r,
-            None => {
-                self.tcx().sess.span_bug(obligation.cause.span,
-                                         &format!("unable to upcast from {} to {}",
-                                                  poly_trait_ref.repr(self.tcx()),
-                                                  obligation_def_id.repr(self.tcx())));
-            }
-        };
+        // Upcast the object type to the obligation type. There must
+        // be exactly one applicable trait-reference; if this were not
+        // the case, we would have reported an ambiguity error rather
+        // than successfully selecting one of the candidates.
+        let upcast_trait_refs = self.upcast(poly_trait_ref.clone(), obligation);
+        assert_eq!(upcast_trait_refs.len(), 1);
+        let upcast_trait_ref = upcast_trait_refs.into_iter().next().unwrap();
 
-        match self.match_poly_trait_ref(obligation, upcast_trait_ref) {
+        match self.match_poly_trait_ref(obligation, upcast_trait_ref.clone()) {
             Ok(()) => { }
             Err(()) => {
                 self.tcx().sess.span_bug(obligation.cause.span,
@@ -2084,7 +2078,8 @@ fn confirm_object_candidate(&mut self,
             }
         }
 
-        VtableObjectData { object_ty: self_ty }
+        VtableObjectData { object_ty: self_ty,
+                           upcast_trait_ref: upcast_trait_ref }
     }
 
     fn confirm_fn_pointer_candidate(&mut self,
@@ -2501,6 +2496,32 @@ fn derived_cause(&self,
             obligation.cause.clone()
         }
     }
+
+    /// Upcasts an object trait-reference into those that match the obligation.
+    fn upcast(&mut self, obj_trait_ref: ty::PolyTraitRef<'tcx>, obligation: &TraitObligation<'tcx>)
+              -> Vec<ty::PolyTraitRef<'tcx>>
+    {
+        debug!("upcast(obj_trait_ref={}, obligation={})",
+               obj_trait_ref.repr(self.tcx()),
+               obligation.repr(self.tcx()));
+
+        let obligation_def_id = obligation.predicate.def_id();
+        let mut upcast_trait_refs = util::upcast(self.tcx(), obj_trait_ref, obligation_def_id);
+
+        // Retain only those upcast versions that match the trait-ref
+        // we are looking for.  In particular, we know that all of
+        // `upcast_trait_refs` apply to the correct trait, but
+        // possibly with incorrect type parameters. For example, we
+        // may be trying to upcast `Foo` to `Bar<i32>`, but `Foo` is
+        // declared as `trait Foo : Bar<u32>`.
+        upcast_trait_refs.retain(|upcast_trait_ref| {
+            let upcast_trait_ref = upcast_trait_ref.clone();
+            self.infcx.probe(|_| self.match_poly_trait_ref(obligation, upcast_trait_ref)).is_ok()
+        });
+
+        debug!("upcast: upcast_trait_refs={}", upcast_trait_refs.repr(self.tcx()));
+        upcast_trait_refs
+    }
 }
 
 impl<'tcx> Repr<'tcx> for SelectionCandidate<'tcx> {
index 7bef5f32475d39153033ebfef81c471b7aebcb5e..4527985302aedaddb31493dae3e51b40e9a2181b 100644 (file)
@@ -76,15 +76,10 @@ fn insert(&mut self, pred: &ty::Predicate<'tcx>) -> bool {
 /// 'static`.
 pub struct Elaborator<'cx, 'tcx:'cx> {
     tcx: &'cx ty::ctxt<'tcx>,
-    stack: Vec<StackEntry<'tcx>>,
+    stack: Vec<ty::Predicate<'tcx>>,
     visited: PredicateSet<'cx,'tcx>,
 }
 
-struct StackEntry<'tcx> {
-    position: uint,
-    predicates: Vec<ty::Predicate<'tcx>>,
-}
-
 pub fn elaborate_trait_ref<'cx, 'tcx>(
     tcx: &'cx ty::ctxt<'tcx>,
     trait_ref: ty::PolyTraitRef<'tcx>)
@@ -111,21 +106,28 @@ pub fn elaborate_predicates<'cx, 'tcx>(
 {
     let mut visited = PredicateSet::new(tcx);
     predicates.retain(|pred| visited.insert(pred));
-    let entry = StackEntry { position: 0, predicates: predicates };
-    Elaborator { tcx: tcx, stack: vec![entry], visited: visited }
+    Elaborator { tcx: tcx, stack: predicates, visited: visited }
 }
 
 impl<'cx, 'tcx> Elaborator<'cx, 'tcx> {
-    pub fn filter_to_traits(self) -> Supertraits<'cx, 'tcx> {
-        Supertraits { elaborator: self }
+    pub fn filter_to_traits(self) -> FilterToTraits<Elaborator<'cx, 'tcx>> {
+        FilterToTraits::new(self)
     }
 
     fn push(&mut self, predicate: &ty::Predicate<'tcx>) {
         match *predicate {
             ty::Predicate::Trait(ref data) => {
-                let mut predicates =
-                    ty::predicates_for_trait_ref(self.tcx,
-                                                 &data.to_poly_trait_ref());
+                // Predicates declared on the trait.
+                let predicates = ty::lookup_super_predicates(self.tcx, data.def_id());
+
+                let mut predicates: Vec<_> =
+                    predicates.predicates
+                              .iter()
+                              .map(|p| p.subst_supertrait(self.tcx, &data.to_poly_trait_ref()))
+                              .collect();
+
+                debug!("super_predicates: data={} predicates={}",
+                       data.repr(self.tcx), predicates.repr(self.tcx));
 
                 // Only keep those bounds that we haven't already
                 // seen.  This is necessary to prevent infinite
@@ -134,8 +136,7 @@ fn push(&mut self, predicate: &ty::Predicate<'tcx>) {
                 // Sized { }`.
                 predicates.retain(|r| self.visited.insert(r));
 
-                self.stack.push(StackEntry { position: 0,
-                                             predicates: predicates });
+                self.stack.extend(predicates.into_iter());
             }
             ty::Predicate::Equate(..) => {
                 // Currently, we do not "elaborate" predicates like
@@ -175,41 +176,16 @@ impl<'cx, 'tcx> Iterator for Elaborator<'cx, 'tcx> {
     type Item = ty::Predicate<'tcx>;
 
     fn next(&mut self) -> Option<ty::Predicate<'tcx>> {
-        loop {
-            // Extract next item from top-most stack frame, if any.
-            let next_predicate = match self.stack.last_mut() {
-                None => {
-                    // No more stack frames. Done.
-                    return None;
-                }
-                Some(entry) => {
-                    let p = entry.position;
-                    if p < entry.predicates.len() {
-                        // Still more predicates left in the top stack frame.
-                        entry.position += 1;
-
-                        let next_predicate =
-                            entry.predicates[p].clone();
-
-                        Some(next_predicate)
-                    } else {
-                        None
-                    }
-                }
-            };
-
-            match next_predicate {
-                Some(next_predicate) => {
-                    self.push(&next_predicate);
-                    return Some(next_predicate);
-                }
-
-                None => {
-                    // Top stack frame is exhausted, pop it.
-                    self.stack.pop();
-                }
+        // Extract next item from top-most stack frame, if any.
+        let next_predicate = match self.stack.pop() {
+            Some(predicate) => predicate,
+            None => {
+                // No more stack frames. Done.
+                return None;
             }
-        }
+        };
+        self.push(&next_predicate);
+        return Some(next_predicate);
     }
 }
 
@@ -217,11 +193,7 @@ fn next(&mut self) -> Option<ty::Predicate<'tcx>> {
 // Supertrait iterator
 ///////////////////////////////////////////////////////////////////////////
 
-/// A filter around the `Elaborator` that just yields up supertrait references,
-/// not other kinds of predicates.
-pub struct Supertraits<'cx, 'tcx:'cx> {
-    elaborator: Elaborator<'cx, 'tcx>,
-}
+pub type Supertraits<'cx, 'tcx> = FilterToTraits<Elaborator<'cx, 'tcx>>;
 
 pub fn supertraits<'cx, 'tcx>(tcx: &'cx ty::ctxt<'tcx>,
                               trait_ref: ty::PolyTraitRef<'tcx>)
@@ -237,12 +209,28 @@ pub fn transitive_bounds<'cx, 'tcx>(tcx: &'cx ty::ctxt<'tcx>,
     elaborate_trait_refs(tcx, bounds).filter_to_traits()
 }
 
-impl<'cx, 'tcx> Iterator for Supertraits<'cx, 'tcx> {
+///////////////////////////////////////////////////////////////////////////
+// Other
+///////////////////////////////////////////////////////////////////////////
+
+/// A filter around an iterator of predicates that makes it yield up
+/// just trait references.
+pub struct FilterToTraits<I> {
+    base_iterator: I
+}
+
+impl<I> FilterToTraits<I> {
+    fn new(base: I) -> FilterToTraits<I> {
+        FilterToTraits { base_iterator: base }
+    }
+}
+
+impl<'tcx,I:Iterator<Item=ty::Predicate<'tcx>>> Iterator for FilterToTraits<I> {
     type Item = ty::PolyTraitRef<'tcx>;
 
     fn next(&mut self) -> Option<ty::PolyTraitRef<'tcx>> {
         loop {
-            match self.elaborator.next() {
+            match self.base_iterator.next() {
                 None => {
                     return None;
                 }
@@ -256,6 +244,7 @@ fn next(&mut self) -> Option<ty::PolyTraitRef<'tcx>> {
     }
 }
 
+
 ///////////////////////////////////////////////////////////////////////////
 // Other
 ///////////////////////////////////////////////////////////////////////////
@@ -370,19 +359,15 @@ pub fn predicate_for_builtin_bound<'tcx>(
 pub fn upcast<'tcx>(tcx: &ty::ctxt<'tcx>,
                     source_trait_ref: ty::PolyTraitRef<'tcx>,
                     target_trait_def_id: ast::DefId)
-                    -> Option<ty::PolyTraitRef<'tcx>>
+                    -> Vec<ty::PolyTraitRef<'tcx>>
 {
     if source_trait_ref.def_id() == target_trait_def_id {
-        return Some(source_trait_ref); // shorcut the most common case
-    }
-
-    for super_trait_ref in supertraits(tcx, source_trait_ref) {
-        if super_trait_ref.def_id() == target_trait_def_id {
-            return Some(super_trait_ref);
-        }
+        return vec![source_trait_ref]; // shorcut the most common case
     }
 
-    None
+    supertraits(tcx, source_trait_ref)
+        .filter(|r| r.def_id() == target_trait_def_id)
+        .collect()
 }
 
 /// Given an object of type `object_trait_ref`, returns the index of
index 635ec09d3394cd52039a4ebba05b6bf026b45e86..4cb4d343de758f3e9cb4b31d40586aa3d57cdbf1 100644 (file)
@@ -17,7 +17,6 @@
 pub use self::InferRegion::*;
 pub use self::ImplOrTraitItemId::*;
 pub use self::ClosureKind::*;
-pub use self::ast_ty_to_ty_cache_entry::*;
 pub use self::Variance::*;
 pub use self::AutoAdjustment::*;
 pub use self::Representability::*;
@@ -76,7 +75,7 @@
 use std::mem;
 use std::ops;
 use std::rc::Rc;
-use std::vec::{CowVec, IntoIter};
+use std::vec::IntoIter;
 use collections::enum_set::{EnumSet, CLike};
 use std::collections::{HashMap, HashSet};
 use syntax::abi;
@@ -266,12 +265,6 @@ pub struct creader_cache_key {
     pub len: uint
 }
 
-#[derive(Copy)]
-pub enum ast_ty_to_ty_cache_entry<'tcx> {
-    atttce_unresolved,  /* not resolved yet */
-    atttce_resolved(Ty<'tcx>)  /* resolved to a type, irrespective of region */
-}
-
 #[derive(Clone, PartialEq, RustcDecodable, RustcEncodable)]
 pub struct ItemVariances {
     pub types: VecPerParamSpace<Variance>,
@@ -716,6 +709,14 @@ pub struct ctxt<'tcx> {
     /// associated predicates.
     pub predicates: RefCell<DefIdMap<GenericPredicates<'tcx>>>,
 
+    /// Maps from the def-id of a trait to the list of
+    /// super-predicates. This is a subset of the full list of
+    /// predicates. We store these in a separate map because we must
+    /// evaluate them even during type conversion, often before the
+    /// full predicates are available (note that supertraits have
+    /// additional acyclicity requirements).
+    pub super_predicates: RefCell<DefIdMap<GenericPredicates<'tcx>>>,
+
     /// Maps from node-id of a trait object cast (like `foo as
     /// Box<Trait>`) to the trait reference.
     pub object_cast_map: ObjectCastMap<'tcx>,
@@ -727,7 +728,7 @@ pub struct ctxt<'tcx> {
     pub rcache: RefCell<FnvHashMap<creader_cache_key, Ty<'tcx>>>,
     pub short_names_cache: RefCell<FnvHashMap<Ty<'tcx>, String>>,
     pub tc_cache: RefCell<FnvHashMap<Ty<'tcx>, TypeContents>>,
-    pub ast_ty_to_ty_cache: RefCell<NodeMap<ast_ty_to_ty_cache_entry<'tcx>>>,
+    pub ast_ty_to_ty_cache: RefCell<NodeMap<Ty<'tcx>>>,
     pub enum_var_cache: RefCell<DefIdMap<Rc<Vec<Rc<VariantInfo<'tcx>>>>>>,
     pub ty_param_defs: RefCell<NodeMap<TypeParameterDef<'tcx>>>,
     pub adjustments: RefCell<NodeMap<AutoAdjustment<'tcx>>>,
@@ -756,8 +757,8 @@ pub struct ctxt<'tcx> {
     /// Maps a trait onto a list of impls of that trait.
     pub trait_impls: RefCell<DefIdMap<Rc<RefCell<Vec<ast::DefId>>>>>,
 
-    /// Maps a trait onto a list of *default* trait implementations
-    default_trait_impls: RefCell<DefIdMap<ast::DefId>>,
+    /// A set of traits that have a default impl
+    traits_with_default_impls: RefCell<DefIdMap<()>>,
 
     /// Maps a DefId of a type to a list of its inherent impls.
     /// Contains implementations of methods that are inherent to a type.
@@ -1352,7 +1353,7 @@ pub enum sty<'tcx> {
     /// definition and not a concrete use of it. To get the correct `ty_enum`
     /// from the tcx, use the `NodeId` from the `ast::Ty` and look it up in
     /// the `ast_ty_to_ty_cache`. This is probably true for `ty_struct` as
-    /// well.`
+    /// well.
     ty_enum(DefId, &'tcx Substs<'tcx>),
     ty_uniq(Ty<'tcx>),
     ty_str,
@@ -1367,7 +1368,7 @@ pub enum sty<'tcx> {
     ty_trait(Box<TyTrait<'tcx>>),
     ty_struct(DefId, &'tcx Substs<'tcx>),
 
-    ty_closure(DefId, &'tcx Region, &'tcx Substs<'tcx>),
+    ty_closure(DefId, &'tcx Substs<'tcx>),
 
     ty_tup(Vec<Ty<'tcx>>),
 
@@ -1495,6 +1496,27 @@ pub fn to_poly_trait_predicate(&self) -> PolyTraitPredicate<'tcx> {
 #[derive(Clone, PartialEq, Eq, Hash, Debug)]
 pub struct Binder<T>(pub T);
 
+impl<T> Binder<T> {
+    /// Skips the binder and returns the "bound" value. This is a
+    /// risky thing to do because it's easy to get confused about
+    /// debruijn indices and the like. It is usually better to
+    /// discharge the binder using `no_late_bound_regions` or
+    /// `replace_late_bound_regions` or something like
+    /// that. `skip_binder` is only valid when you are either
+    /// extracting data that has nothing to do with bound regions, you
+    /// are doing some sort of test that does not involve bound
+    /// regions, or you are being very careful about your depth
+    /// accounting.
+    ///
+    /// Some examples where `skip_binder` is reasonable:
+    /// - extracting the def-id from a PolyTraitRef;
+    /// - comparing the self type of a PolyTraitRef to see if it is equal to
+    ///   a type parameter `X`, since the type `X`  does not reference any regions
+    pub fn skip_binder(&self) -> &T {
+        &self.0
+    }
+}
+
 #[derive(Clone, Copy, PartialEq)]
 pub enum IntVarValue {
     IntType(ast::IntTy),
@@ -1817,6 +1839,16 @@ pub fn instantiate(&self, tcx: &ty::ctxt<'tcx>, substs: &Substs<'tcx>)
             predicates: self.predicates.subst(tcx, substs),
         }
     }
+
+    pub fn instantiate_supertrait(&self,
+                                  tcx: &ty::ctxt<'tcx>,
+                                  poly_trait_ref: &ty::PolyTraitRef<'tcx>)
+                                  -> InstantiatedPredicates<'tcx>
+    {
+        InstantiatedPredicates {
+            predicates: self.predicates.map(|pred| pred.subst_supertrait(tcx, poly_trait_ref))
+        }
+    }
 }
 
 #[derive(Clone, PartialEq, Eq, Hash, Debug)]
@@ -1840,6 +1872,93 @@ pub enum Predicate<'tcx> {
     Projection(PolyProjectionPredicate<'tcx>),
 }
 
+impl<'tcx> Predicate<'tcx> {
+    /// Performs a substituion suitable for going from a
+    /// poly-trait-ref to supertraits that must hold if that
+    /// poly-trait-ref holds. This is slightly different from a normal
+    /// substitution in terms of what happens with bound regions.  See
+    /// lengthy comment below for details.
+    pub fn subst_supertrait(&self,
+                            tcx: &ty::ctxt<'tcx>,
+                            trait_ref: &ty::PolyTraitRef<'tcx>)
+                            -> ty::Predicate<'tcx>
+    {
+        // The interaction between HRTB and supertraits is not entirely
+        // obvious. Let me walk you (and myself) through an example.
+        //
+        // Let's start with an easy case. Consider two traits:
+        //
+        //     trait Foo<'a> : Bar<'a,'a> { }
+        //     trait Bar<'b,'c> { }
+        //
+        // Now, if we have a trait reference `for<'x> T : Foo<'x>`, then
+        // we can deduce that `for<'x> T : Bar<'x,'x>`. Basically, if we
+        // knew that `Foo<'x>` (for any 'x) then we also know that
+        // `Bar<'x,'x>` (for any 'x). This more-or-less falls out from
+        // normal substitution.
+        //
+        // In terms of why this is sound, the idea is that whenever there
+        // is an impl of `T:Foo<'a>`, it must show that `T:Bar<'a,'a>`
+        // holds.  So if there is an impl of `T:Foo<'a>` that applies to
+        // all `'a`, then we must know that `T:Bar<'a,'a>` holds for all
+        // `'a`.
+        //
+        // Another example to be careful of is this:
+        //
+        //     trait Foo1<'a> : for<'b> Bar1<'a,'b> { }
+        //     trait Bar1<'b,'c> { }
+        //
+        // Here, if we have `for<'x> T : Foo1<'x>`, then what do we know?
+        // The answer is that we know `for<'x,'b> T : Bar1<'x,'b>`. The
+        // reason is similar to the previous example: any impl of
+        // `T:Foo1<'x>` must show that `for<'b> T : Bar1<'x, 'b>`.  So
+        // basically we would want to collapse the bound lifetimes from
+        // the input (`trait_ref`) and the supertraits.
+        //
+        // To achieve this in practice is fairly straightforward. Let's
+        // consider the more complicated scenario:
+        //
+        // - We start out with `for<'x> T : Foo1<'x>`. In this case, `'x`
+        //   has a De Bruijn index of 1. We want to produce `for<'x,'b> T : Bar1<'x,'b>`,
+        //   where both `'x` and `'b` would have a DB index of 1.
+        //   The substitution from the input trait-ref is therefore going to be
+        //   `'a => 'x` (where `'x` has a DB index of 1).
+        // - The super-trait-ref is `for<'b> Bar1<'a,'b>`, where `'a` is an
+        //   early-bound parameter and `'b' is a late-bound parameter with a
+        //   DB index of 1.
+        // - If we replace `'a` with `'x` from the input, it too will have
+        //   a DB index of 1, and thus we'll have `for<'x,'b> Bar1<'x,'b>`
+        //   just as we wanted.
+        //
+        // There is only one catch. If we just apply the substitution `'a
+        // => 'x` to `for<'b> Bar1<'a,'b>`, the substitution code will
+        // adjust the DB index because we substituting into a binder (it
+        // tries to be so smart...) resulting in `for<'x> for<'b>
+        // Bar1<'x,'b>` (we have no syntax for this, so use your
+        // imagination). Basically the 'x will have DB index of 2 and 'b
+        // will have DB index of 1. Not quite what we want. So we apply
+        // the substitution to the *contents* of the trait reference,
+        // rather than the trait reference itself (put another way, the
+        // substitution code expects equal binding levels in the values
+        // from the substitution and the value being substituted into, and
+        // this trick achieves that).
+
+        let substs = &trait_ref.0.substs;
+        match *self {
+            Predicate::Trait(ty::Binder(ref data)) =>
+                Predicate::Trait(ty::Binder(data.subst(tcx, substs))),
+            Predicate::Equate(ty::Binder(ref data)) =>
+                Predicate::Equate(ty::Binder(data.subst(tcx, substs))),
+            Predicate::RegionOutlives(ty::Binder(ref data)) =>
+                Predicate::RegionOutlives(ty::Binder(data.subst(tcx, substs))),
+            Predicate::TypeOutlives(ty::Binder(ref data)) =>
+                Predicate::TypeOutlives(ty::Binder(data.subst(tcx, substs))),
+            Predicate::Projection(ty::Binder(ref data)) =>
+                Predicate::Projection(ty::Binder(data.subst(tcx, substs))),
+        }
+    }
+}
+
 #[derive(Clone, PartialEq, Eq, Hash, Debug)]
 pub struct TraitPredicate<'tcx> {
     pub trait_ref: Rc<TraitRef<'tcx>>
@@ -2324,9 +2443,6 @@ pub struct TraitDef<'tcx> {
     /// implements the trait.
     pub generics: Generics<'tcx>,
 
-    /// The "supertrait" bounds.
-    pub bounds: ParamBounds<'tcx>,
-
     pub trait_ref: Rc<ty::TraitRef<'tcx>>,
 
     /// A list of the associated types defined in this trait. Useful
@@ -2451,6 +2567,7 @@ pub fn mk_ctxt<'tcx>(s: Session,
         impl_trait_refs: RefCell::new(NodeMap()),
         trait_defs: RefCell::new(DefIdMap()),
         predicates: RefCell::new(DefIdMap()),
+        super_predicates: RefCell::new(DefIdMap()),
         object_cast_map: RefCell::new(NodeMap()),
         map: map,
         intrinsic_defs: RefCell::new(DefIdMap()),
@@ -2474,7 +2591,7 @@ pub fn mk_ctxt<'tcx>(s: Session,
         destructor_for_type: RefCell::new(DefIdMap()),
         destructors: RefCell::new(DefIdSet()),
         trait_impls: RefCell::new(DefIdMap()),
-        default_trait_impls: RefCell::new(DefIdMap()),
+        traits_with_default_impls: RefCell::new(DefIdMap()),
         inherent_impls: RefCell::new(DefIdMap()),
         impl_items: RefCell::new(DefIdMap()),
         used_unsafe: RefCell::new(NodeSet()),
@@ -2658,8 +2775,7 @@ fn add_sty(&mut self, st: &sty) {
                 }
             }
 
-            &ty_closure(_, region, substs) => {
-                self.add_region(*region);
+            &ty_closure(_, substs) => {
                 self.add_substs(substs);
             }
 
@@ -2927,10 +3043,9 @@ pub fn mk_struct<'tcx>(cx: &ctxt<'tcx>, struct_id: ast::DefId,
     mk_t(cx, ty_struct(struct_id, substs))
 }
 
-pub fn mk_closure<'tcx>(cx: &ctxt<'tcx>, closure_id: ast::DefId,
-                        region: &'tcx Region, substs: &'tcx Substs<'tcx>)
+pub fn mk_closure<'tcx>(cx: &ctxt<'tcx>, closure_id: ast::DefId, substs: &'tcx Substs<'tcx>)
                         -> Ty<'tcx> {
-    mk_t(cx, ty_closure(closure_id, region, substs))
+    mk_t(cx, ty_closure(closure_id, substs))
 }
 
 pub fn mk_var<'tcx>(cx: &ctxt<'tcx>, v: TyVid) -> Ty<'tcx> {
@@ -3513,13 +3628,11 @@ fn tc_ty<'tcx>(cx: &ctxt<'tcx>,
                 apply_lang_items(cx, did, res)
             }
 
-            ty_closure(did, r, substs) => {
+            ty_closure(did, substs) => {
                 // FIXME(#14449): `borrowed_contents` below assumes `&mut` closure.
                 let param_env = ty::empty_parameter_environment(cx);
                 let upvars = closure_upvars(&param_env, did, substs).unwrap();
-                TypeContents::union(&upvars,
-                                    |f| tc_ty(cx, &f.ty, cache))
-                    | borrowed_contents(*r, MutMutable)
+                TypeContents::union(&upvars, |f| tc_ty(cx, &f.ty, cache))
             }
 
             ty_tup(ref tys) => {
@@ -5175,7 +5288,7 @@ pub fn ty_to_def_id(ty: Ty) -> Option<ast::DefId> {
             Some(tt.principal_def_id()),
         ty_struct(id, _) |
         ty_enum(id, _) |
-        ty_closure(id, _, _) =>
+        ty_closure(id, _) =>
             Some(id),
         _ =>
             None
@@ -5337,6 +5450,7 @@ pub fn type_is_empty(cx: &ctxt, ty: Ty) -> bool {
 
 pub fn enum_variants<'tcx>(cx: &ctxt<'tcx>, id: ast::DefId)
                            -> Rc<Vec<Rc<VariantInfo<'tcx>>>> {
+    use std::num::Int; // For checked_add
     memoized(&cx.enum_var_cache, id, |id: ast::DefId| {
         if ast::LOCAL_CRATE != id.krate {
             Rc::new(csearch::get_enum_variants(cx, id))
@@ -5353,11 +5467,7 @@ pub fn enum_variants<'tcx>(cx: &ctxt<'tcx>, id: ast::DefId)
                             let mut last_discriminant: Option<Disr> = None;
                             Rc::new(enum_definition.variants.iter().map(|variant| {
 
-                                let mut discriminant = match last_discriminant {
-                                    Some(val) => val + 1,
-                                    None => INITIAL_DISCRIMINANT_VALUE
-                                };
-
+                                let mut discriminant = INITIAL_DISCRIMINANT_VALUE;
                                 if let Some(ref e) = variant.node.disr_expr {
                                     // Preserve all values, and prefer signed.
                                     let ty = Some(cx.types.i64);
@@ -5373,11 +5483,24 @@ pub fn enum_variants<'tcx>(cx: &ctxt<'tcx>, id: ast::DefId)
                                                       "expected signed integer constant");
                                         }
                                         Err(err) => {
-                                            span_err!(cx.sess, e.span, E0305,
-                                                      "expected constant: {}", err);
+                                            span_err!(cx.sess, err.span, E0305,
+                                                      "constant evaluation error: {}",
+                                                      err.description());
+                                        }
+                                    }
+                                } else {
+                                    if let Some(val) = last_discriminant {
+                                        if let Some(v) = val.checked_add(1) {
+                                            discriminant = v
+                                        } else {
+                                            cx.sess.span_err(
+                                                variant.span,
+                                                &format!("Discriminant overflowed!"));
                                         }
+                                    } else {
+                                        discriminant = INITIAL_DISCRIMINANT_VALUE;
                                     }
-                                };
+                                }
 
                                 last_discriminant = Some(discriminant);
                                 Rc::new(VariantInfo::from_ast_variant(cx, &**variant,
@@ -5426,7 +5549,7 @@ pub fn lookup_trait_def<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
     })
 }
 
-/// Given the did of a trait, returns its full set of predicates.
+/// Given the did of an item, returns its full set of predicates.
 pub fn lookup_predicates<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
                                 -> GenericPredicates<'tcx>
 {
@@ -5436,117 +5559,14 @@ pub fn lookup_predicates<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
     })
 }
 
-/// Given a reference to a trait, returns the "superbounds" declared
-/// on the trait, with appropriate substitutions applied. Basically,
-/// this applies a filter to the where clauses on the trait, returning
-/// those that have the form:
-///
-///     Self : SuperTrait<...>
-///     Self : 'region
-pub fn predicates_for_trait_ref<'tcx>(tcx: &ctxt<'tcx>,
-                                      trait_ref: &PolyTraitRef<'tcx>)
-                                      -> Vec<ty::Predicate<'tcx>>
+/// Given the did of a trait, returns its superpredicates.
+pub fn lookup_super_predicates<'tcx>(cx: &ctxt<'tcx>, did: ast::DefId)
+                                     -> GenericPredicates<'tcx>
 {
-    let trait_def = lookup_trait_def(tcx, trait_ref.def_id());
-
-    debug!("bounds_for_trait_ref(trait_def={:?}, trait_ref={:?})",
-           trait_def.repr(tcx), trait_ref.repr(tcx));
-
-    // The interaction between HRTB and supertraits is not entirely
-    // obvious. Let me walk you (and myself) through an example.
-    //
-    // Let's start with an easy case. Consider two traits:
-    //
-    //     trait Foo<'a> : Bar<'a,'a> { }
-    //     trait Bar<'b,'c> { }
-    //
-    // Now, if we have a trait reference `for<'x> T : Foo<'x>`, then
-    // we can deduce that `for<'x> T : Bar<'x,'x>`. Basically, if we
-    // knew that `Foo<'x>` (for any 'x) then we also know that
-    // `Bar<'x,'x>` (for any 'x). This more-or-less falls out from
-    // normal substitution.
-    //
-    // In terms of why this is sound, the idea is that whenever there
-    // is an impl of `T:Foo<'a>`, it must show that `T:Bar<'a,'a>`
-    // holds.  So if there is an impl of `T:Foo<'a>` that applies to
-    // all `'a`, then we must know that `T:Bar<'a,'a>` holds for all
-    // `'a`.
-    //
-    // Another example to be careful of is this:
-    //
-    //     trait Foo1<'a> : for<'b> Bar1<'a,'b> { }
-    //     trait Bar1<'b,'c> { }
-    //
-    // Here, if we have `for<'x> T : Foo1<'x>`, then what do we know?
-    // The answer is that we know `for<'x,'b> T : Bar1<'x,'b>`. The
-    // reason is similar to the previous example: any impl of
-    // `T:Foo1<'x>` must show that `for<'b> T : Bar1<'x, 'b>`.  So
-    // basically we would want to collapse the bound lifetimes from
-    // the input (`trait_ref`) and the supertraits.
-    //
-    // To achieve this in practice is fairly straightforward. Let's
-    // consider the more complicated scenario:
-    //
-    // - We start out with `for<'x> T : Foo1<'x>`. In this case, `'x`
-    //   has a De Bruijn index of 1. We want to produce `for<'x,'b> T : Bar1<'x,'b>`,
-    //   where both `'x` and `'b` would have a DB index of 1.
-    //   The substitution from the input trait-ref is therefore going to be
-    //   `'a => 'x` (where `'x` has a DB index of 1).
-    // - The super-trait-ref is `for<'b> Bar1<'a,'b>`, where `'a` is an
-    //   early-bound parameter and `'b' is a late-bound parameter with a
-    //   DB index of 1.
-    // - If we replace `'a` with `'x` from the input, it too will have
-    //   a DB index of 1, and thus we'll have `for<'x,'b> Bar1<'x,'b>`
-    //   just as we wanted.
-    //
-    // There is only one catch. If we just apply the substitution `'a
-    // => 'x` to `for<'b> Bar1<'a,'b>`, the substitution code will
-    // adjust the DB index because we substituting into a binder (it
-    // tries to be so smart...) resulting in `for<'x> for<'b>
-    // Bar1<'x,'b>` (we have no syntax for this, so use your
-    // imagination). Basically the 'x will have DB index of 2 and 'b
-    // will have DB index of 1. Not quite what we want. So we apply
-    // the substitution to the *contents* of the trait reference,
-    // rather than the trait reference itself (put another way, the
-    // substitution code expects equal binding levels in the values
-    // from the substitution and the value being substituted into, and
-    // this trick achieves that).
-
-    // Carefully avoid the binder introduced by each trait-ref by
-    // substituting over the substs, not the trait-refs themselves,
-    // thus achieving the "collapse" described in the big comment
-    // above.
-    let trait_bounds: Vec<_> =
-        trait_def.bounds.trait_bounds
-        .iter()
-        .map(|poly_trait_ref| ty::Binder(poly_trait_ref.0.subst(tcx, trait_ref.substs())))
-        .collect();
-
-    let projection_bounds: Vec<_> =
-        trait_def.bounds.projection_bounds
-        .iter()
-        .map(|poly_proj| ty::Binder(poly_proj.0.subst(tcx, trait_ref.substs())))
-        .collect();
-
-    debug!("bounds_for_trait_ref: trait_bounds={} projection_bounds={}",
-           trait_bounds.repr(tcx),
-           projection_bounds.repr(tcx));
-
-    // The region bounds and builtin bounds do not currently introduce
-    // binders so we can just substitute in a straightforward way here.
-    let region_bounds =
-        trait_def.bounds.region_bounds.subst(tcx, trait_ref.substs());
-    let builtin_bounds =
-        trait_def.bounds.builtin_bounds.subst(tcx, trait_ref.substs());
-
-    let bounds = ty::ParamBounds {
-        trait_bounds: trait_bounds,
-        region_bounds: region_bounds,
-        builtin_bounds: builtin_bounds,
-        projection_bounds: projection_bounds,
-    };
-
-    predicates(tcx, trait_ref.self_ty(), &bounds)
+    memoized(&cx.super_predicates, did, |did: DefId| {
+        assert!(did.krate != ast::LOCAL_CRATE);
+        csearch::get_super_predicates(cx, did)
+    })
 }
 
 pub fn predicates<'tcx>(
@@ -5584,10 +5604,9 @@ pub fn predicates<'tcx>(
 
 /// Get the attributes of a definition.
 pub fn get_attrs<'tcx>(tcx: &'tcx ctxt, did: DefId)
-                       -> CowVec<'tcx, ast::Attribute> {
+                       -> Cow<'tcx, [ast::Attribute]> {
     if is_local(did) {
-        let item = tcx.map.expect_item(did.node);
-        Cow::Borrowed(&item.attrs)
+        Cow::Borrowed(tcx.map.attrs(did.node))
     } else {
         Cow::Owned(csearch::get_item_attrs(&tcx.sess.cstore, did))
     }
@@ -5757,22 +5776,22 @@ pub fn closure_upvars<'tcx>(typer: &mc::Typer<'tcx>,
 
 pub fn is_binopable<'tcx>(cx: &ctxt<'tcx>, ty: Ty<'tcx>, op: ast::BinOp) -> bool {
     #![allow(non_upper_case_globals)]
-    static tycat_other: int = 0;
-    static tycat_bool: int = 1;
-    static tycat_char: int = 2;
-    static tycat_int: int = 3;
-    static tycat_float: int = 4;
-    static tycat_raw_ptr: int = 6;
-
-    static opcat_add: int = 0;
-    static opcat_sub: int = 1;
-    static opcat_mult: int = 2;
-    static opcat_shift: int = 3;
-    static opcat_rel: int = 4;
-    static opcat_eq: int = 5;
-    static opcat_bit: int = 6;
-    static opcat_logic: int = 7;
-    static opcat_mod: int = 8;
+    const tycat_other: int = 0;
+    const tycat_bool: int = 1;
+    const tycat_char: int = 2;
+    const tycat_int: int = 3;
+    const tycat_float: int = 4;
+    const tycat_raw_ptr: int = 6;
+
+    const opcat_add: int = 0;
+    const opcat_sub: int = 1;
+    const opcat_mult: int = 2;
+    const opcat_shift: int = 3;
+    const opcat_rel: int = 4;
+    const opcat_eq: int = 5;
+    const opcat_bit: int = 6;
+    const opcat_logic: int = 7;
+    const opcat_mod: int = 8;
 
     fn opcat(op: ast::BinOp) -> int {
         match op.node {
@@ -5811,8 +5830,8 @@ fn tycat<'tcx>(cx: &ctxt<'tcx>, ty: Ty<'tcx>) -> int {
         }
     }
 
-    static t: bool = true;
-    static f: bool = false;
+    const t: bool = true;
+    const f: bool = false;
 
     let tbl = [
     //           +, -, *, shift, rel, ==, bit, logic, mod
@@ -5955,32 +5974,22 @@ pub fn item_variances(tcx: &ctxt, item_id: ast::DefId) -> Rc<ItemVariances> {
         || Rc::new(csearch::get_item_variances(&tcx.sess.cstore, item_id)))
 }
 
-pub fn trait_default_impl(tcx: &ctxt, trait_def_id: DefId) -> Option<ast::DefId> {
-    match tcx.default_trait_impls.borrow().get(&trait_def_id) {
-        Some(id) => Some(*id),
-        None => None
-    }
-}
-
 pub fn trait_has_default_impl(tcx: &ctxt, trait_def_id: DefId) -> bool {
+    populate_implementations_for_trait_if_necessary(tcx, trait_def_id);
     match tcx.lang_items.to_builtin_kind(trait_def_id) {
         Some(BoundSend) | Some(BoundSync) => true,
-        _ => tcx.default_trait_impls.borrow().contains_key(&trait_def_id)
+        _ => tcx.traits_with_default_impls.borrow().contains_key(&trait_def_id),
     }
 }
 
 /// Records a trait-to-implementation mapping.
-pub fn record_default_trait_implementation(tcx: &ctxt,
-                                           trait_def_id: DefId,
-                                           impl_def_id: DefId) {
-
+pub fn record_trait_has_default_impl(tcx: &ctxt, trait_def_id: DefId) {
     // We're using the latest implementation found as the reference one.
     // Duplicated implementations are caught and reported in the coherence
     // step.
-    tcx.default_trait_impls.borrow_mut().insert(trait_def_id, impl_def_id);
+    tcx.traits_with_default_impls.borrow_mut().insert(trait_def_id, ());
 }
 
-
 /// Records a trait-to-implementation mapping.
 pub fn record_trait_implementation(tcx: &ctxt,
                                    trait_def_id: DefId,
@@ -6011,8 +6020,7 @@ pub fn populate_implementations_for_type_if_necessary(tcx: &ctxt,
     debug!("populate_implementations_for_type_if_necessary: searching for {:?}", type_id);
 
     let mut inherent_impls = Vec::new();
-    csearch::each_implementation_for_type(&tcx.sess.cstore, type_id,
-            |impl_def_id| {
+    csearch::each_implementation_for_type(&tcx.sess.cstore, type_id, |impl_def_id| {
         let impl_items = csearch::get_impl_items(&tcx.sess.cstore, impl_def_id);
 
         // Record the trait->implementation mappings, if applicable.
@@ -6058,27 +6066,20 @@ pub fn populate_implementations_for_trait_if_necessary(
     if trait_id.krate == LOCAL_CRATE {
         return
     }
+
     if tcx.populated_external_traits.borrow().contains(&trait_id) {
         return
     }
 
-    csearch::each_implementation_for_trait(&tcx.sess.cstore, trait_id,
-            |implementation_def_id|{
-        let impl_items = csearch::get_impl_items(&tcx.sess.cstore, implementation_def_id);
+    if csearch::is_defaulted_trait(&tcx.sess.cstore, trait_id) {
+        record_trait_has_default_impl(tcx, trait_id);
+    }
 
-        if csearch::is_default_trait(&tcx.sess.cstore, implementation_def_id) {
-            record_default_trait_implementation(tcx, trait_id,
-                                                implementation_def_id);
-            tcx.populated_external_traits.borrow_mut().insert(trait_id);
+    csearch::each_implementation_for_trait(&tcx.sess.cstore, trait_id, |implementation_def_id| {
+        let impl_items = csearch::get_impl_items(&tcx.sess.cstore, implementation_def_id);
 
-            // Nothing else to do for default trait implementations since
-            // they are not allowed to have type parameters, methods, or any
-            // other item that could be associated to a trait implementation.
-            return;
-        } else {
-            // Record the trait->implementation mapping.
-            record_trait_implementation(tcx, trait_id, implementation_def_id);
-        }
+        // Record the trait->implementation mapping.
+        record_trait_implementation(tcx, trait_id, implementation_def_id);
 
         // For any methods that use a default implementation, add them to
         // the map. This is a bit unfortunate.
@@ -6088,8 +6089,8 @@ pub fn populate_implementations_for_trait_if_necessary(
                 MethodTraitItem(method) => {
                     if let Some(source) = method.provided_source {
                         tcx.provided_method_sources
-                           .borrow_mut()
-                           .insert(method_def_id, source);
+                            .borrow_mut()
+                            .insert(method_def_id, source);
                     }
                 }
                 TypeTraitItem(_) => {}
@@ -6301,10 +6302,9 @@ macro_rules! hash { ($e:expr) => { $e.hash(state) }  }
                 }
                 ty_infer(_) => unreachable!(),
                 ty_err => byte!(21),
-                ty_closure(d, r, _) => {
+                ty_closure(d, _) => {
                     byte!(22);
                     did(state, d);
-                    region(state, *r);
                 }
                 ty_projection(ref data) => {
                     byte!(23);
@@ -6618,8 +6618,7 @@ pub fn accumulate_lifetimes_in_type(accumulator: &mut Vec<ty::Region>,
             ty_struct(_, substs) => {
                 accum_substs(accumulator, substs);
             }
-            ty_closure(_, region, substs) => {
-                accumulator.push(*region);
+            ty_closure(_, substs) => {
                 accum_substs(accumulator, substs);
             }
             ty_bool |
index 4bf47c3a75f8003761a99ca641a540b8ae4a7f96..f3a7c1ee6a0c8fe673dd306120041a47c8e8798b 100644 (file)
@@ -544,7 +544,8 @@ fn fold_with<F:TypeFolder<'tcx>>(&self, folder: &mut F) -> traits::Vtable<'tcx,
 impl<'tcx> TypeFoldable<'tcx> for traits::VtableObjectData<'tcx> {
     fn fold_with<F:TypeFolder<'tcx>>(&self, folder: &mut F) -> traits::VtableObjectData<'tcx> {
         traits::VtableObjectData {
-            object_ty: self.object_ty.fold_with(folder)
+            object_ty: self.object_ty.fold_with(folder),
+            upcast_trait_ref: self.upcast_trait_ref.fold_with(folder),
         }
     }
 }
@@ -650,10 +651,9 @@ pub fn super_fold_ty<'tcx, T: TypeFolder<'tcx>>(this: &mut T,
             let substs = substs.fold_with(this);
             ty::ty_struct(did, this.tcx().mk_substs(substs))
         }
-        ty::ty_closure(did, ref region, ref substs) => {
-            let r = region.fold_with(this);
+        ty::ty_closure(did, ref substs) => {
             let s = substs.fold_with(this);
-            ty::ty_closure(did, this.tcx().mk_region(r), this.tcx().mk_substs(s))
+            ty::ty_closure(did, this.tcx().mk_substs(s))
         }
         ty::ty_projection(ref data) => {
             ty::ty_projection(data.fold_with(this))
index 3336e7ee8bf71e6186107a989782913d8dd13f2f..5b5eac451783a8502edb0844d53bd9c221dde5bf 100644 (file)
@@ -45,7 +45,7 @@ fn push_subtypes(&mut self, parent_ty: Ty<'tcx>) {
             }
             ty::ty_enum(_, ref substs) |
             ty::ty_struct(_, ref substs) |
-            ty::ty_closure(_, _, ref substs) => {
+            ty::ty_closure(_, ref substs) => {
                 self.push_reversed(substs.types.as_slice());
             }
             ty::ty_tup(ref ts) => {
index a419d4134b40e4677faba9b0355848ccc5e1b98a..8267b79ff9e7aee3432559ea0e18f621a5ecf317 100644 (file)
 use metadata::creader::CrateReader;
 use plugin::registry::Registry;
 
-use std::mem;
-use std::os;
-use std::dynamic_lib::DynamicLibrary;
 use std::borrow::ToOwned;
+use std::dynamic_lib::DynamicLibrary;
+use std::env;
+use std::mem;
+use std::old_path;
+use std::path::PathBuf;
 use syntax::ast;
 use syntax::codemap::{Span, COMMAND_LINE_SP};
 use syntax::ptr::P;
@@ -100,10 +102,11 @@ fn load_plugin(&mut self, span: Span, name: &str, args: Vec<P<ast::MetaItem>>) {
     // Dynamically link a registrar function into the compiler process.
     fn dylink_registrar(&mut self,
                         span: Span,
-                        path: Path,
+                        path: PathBuf,
                         symbol: String) -> PluginRegistrarFun {
         // Make sure the path contains a / or the linker will search for it.
-        let path = os::getcwd().unwrap().join(&path);
+        let path = env::current_dir().unwrap().join(&path);
+        let path = old_path::Path::new(path.to_str().unwrap());
 
         let lib = match DynamicLibrary::open(Some(&path)) {
             Ok(lib) => lib,
index 12634204f8b12f2bd31c02dc36d8ccf8b973c8c1..78f7b3b91ddf74d5c9935466183229933fd87dda 100644 (file)
@@ -81,8 +81,12 @@ pub fn args<'b>(&'b self) -> &'b Vec<P<ast::MetaItem>> {
     /// This is the most general hook into `libsyntax`'s expansion behavior.
     pub fn register_syntax_extension(&mut self, name: ast::Name, extension: SyntaxExtension) {
         self.syntax_exts.push((name, match extension {
-            NormalTT(ext, _) => NormalTT(ext, Some(self.krate_span)),
-            IdentTT(ext, _) => IdentTT(ext, Some(self.krate_span)),
+            NormalTT(ext, _, allow_internal_unstable) => {
+                NormalTT(ext, Some(self.krate_span), allow_internal_unstable)
+            }
+            IdentTT(ext, _, allow_internal_unstable) => {
+                IdentTT(ext, Some(self.krate_span), allow_internal_unstable)
+            }
             Decorator(ext) => Decorator(ext),
             Modifier(ext) => Modifier(ext),
             MultiModifier(ext) => MultiModifier(ext),
@@ -99,7 +103,8 @@ pub fn register_syntax_extension(&mut self, name: ast::Name, extension: SyntaxEx
     /// It builds for you a `NormalTT` that calls `expander`,
     /// and also takes care of interning the macro's name.
     pub fn register_macro(&mut self, name: &str, expander: MacroExpanderFn) {
-        self.register_syntax_extension(token::intern(name), NormalTT(box expander, None));
+        self.register_syntax_extension(token::intern(name),
+                                       NormalTT(Box::new(expander), None, false));
     }
 
     /// Register a compiler lint pass.
index efcde8b2fa1ac94cb00bb44c1dbc19616da14561..1b09be050203bd82b894d0e981b43f5417a0f524 100644 (file)
@@ -38,6 +38,7 @@
 use std::collections::hash_map::Entry::{Occupied, Vacant};
 use std::env;
 use std::fmt;
+use std::path::PathBuf;
 
 use llvm;
 
@@ -80,6 +81,7 @@ pub struct Options {
 
     pub gc: bool,
     pub optimize: OptLevel,
+    pub debug_assertions: bool,
     pub debuginfo: DebugInfoLevel,
     pub lint_opts: Vec<(String, lint::Level)>,
     pub describe_lints: bool,
@@ -89,7 +91,7 @@ pub struct Options {
     // this.
     pub search_paths: SearchPaths,
     pub libs: Vec<(String, cstore::NativeLibraryKind)>,
-    pub maybe_sysroot: Option<Path>,
+    pub maybe_sysroot: Option<PathBuf>,
     pub target_triple: String,
     // User-specified cfg meta items. The compiler itself will add additional
     // items to the crate config, and during parsing the entire crate config
@@ -103,7 +105,7 @@ pub struct Options {
     pub no_analysis: bool,
     pub debugging_opts: DebuggingOptions,
     /// Whether to write dependency files. It's (enabled, optional filename).
-    pub write_dependency_info: (bool, Option<Path>),
+    pub write_dependency_info: (bool, Option<PathBuf>),
     pub prints: Vec<PrintRequest>,
     pub cg: CodegenOptions,
     pub color: ColorConfig,
@@ -142,7 +144,7 @@ pub enum PrintRequest {
 
 pub enum Input {
     /// Load source from file
-    File(Path),
+    File(PathBuf),
     /// The string is the source
     Str(String)
 }
@@ -150,7 +152,8 @@ pub enum Input {
 impl Input {
     pub fn filestem(&self) -> String {
         match *self {
-            Input::File(ref ifile) => ifile.filestem_str().unwrap().to_string(),
+            Input::File(ref ifile) => ifile.file_stem().unwrap()
+                                           .to_str().unwrap().to_string(),
             Input::Str(_) => "rust_out".to_string(),
         }
     }
@@ -158,14 +161,14 @@ pub fn filestem(&self) -> String {
 
 #[derive(Clone)]
 pub struct OutputFilenames {
-    pub out_directory: Path,
+    pub out_directory: PathBuf,
     pub out_filestem: String,
-    pub single_output_file: Option<Path>,
+    pub single_output_file: Option<PathBuf>,
     pub extra: String,
 }
 
 impl OutputFilenames {
-    pub fn path(&self, flavor: OutputType) -> Path {
+    pub fn path(&self, flavor: OutputType) -> PathBuf {
         match self.single_output_file {
             Some(ref path) => return path.clone(),
             None => {}
@@ -173,8 +176,8 @@ pub fn path(&self, flavor: OutputType) -> Path {
         self.temp_path(flavor)
     }
 
-    pub fn temp_path(&self, flavor: OutputType) -> Path {
-        let base = self.out_directory.join(self.filestem());
+    pub fn temp_path(&self, flavor: OutputType) -> PathBuf {
+        let base = self.out_directory.join(&self.filestem());
         match flavor {
             OutputTypeBitcode => base.with_extension("bc"),
             OutputTypeAssembly => base.with_extension("s"),
@@ -185,8 +188,8 @@ pub fn temp_path(&self, flavor: OutputType) -> Path {
         }
     }
 
-    pub fn with_extension(&self, extension: &str) -> Path {
-        self.out_directory.join(self.filestem()).with_extension(extension)
+    pub fn with_extension(&self, extension: &str) -> PathBuf {
+        self.out_directory.join(&self.filestem()).with_extension(extension)
     }
 
     pub fn filestem(&self) -> String {
@@ -236,7 +239,8 @@ pub fn basic_options() -> Options {
         crate_name: None,
         alt_std_name: None,
         libs: Vec::new(),
-        unstable_features: UnstableFeatures::Disallow
+        unstable_features: UnstableFeatures::Disallow,
+        debug_assertions: true,
     }
 }
 
@@ -259,7 +263,6 @@ pub enum CrateType {
     CrateTypeStaticlib,
 }
 
-
 #[derive(Clone)]
 pub enum Passes {
     SomePasses(Vec<String>),
@@ -349,7 +352,8 @@ pub fn $buildfn(matches: &getopts::Matches) -> $struct_name
     #[allow(non_upper_case_globals, dead_code)]
     mod $mod_desc {
         pub const parse_bool: Option<&'static str> = None;
-        pub const parse_opt_bool: Option<&'static str> = None;
+        pub const parse_opt_bool: Option<&'static str> =
+            Some("one of: `y`, `yes`, `on`, `n`, `no`, or `off`");
         pub const parse_string: Option<&'static str> = Some("a string");
         pub const parse_opt_string: Option<&'static str> = Some("a string");
         pub const parse_list: Option<&'static str> = Some("a space-separated list of strings");
@@ -380,7 +384,19 @@ fn parse_bool(slot: &mut bool, v: Option<&str>) -> bool {
 
         fn parse_opt_bool(slot: &mut Option<bool>, v: Option<&str>) -> bool {
             match v {
-                Some(..) => false,
+                Some(s) => {
+                    match s {
+                        "n" | "no" | "off" => {
+                            *slot = Some(false);
+                        }
+                        "y" | "yes" | "on" => {
+                            *slot = Some(true);
+                        }
+                        _ => { return false; }
+                    }
+
+                    true
+                },
                 None => { *slot = Some(true); true }
             }
         }
@@ -514,6 +530,8 @@ fn parse_passes(slot: &mut Passes, v: Option<&str>) -> bool {
          2 = full debug info with variable and type information"),
     opt_level: Option<uint> = (None, parse_opt_uint,
         "Optimize with possible levels 0-3"),
+    debug_assertions: Option<bool> = (None, parse_opt_bool,
+        "explicitly enable the cfg(debug_assertions) directive"),
 }
 
 
@@ -585,6 +603,8 @@ fn parse_passes(slot: &mut Passes, v: Option<&str>) -> bool {
           "Adds unstable command line options to rustc interface"),
     print_enum_sizes: bool = (false, parse_bool,
           "Print the size of enums and their variants"),
+    force_overflow_checks: Option<bool> = (None, parse_opt_bool,
+          "Force overflow checks on or off"),
 }
 
 pub fn default_lib_output() -> CrateType {
@@ -605,7 +625,7 @@ pub fn default_configuration(sess: &Session) -> ast::CrateConfig {
     };
 
     let mk = attr::mk_name_value_item_str;
-    return vec!(// Target bindings.
+    let mut ret = vec![ // Target bindings.
          attr::mk_word_item(fam.clone()),
          mk(InternedString::new("target_os"), intern(os)),
          mk(InternedString::new("target_family"), fam),
@@ -613,7 +633,11 @@ pub fn default_configuration(sess: &Session) -> ast::CrateConfig {
          mk(InternedString::new("target_endian"), intern(end)),
          mk(InternedString::new("target_pointer_width"),
             intern(wordsz))
-    );
+    ];
+    if sess.opts.debug_assertions {
+        ret.push(attr::mk_word_item(InternedString::new("debug_assertions")));
+    }
+    return ret;
 }
 
 pub fn append_configuration(cfg: &mut ast::CrateConfig,
@@ -883,7 +907,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
 
     let cg = build_codegen_options(matches);
 
-    let sysroot_opt = matches.opt_str("sysroot").map(|m| Path::new(m));
+    let sysroot_opt = matches.opt_str("sysroot").map(|m| PathBuf::new(&m));
     let target = matches.opt_str("target").unwrap_or(
         host_triple().to_string());
     let opt_level = {
@@ -907,6 +931,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
             }
         }
     };
+    let debug_assertions = cg.debug_assertions.unwrap_or(opt_level == No);
     let gc = debugging_opts.gc;
     let debuginfo = if matches.opt_present("g") {
         if cg.debuginfo.is_some() {
@@ -1048,6 +1073,7 @@ pub fn build_session_options(matches: &getopts::Matches) -> Options {
         alt_std_name: None,
         libs: libs,
         unstable_features: get_unstable_features_setting(),
+        debug_assertions: debug_assertions,
     }
 }
 
index 67c39bcca81f9a963fd8d863d57dc562675de040..8bc842671a0a96da425b7e9257dc81c8a40c2733 100644 (file)
@@ -26,8 +26,9 @@
 
 use rustc_back::target::Target;
 
+use std::path::{Path, PathBuf};
 use std::cell::{Cell, RefCell};
-use std::os;
+use std::env;
 
 pub mod config;
 pub mod search_paths;
@@ -44,11 +45,11 @@ pub struct Session {
     pub entry_fn: RefCell<Option<(NodeId, codemap::Span)>>,
     pub entry_type: Cell<Option<config::EntryFnType>>,
     pub plugin_registrar_fn: Cell<Option<ast::NodeId>>,
-    pub default_sysroot: Option<Path>,
+    pub default_sysroot: Option<PathBuf>,
     // The name of the root source file of the crate, in the local file system. The path is always
     // expected to be absolute. `None` means that there is no source file.
-    pub local_crate_source_file: Option<Path>,
-    pub working_dir: Path,
+    pub local_crate_source_file: Option<PathBuf>,
+    pub working_dir: PathBuf,
     pub lint_store: RefCell<lint::LintStore>,
     pub lints: RefCell<NodeMap<Vec<(lint::LintId, codemap::Span, String)>>>,
     pub crate_types: RefCell<Vec<config::CrateType>>,
@@ -64,12 +65,21 @@ pub struct Session {
 
 impl Session {
     pub fn span_fatal(&self, sp: Span, msg: &str) -> ! {
+        if self.opts.treat_err_as_bug {
+            self.span_bug(sp, msg);
+        }
         self.diagnostic().span_fatal(sp, msg)
     }
     pub fn span_fatal_with_code(&self, sp: Span, msg: &str, code: &str) -> ! {
+        if self.opts.treat_err_as_bug {
+            self.span_bug(sp, msg);
+        }
         self.diagnostic().span_fatal_with_code(sp, msg, code)
     }
     pub fn fatal(&self, msg: &str) -> ! {
+        if self.opts.treat_err_as_bug {
+            self.bug(msg);
+        }
         self.diagnostic().handler().fatal(msg)
     }
     pub fn span_err(&self, sp: Span, msg: &str) {
@@ -310,7 +320,7 @@ fn split_msg_into_multilines(msg: &str) -> Option<String> {
 }
 
 pub fn build_session(sopts: config::Options,
-                     local_crate_source_file: Option<Path>,
+                     local_crate_source_file: Option<PathBuf>,
                      registry: diagnostics::registry::Registry)
                      -> Session {
     // FIXME: This is not general enough to make the warning lint completely override
@@ -333,7 +343,7 @@ pub fn build_session(sopts: config::Options,
 }
 
 pub fn build_session_(sopts: config::Options,
-                      local_crate_source_file: Option<Path>,
+                      local_crate_source_file: Option<PathBuf>,
                       span_diagnostic: diagnostic::SpanHandler)
                       -> Session {
     let host = match Target::search(config::host_triple()) {
@@ -355,7 +365,7 @@ pub fn build_session_(sopts: config::Options,
         if path.is_absolute() {
             path.clone()
         } else {
-            os::getcwd().unwrap().join(&path)
+            env::current_dir().unwrap().join(&path)
         }
     );
 
@@ -378,7 +388,7 @@ pub fn build_session_(sopts: config::Options,
         plugin_registrar_fn: Cell::new(None),
         default_sysroot: default_sysroot,
         local_crate_source_file: local_crate_source_file,
-        working_dir: os::getcwd().unwrap(),
+        working_dir: env::current_dir().unwrap(),
         lint_store: RefCell::new(lint::LintStore::new()),
         lints: RefCell::new(NodeMap()),
         crate_types: RefCell::new(Vec::new()),
index c314a999f246119cf1ca7d340b5c8586f0a245e3..f85fb3039102e9eb300c9160352ab4c6ac7f24c7 100644 (file)
@@ -9,15 +9,16 @@
 // except according to those terms.
 
 use std::slice;
+use std::path::{Path, PathBuf};
 
 #[derive(Clone, Debug)]
 pub struct SearchPaths {
-    paths: Vec<(PathKind, Path)>,
+    paths: Vec<(PathKind, PathBuf)>,
 }
 
 pub struct Iter<'a> {
     kind: PathKind,
-    iter: slice::Iter<'a, (PathKind, Path)>,
+    iter: slice::Iter<'a, (PathKind, PathBuf)>,
 }
 
 #[derive(Eq, PartialEq, Clone, Copy, Debug)]
@@ -49,7 +50,7 @@ pub fn add_path(&mut self, path: &str) {
         } else {
             (PathKind::All, path)
         };
-        self.paths.push((kind, Path::new(path)));
+        self.paths.push((kind, PathBuf::new(path)));
     }
 
     pub fn iter(&self, kind: PathKind) -> Iter {
index ca740f53782192de205ca915ea630785cd62bc1d..0b32f7f69eb448234f93f89756c22a8bf13389da 100644 (file)
 
 use std::cell::{RefCell, Cell};
 use std::collections::HashMap;
+use std::collections::hash_state::HashState;
+use std::ffi::CString;
 use std::fmt::Debug;
 use std::hash::Hash;
 use std::iter::repeat;
+use std::path::Path;
 use std::time::Duration;
-use std::collections::hash_state::HashState;
 
 use syntax::ast;
 use syntax::visit;
@@ -222,3 +224,14 @@ pub fn memoized<T, U, S, F>(cache: &RefCell<HashMap<T, U, S>>, arg: T, f: F) ->
         }
     }
 }
+
+#[cfg(unix)]
+pub fn path2cstr(p: &Path) -> CString {
+    use std::os::unix::prelude::*;
+    use std::ffi::AsOsStr;
+    CString::new(p.as_os_str().as_bytes()).unwrap()
+}
+#[cfg(windows)]
+pub fn path2cstr(p: &Path) -> CString {
+    CString::new(p.to_str().unwrap()).unwrap()
+}
index 10a7b2abea80bb389e3213ec3895b27661ded2d8..d3b9b07ea416970daecfaab42dec9f9cf22de738 100644 (file)
@@ -45,7 +45,7 @@ pub fn lev_distance(me: &str, t: &str) -> uint {
 fn test_lev_distance() {
     use std::char::{ from_u32, MAX };
     // Test bytelength agnosticity
-    for c in (0u32..MAX as u32)
+    for c in (0..MAX as u32)
              .filter_map(|i| from_u32(i))
              .map(|i| i.to_string()) {
         assert_eq!(lev_distance(&c[..], &c[..]), 0);
index b15da7dab3ee606627f78d4d53618fa47e55dfd8..0f69aa941a31e67b51080dd3051068f5f5362aee 100644 (file)
@@ -57,7 +57,7 @@ fn write(&mut self, bytes: &[u8]) {
         let FnvHasher(mut hash) = *self;
         for byte in bytes {
             hash = hash ^ (*byte as u64);
-            hash = hash * 0x100000001b3;
+            hash = hash.wrapping_mul(0x100000001b3);
         }
         *self = FnvHasher(hash);
     }
index 15b3c6d9d0602c7ed65a0ce39c560de1e99f4414..f41d969c1a271ccf5da0cba4ae20d3003b1f7316 100644 (file)
@@ -115,7 +115,7 @@ pub fn explain_region_and_span(cx: &ctxt, region: ty::Region)
             region::CodeExtent::Misc(_) => tag,
             region::CodeExtent::DestructionScope(_) => {
                 new_string = format!("destruction scope surrounding {}", tag);
-                new_string.as_slice()
+                &*new_string
             }
             region::CodeExtent::Remainder(r) => {
                 new_string = format!("block suffix following statement {}",
@@ -406,7 +406,7 @@ fn infer_ty_to_string(cx: &ctxt, ty: ty::InferTy) -> String {
                     data.item_name.user_string(cx))
         }
         ty_str => "str".to_string(),
-        ty_closure(ref did, _, substs) => {
+        ty_closure(ref did, substs) => {
             let closure_tys = cx.closure_tys.borrow();
             closure_tys.get(did).map(|closure_type| {
                 closure_to_string(cx, &closure_type.subst(cx, substs))
@@ -820,9 +820,8 @@ fn repr(&self, tcx: &ctxt<'tcx>) -> String {
 
 impl<'tcx> Repr<'tcx> for ty::TraitDef<'tcx> {
     fn repr(&self, tcx: &ctxt<'tcx>) -> String {
-        format!("TraitDef(generics={}, bounds={}, trait_ref={})",
+        format!("TraitDef(generics={}, trait_ref={})",
                 self.generics.repr(tcx),
-                self.bounds.repr(tcx),
                 self.trait_ref.repr(tcx))
     }
 }
index 3fcae6a8034c207ac3408c2beb3ea76bdf2f97cb..ed44bf8952951ae6363d04bed52eb3c2a9d1f83f 100644 (file)
 
 //! A helper class for dealing with static archives
 
-use std::old_io::fs::PathExtensions;
-use std::old_io::process::{Command, ProcessOutput};
-use std::old_io::{fs, TempDir};
-use std::old_io;
-use std::os;
+use std::env;
+use std::fs;
+use std::io::prelude::*;
+use std::io;
+use std::path::{Path, PathBuf};
+use std::process::{Command, Output, Stdio};
 use std::str;
 use syntax::diagnostic::Handler as ErrorHandler;
 
-pub static METADATA_FILENAME: &'static str = "rust.metadata.bin";
+use tempdir::TempDir;
+
+pub const METADATA_FILENAME: &'static str = "rust.metadata.bin";
 
 pub struct ArchiveConfig<'a> {
     pub handler: &'a ErrorHandler,
-    pub dst: Path,
-    pub lib_search_paths: Vec<Path>,
+    pub dst: PathBuf,
+    pub lib_search_paths: Vec<PathBuf>,
     pub slib_prefix: String,
     pub slib_suffix: String,
     pub maybe_ar_prog: Option<String>
@@ -31,8 +34,8 @@ pub struct ArchiveConfig<'a> {
 
 pub struct Archive<'a> {
     handler: &'a ErrorHandler,
-    dst: Path,
-    lib_search_paths: Vec<Path>,
+    dst: PathBuf,
+    lib_search_paths: Vec<PathBuf>,
     slib_prefix: String,
     slib_suffix: String,
     maybe_ar_prog: Option<String>
@@ -45,25 +48,25 @@ pub struct ArchiveBuilder<'a> {
     archive: Archive<'a>,
     work_dir: TempDir,
     /// Filename of each member that should be added to the archive.
-    members: Vec<Path>,
+    members: Vec<PathBuf>,
     should_update_symbols: bool,
 }
 
 fn run_ar(handler: &ErrorHandler, maybe_ar_prog: &Option<String>,
           args: &str, cwd: Option<&Path>,
-          paths: &[&Path]) -> ProcessOutput {
+          paths: &[&Path]) -> Output {
     let ar = match *maybe_ar_prog {
         Some(ref ar) => &ar[..],
         None => "ar"
     };
     let mut cmd = Command::new(ar);
 
-    cmd.arg(args).args(paths);
+    cmd.arg(args).args(paths).stdout(Stdio::piped()).stderr(Stdio::piped());
     debug!("{:?}", cmd);
 
     match cwd {
         Some(p) => {
-            cmd.cwd(p);
+            cmd.current_dir(p);
             debug!("inside {:?}", p.display());
         }
         None => {}
@@ -75,9 +78,9 @@ fn run_ar(handler: &ErrorHandler, maybe_ar_prog: &Option<String>,
             if !o.status.success() {
                 handler.err(&format!("{:?} failed with: {}", cmd, o.status));
                 handler.note(&format!("stdout ---\n{}",
-                                  str::from_utf8(&o.output).unwrap()));
+                                  str::from_utf8(&o.stdout).unwrap()));
                 handler.note(&format!("stderr ---\n{}",
-                                  str::from_utf8(&o.error).unwrap())
+                                  str::from_utf8(&o.stderr).unwrap())
                              );
                 handler.abort_if_errors();
             }
@@ -93,14 +96,15 @@ fn run_ar(handler: &ErrorHandler, maybe_ar_prog: &Option<String>,
 }
 
 pub fn find_library(name: &str, osprefix: &str, ossuffix: &str,
-                    search_paths: &[Path], handler: &ErrorHandler) -> Path {
+                    search_paths: &[PathBuf],
+                    handler: &ErrorHandler) -> PathBuf {
     // On Windows, static libraries sometimes show up as libfoo.a and other
     // times show up as foo.lib
     let oslibname = format!("{}{}{}", osprefix, name, ossuffix);
     let unixlibname = format!("lib{}.a", name);
 
     for path in search_paths {
-        debug!("looking for {} inside {:?}", name, path.display());
+        debug!("looking for {} inside {:?}", name, path);
         let test = path.join(&oslibname[..]);
         if test.exists() { return test }
         if oslibname != unixlibname {
@@ -142,7 +146,7 @@ pub fn remove_file(&mut self, file: &str) {
     /// Lists all files in an archive
     pub fn files(&self) -> Vec<String> {
         let output = run_ar(self.handler, &self.maybe_ar_prog, "t", None, &[&self.dst]);
-        let output = str::from_utf8(&output.output).unwrap();
+        let output = str::from_utf8(&output.stdout).unwrap();
         // use lines_any because windows delimits output with `\r\n` instead of
         // just `\n`
         output.lines_any().map(|s| s.to_string()).collect()
@@ -172,7 +176,7 @@ pub fn create(config: ArchiveConfig<'a>) -> ArchiveBuilder<'a> {
 
     /// Adds all of the contents of a native library to this archive. This will
     /// search in the relevant locations for a library named `name`.
-    pub fn add_native_library(&mut self, name: &str) -> old_io::IoResult<()> {
+    pub fn add_native_library(&mut self, name: &str) -> io::Result<()> {
         let location = find_library(name,
                                     &self.archive.slib_prefix,
                                     &self.archive.slib_suffix,
@@ -187,7 +191,7 @@ pub fn add_native_library(&mut self, name: &str) -> old_io::IoResult<()> {
     /// This ignores adding the bytecode from the rlib, and if LTO is enabled
     /// then the object file also isn't added.
     pub fn add_rlib(&mut self, rlib: &Path, name: &str,
-                    lto: bool) -> old_io::IoResult<()> {
+                    lto: bool) -> io::Result<()> {
         // Ignoring obj file starting with the crate name
         // as simple comparison is not enough - there
         // might be also an extra name suffix
@@ -205,11 +209,11 @@ pub fn add_rlib(&mut self, rlib: &Path, name: &str,
     }
 
     /// Adds an arbitrary file to this archive
-    pub fn add_file(&mut self, file: &Path) -> old_io::IoResult<()> {
-        let filename = Path::new(file.filename().unwrap());
+    pub fn add_file(&mut self, file: &Path) -> io::Result<()> {
+        let filename = Path::new(file.file_name().unwrap());
         let new_file = self.work_dir.path().join(&filename);
         try!(fs::copy(file, &new_file));
-        self.members.push(filename);
+        self.members.push(filename.to_path_buf());
         Ok(())
     }
 
@@ -224,10 +228,10 @@ pub fn update_symbols(&mut self) {
     pub fn build(self) -> Archive<'a> {
         // Get an absolute path to the destination, so `ar` will work even
         // though we run it from `self.work_dir`.
-        let abs_dst = os::getcwd().unwrap().join(&self.archive.dst);
+        let abs_dst = env::current_dir().unwrap().join(&self.archive.dst);
         assert!(!abs_dst.is_relative());
-        let mut args = vec![&abs_dst];
-        let mut total_len = abs_dst.as_vec().len();
+        let mut args = vec![&*abs_dst];
+        let mut total_len = abs_dst.to_string_lossy().len();
 
         if self.members.is_empty() {
             // OSX `ar` does not allow using `r` with no members, but it does
@@ -242,10 +246,10 @@ pub fn build(self) -> Archive<'a> {
         // Don't allow the total size of `args` to grow beyond 32,000 bytes.
         // Windows will raise an error if the argument string is longer than
         // 32,768, and we leave a bit of extra space for the program name.
-        static ARG_LENGTH_LIMIT: uint = 32000;
+        const ARG_LENGTH_LIMIT: uint = 32_000;
 
         for member_name in &self.members {
-            let len = member_name.as_vec().len();
+            let len = member_name.to_string_lossy().len();
 
             // `len + 1` to account for the space that's inserted before each
             // argument.  (Windows passes command-line arguments as a single
@@ -258,7 +262,7 @@ pub fn build(self) -> Archive<'a> {
 
                 args.clear();
                 args.push(&abs_dst);
-                total_len = abs_dst.as_vec().len();
+                total_len = abs_dst.to_string_lossy().len();
             }
 
             args.push(member_name);
@@ -275,7 +279,7 @@ pub fn build(self) -> Archive<'a> {
     }
 
     fn add_archive<F>(&mut self, archive: &Path, name: &str,
-                      mut skip: F) -> old_io::IoResult<()>
+                      mut skip: F) -> io::Result<()>
         where F: FnMut(&str) -> bool,
     {
         let loc = TempDir::new("rsar").unwrap();
@@ -283,7 +287,7 @@ fn add_archive<F>(&mut self, archive: &Path, name: &str,
         // First, extract the contents of the archive to a temporary directory.
         // We don't unpack directly into `self.work_dir` due to the possibility
         // of filename collisions.
-        let archive = os::getcwd().unwrap().join(archive);
+        let archive = env::current_dir().unwrap().join(archive);
         run_ar(self.archive.handler, &self.archive.maybe_ar_prog,
                "x", Some(loc.path()), &[&archive]);
 
@@ -296,9 +300,10 @@ fn add_archive<F>(&mut self, archive: &Path, name: &str,
         // We skip any files explicitly desired for skipping, and we also skip
         // all SYMDEF files as these are just magical placeholders which get
         // re-created when we make a new archive anyway.
-        let files = try!(fs::readdir(loc.path()));
-        for file in &files {
-            let filename = file.filename_str().unwrap();
+        let files = try!(fs::read_dir(loc.path()));
+        for file in files {
+            let file = try!(file).path();
+            let filename = file.file_name().unwrap().to_str().unwrap();
             if skip(filename) { continue }
             if filename.contains(".SYMDEF") { continue }
 
@@ -313,8 +318,8 @@ fn add_archive<F>(&mut self, archive: &Path, name: &str,
                 filename
             };
             let new_filename = self.work_dir.path().join(&filename[..]);
-            try!(fs::rename(file, &new_filename));
-            self.members.push(Path::new(filename));
+            try!(fs::rename(&file, &new_filename));
+            self.members.push(PathBuf::new(&filename));
         }
         Ok(())
     }
index 99a1df95a80cddf398549aa2226f3d48fb2be119..c00c33d4c2fed505ce680d72c1321777498a1141 100644 (file)
@@ -8,14 +8,29 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-use std::old_io;
+use std::io;
 use std::old_io::fs;
+use std::old_io;
+use std::old_path;
 use std::os;
+use std::path::{Path, PathBuf};
 
 /// Returns an absolute path in the filesystem that `path` points to. The
 /// returned path does not contain any symlinks in its hierarchy.
-pub fn realpath(original: &Path) -> old_io::IoResult<Path> {
-    static MAX_LINKS_FOLLOWED: uint = 256;
+#[allow(deprecated)] // readlink is deprecated
+pub fn realpath(original: &Path) -> io::Result<PathBuf> {
+    let old = old_path::Path::new(original.to_str().unwrap());
+    match old_realpath(&old) {
+        Ok(p) => Ok(PathBuf::new(p.as_str().unwrap())),
+        Err(e) => Err(io::Error::new(io::ErrorKind::Other,
+                                     "realpath error",
+                                     Some(e.to_string())))
+    }
+}
+
+#[allow(deprecated)]
+fn old_realpath(original: &old_path::Path) -> old_io::IoResult<old_path::Path> {
+    const MAX_LINKS_FOLLOWED: usize = 256;
     let original = try!(os::getcwd()).join(original);
 
     // Right now lstat on windows doesn't work quite well
@@ -55,7 +70,7 @@ pub fn realpath(original: &Path) -> old_io::IoResult<Path> {
 mod test {
     use std::old_io;
     use std::old_io::fs::{File, symlink, mkdir, mkdir_recursive};
-    use super::realpath;
+    use super::old_realpath as realpath;
     use std::old_io::TempDir;
 
     #[test]
index 9005c666afbcdd254b1c3503b3796663e667a7e4..333c97b446ba3d421e21a7061ca631f25f8949ee 100644 (file)
@@ -21,6 +21,8 @@
 //! one that doesn't; the one that doesn't might get decent parallel
 //! build speedups.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_back"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
 #![feature(box_syntax)]
 #![feature(collections)]
 #![feature(core)]
+#![feature(old_fs)]
 #![feature(hash)]
 #![feature(int_uint)]
+#![feature(io)]
 #![feature(old_io)]
-#![feature(os)]
 #![feature(old_path)]
+#![feature(os)]
+#![feature(path)]
 #![feature(rustc_private)]
 #![feature(staged_api)]
-#![feature(path)]
+#![feature(rand)]
+#![feature(path_ext)]
 
 extern crate syntax;
 extern crate serialize;
@@ -48,6 +54,7 @@
 
 pub mod abi;
 pub mod archive;
+pub mod tempdir;
 pub mod arm;
 pub mod fs;
 pub mod mips;
index 943ff52925a244545de15c4856f252db57bf7991..4f9f1447d8a731b918f765666306916435348de4 100644 (file)
 
 use std::collections::HashSet;
 use std::env;
-use std::old_io::IoError;
-use std::os;
+use std::io;
+use std::path::{Path, PathBuf};
 use syntax::ast;
 
-pub struct RPathConfig<F, G> where
-    F: FnOnce() -> Path,
-    G: FnMut(&Path) -> Result<Path, IoError>,
-{
-    pub used_crates: Vec<(ast::CrateNum, Option<Path>)>,
-    pub out_filename: Path,
+pub struct RPathConfig<'a> {
+    pub used_crates: Vec<(ast::CrateNum, Option<PathBuf>)>,
+    pub out_filename: PathBuf,
     pub is_like_osx: bool,
     pub has_rpath: bool,
-    pub get_install_prefix_lib_path: F,
-    pub realpath: G,
+    pub get_install_prefix_lib_path: &'a mut FnMut() -> PathBuf,
+    pub realpath: &'a mut FnMut(&Path) -> io::Result<PathBuf>,
 }
 
-pub fn get_rpath_flags<F, G>(config: RPathConfig<F, G>) -> Vec<String> where
-    F: FnOnce() -> Path,
-    G: FnMut(&Path) -> Result<Path, IoError>,
-{
+pub fn get_rpath_flags(config: &mut RPathConfig) -> Vec<String> {
     // No rpath on windows
     if !config.has_rpath {
         return Vec::new();
@@ -54,10 +48,7 @@ fn rpaths_to_flags(rpaths: &[String]) -> Vec<String> {
     return ret;
 }
 
-fn get_rpaths<F, G>(mut config: RPathConfig<F, G>, libs: &[Path]) -> Vec<String> where
-    F: FnOnce() -> Path,
-    G: FnMut(&Path) -> Result<Path, IoError>,
-{
+fn get_rpaths(config: &mut RPathConfig, libs: &[PathBuf]) -> Vec<String> {
     debug!("output: {:?}", config.out_filename.display());
     debug!("libs:");
     for libpath in libs {
@@ -67,7 +58,7 @@ fn get_rpaths<F, G>(mut config: RPathConfig<F, G>, libs: &[Path]) -> Vec<String>
     // Use relative paths to the libraries. Binaries can be moved
     // as long as they maintain the relative relationship to the
     // crates they depend on.
-    let rel_rpaths = get_rpaths_relative_to_output(&mut config, libs);
+    let rel_rpaths = get_rpaths_relative_to_output(config, libs);
 
     // And a final backup rpath to the global library location.
     let fallback_rpaths = vec!(get_install_prefix_rpath(config));
@@ -90,18 +81,12 @@ fn log_rpaths(desc: &str, rpaths: &[String]) {
     return rpaths;
 }
 
-fn get_rpaths_relative_to_output<F, G>(config: &mut RPathConfig<F, G>,
-                                       libs: &[Path]) -> Vec<String> where
-    F: FnOnce() -> Path,
-    G: FnMut(&Path) -> Result<Path, IoError>,
-{
+fn get_rpaths_relative_to_output(config: &mut RPathConfig,
+                                 libs: &[PathBuf]) -> Vec<String> {
     libs.iter().map(|a| get_rpath_relative_to_output(config, a)).collect()
 }
 
-fn get_rpath_relative_to_output<F, G>(config: &mut RPathConfig<F, G>, lib: &Path) -> String where
-    F: FnOnce() -> Path,
-    G: FnMut(&Path) -> Result<Path, IoError>,
-{
+fn get_rpath_relative_to_output(config: &mut RPathConfig, lib: &Path) -> String {
     // Mac doesn't appear to support $ORIGIN
     let prefix = if config.is_like_osx {
         "@loader_path"
@@ -109,23 +94,36 @@ fn get_rpath_relative_to_output<F, G>(config: &mut RPathConfig<F, G>, lib: &Path
         "$ORIGIN"
     };
 
-    let cwd = os::getcwd().unwrap();
+    let cwd = env::current_dir().unwrap();
     let mut lib = (config.realpath)(&cwd.join(lib)).unwrap();
     lib.pop();
     let mut output = (config.realpath)(&cwd.join(&config.out_filename)).unwrap();
     output.pop();
-    let relative = lib.path_relative_from(&output);
-    let relative = relative.expect("could not create rpath relative to output");
+    let relative = relativize(&lib, &output);
     // FIXME (#9639): This needs to handle non-utf8 paths
-    format!("{}/{}",
-            prefix,
-            relative.as_str().expect("non-utf8 component in path"))
+    format!("{}/{}", prefix,
+            relative.to_str().expect("non-utf8 component in path"))
 }
 
-fn get_install_prefix_rpath<F, G>(config: RPathConfig<F, G>) -> String where
-    F: FnOnce() -> Path,
-    G: FnMut(&Path) -> Result<Path, IoError>,
-{
+fn relativize(path: &Path, rel: &Path) -> PathBuf {
+    let mut res = PathBuf::new("");
+    let mut cur = rel;
+    while !path.starts_with(cur) {
+        res.push("..");
+        match cur.parent() {
+            Some(p) => cur = p,
+            None => panic!("can't create relative paths across filesystems"),
+        }
+    }
+    match path.relative_from(cur) {
+        Some(s) => { res.push(s); res }
+        None => panic!("couldn't create relative path from {:?} to {:?}",
+                       rel, path),
+    }
+
+}
+
+fn get_install_prefix_rpath(config: &mut RPathConfig) -> String {
     let path = (config.get_install_prefix_lib_path)();
     let path = env::current_dir().unwrap().join(&path);
     // FIXME (#9639): This needs to handle non-utf8 paths
@@ -147,6 +145,7 @@ fn minimize_rpaths(rpaths: &[String]) -> Vec<String> {
 mod test {
     use super::{RPathConfig};
     use super::{minimize_rpaths, rpaths_to_flags, get_rpath_relative_to_output};
+    use std::path::{Path, PathBuf};
 
     #[test]
     fn test_rpaths_to_flags() {
@@ -195,50 +194,31 @@ fn test_minimize2() {
     }
 
     #[test]
-    #[cfg(any(target_os = "linux", target_os = "android"))]
     fn test_rpath_relative() {
-        let config = &mut RPathConfig {
-            used_crates: Vec::new(),
-            out_filename: Path::new("bin/rustc"),
-            get_install_prefix_lib_path: || panic!(),
-            has_rpath: true,
-            is_like_osx: false,
-            realpath: |p| Ok(p.clone())
-        };
-        let res = get_rpath_relative_to_output(config, &Path::new("lib/libstd.so"));
-        assert_eq!(res, "$ORIGIN/../lib");
-    }
-
-    #[test]
-    #[cfg(any(target_os = "freebsd",
-              target_os = "dragonfly",
-              target_os = "bitrig",
-              target_os = "openbsd"))]
-    fn test_rpath_relative() {
-        let config = &mut RPathConfig {
-            used_crates: Vec::new(),
-            has_rpath: true,
-            is_like_osx: false,
-            out_filename: Path::new("bin/rustc"),
-            get_install_prefix_lib_path: || panic!(),
-            realpath: |p| Ok(p.clone())
-        };
-        let res = get_rpath_relative_to_output(config, &Path::new("lib/libstd.so"));
-        assert_eq!(res, "$ORIGIN/../lib");
-    }
-
-    #[test]
-    #[cfg(target_os = "macos")]
-    fn test_rpath_relative() {
-        let config = &mut RPathConfig {
-            used_crates: Vec::new(),
-            has_rpath: true,
-            is_like_osx: true,
-            out_filename: Path::new("bin/rustc"),
-            get_install_prefix_lib_path: || panic!(),
-            realpath: |p| Ok(p.clone())
-        };
-        let res = get_rpath_relative_to_output(config, &Path::new("lib/libstd.so"));
-        assert_eq!(res, "@loader_path/../lib");
+        if cfg!(target_os = "macos") {
+            let config = &mut RPathConfig {
+                used_crates: Vec::new(),
+                has_rpath: true,
+                is_like_osx: true,
+                out_filename: PathBuf::new("bin/rustc"),
+                get_install_prefix_lib_path: &mut || panic!(),
+                realpath: &mut |p| Ok(p.to_path_buf()),
+            };
+            let res = get_rpath_relative_to_output(config,
+                                                   Path::new("lib/libstd.so"));
+            assert_eq!(res, "@loader_path/../lib");
+        } else {
+            let config = &mut RPathConfig {
+                used_crates: Vec::new(),
+                out_filename: PathBuf::new("bin/rustc"),
+                get_install_prefix_lib_path: &mut || panic!(),
+                has_rpath: true,
+                is_like_osx: false,
+                realpath: &mut |p| Ok(p.to_path_buf()),
+            };
+            let res = get_rpath_relative_to_output(config,
+                                                   Path::new("lib/libstd.so"));
+            assert_eq!(res, "$ORIGIN/../lib");
+        }
     }
 }
index 6654a46f7c31b51cdaee38add94af4f904eb793e..1a399519296a829ecd782994096376ff890a392b 100644 (file)
@@ -119,7 +119,7 @@ impl FixedBuffer64 {
     /// Create a new FixedBuffer64
     fn new() -> FixedBuffer64 {
         return FixedBuffer64 {
-            buffer: [0u8; 64],
+            buffer: [0; 64],
             buffer_idx: 0
         };
     }
@@ -258,7 +258,7 @@ fn input_str(&mut self, input: &str) {
     /// Convenience function that retrieves the result of a digest as a
     /// newly allocated vec of bytes.
     fn result_bytes(&mut self) -> Vec<u8> {
-        let mut buf: Vec<u8> = repeat(0u8).take((self.output_bits()+7)/8).collect();
+        let mut buf: Vec<u8> = repeat(0).take((self.output_bits()+7)/8).collect();
         self.result(&mut buf);
         buf
     }
@@ -342,22 +342,24 @@ fn sigma1(x: u32) -> u32 {
         let mut g = self.h6;
         let mut h = self.h7;
 
-        let mut w = [0u32; 64];
+        let mut w = [0; 64];
 
         // Sha-512 and Sha-256 use basically the same calculations which are implemented
         // by these macros. Inlining the calculations seems to result in better generated code.
         macro_rules! schedule_round { ($t:expr) => (
-                w[$t] = sigma1(w[$t - 2]) + w[$t - 7] + sigma0(w[$t - 15]) + w[$t - 16];
-                )
+            w[$t] = sigma1(w[$t - 2]).wrapping_add(w[$t - 7])
+                .wrapping_add(sigma0(w[$t - 15])).wrapping_add(w[$t - 16]);
+            )
         }
 
         macro_rules! sha2_round {
             ($A:ident, $B:ident, $C:ident, $D:ident,
              $E:ident, $F:ident, $G:ident, $H:ident, $K:ident, $t:expr) => (
                 {
-                    $H += sum1($E) + ch($E, $F, $G) + $K[$t] + w[$t];
-                    $D += $H;
-                    $H += sum0($A) + maj($A, $B, $C);
+                    $H = $H.wrapping_add(sum1($E)).wrapping_add(ch($E, $F, $G))
+                        .wrapping_add($K[$t]).wrapping_add(w[$t]);
+                    $D = $D.wrapping_add($H);
+                    $H = $H.wrapping_add(sum0($A)).wrapping_add(maj($A, $B, $C));
                 }
              )
         }
@@ -397,14 +399,14 @@ macro_rules! sha2_round {
             sha2_round!(b, c, d, e, f, g, h, a, K32, t + 7);
         }
 
-        self.h0 += a;
-        self.h1 += b;
-        self.h2 += c;
-        self.h3 += d;
-        self.h4 += e;
-        self.h5 += f;
-        self.h6 += g;
-        self.h7 += h;
+        self.h0 = self.h0.wrapping_add(a);
+        self.h1 = self.h1.wrapping_add(b);
+        self.h2 = self.h2.wrapping_add(c);
+        self.h3 = self.h3.wrapping_add(d);
+        self.h4 = self.h4.wrapping_add(e);
+        self.h5 = self.h5.wrapping_add(f);
+        self.h6 = self.h6.wrapping_add(g);
+        self.h7 = self.h7.wrapping_add(h);
     }
 }
 
@@ -546,7 +548,7 @@ fn test_add_bytes_to_bits_ok() {
 
     // A simple failure case - adding 1 to the max value
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_add_bytes_to_bits_overflow() {
         super::add_bytes_to_bits::<u64>(Int::max_value(), 1);
     }
@@ -604,7 +606,7 @@ fn test_sha256() {
 
         let tests = wikipedia_tests;
 
-        let mut sh = box Sha256::new();
+        let mut sh: Box<_> = box Sha256::new();
 
         test_hash(&mut *sh, &tests);
     }
@@ -658,7 +660,7 @@ mod bench {
     #[bench]
     pub fn sha256_10(b: &mut Bencher) {
         let mut sh = Sha256::new();
-        let bytes = [1u8; 10];
+        let bytes = [1; 10];
         b.iter(|| {
             sh.input(&bytes);
         });
@@ -668,7 +670,7 @@ pub fn sha256_10(b: &mut Bencher) {
     #[bench]
     pub fn sha256_1k(b: &mut Bencher) {
         let mut sh = Sha256::new();
-        let bytes = [1u8; 1024];
+        let bytes = [1; 1024];
         b.iter(|| {
             sh.input(&bytes);
         });
@@ -678,7 +680,7 @@ pub fn sha256_1k(b: &mut Bencher) {
     #[bench]
     pub fn sha256_64k(b: &mut Bencher) {
         let mut sh = Sha256::new();
-        let bytes = [1u8; 65536];
+        let bytes = [1; 65536];
         b.iter(|| {
             sh.input(&bytes);
         });
index 904b337c03f46e63e664126f01cc470d457c013a..2fbbe7d1f7c5ea60e7865617f78a5ecc8898e4da 100644 (file)
@@ -8,7 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-use std::old_io::{Command, IoError, OtherIoError};
+use std::io;
+use std::process::Command;
 use target::TargetOptions;
 
 use self::Arch::*;
@@ -40,16 +41,15 @@ pub fn get_sdk_root(sdk_name: &str) -> String {
                       .arg("--show-sdk-path")
                       .arg("-sdk")
                       .arg(sdk_name)
-                      .spawn()
-                      .and_then(|c| c.wait_with_output())
+                      .output()
                       .and_then(|output| {
                           if output.status.success() {
-                              Ok(String::from_utf8(output.output).unwrap())
+                              Ok(String::from_utf8(output.stdout).unwrap())
                           } else {
-                              Err(IoError {
-                                  kind: OtherIoError,
-                                  desc: "process exit with error",
-                                  detail: String::from_utf8(output.error).ok()})
+                              let error = String::from_utf8(output.stderr);
+                              Err(io::Error::new(io::ErrorKind::Other,
+                                                 "process exit with error",
+                                                 error.ok()))
                           }
                       });
 
index d09a7c355d3e3c32ef00aa2d1f819f1d9d39ff26..4663901a7b4c1f84114586dc066bf05feecf5aac 100644 (file)
@@ -48,7 +48,7 @@
 use serialize::json::Json;
 use syntax::{diagnostic, abi};
 use std::default::Default;
-use std::old_io::fs::PathExtensions;
+use std::io::prelude::*;
 
 mod windows_base;
 mod linux_base;
@@ -302,23 +302,26 @@ macro_rules! key {
         base
     }
 
-    /// Search RUST_TARGET_PATH for a JSON file specifying the given target triple. Note that it
-    /// could also just be a bare filename already, so also check for that. If one of the hardcoded
-    /// targets we know about, just return it directly.
+    /// Search RUST_TARGET_PATH for a JSON file specifying the given target
+    /// triple. Note that it could also just be a bare filename already, so also
+    /// check for that. If one of the hardcoded targets we know about, just
+    /// return it directly.
     ///
-    /// The error string could come from any of the APIs called, including filesystem access and
-    /// JSON decoding.
+    /// The error string could come from any of the APIs called, including
+    /// filesystem access and JSON decoding.
     pub fn search(target: &str) -> Result<Target, String> {
         use std::env;
-        use std::os;
         use std::ffi::OsString;
-        use std::old_io::File;
-        use std::old_path::Path;
+        use std::fs::File;
+        use std::path::{Path, PathBuf};
         use serialize::json;
 
         fn load_file(path: &Path) -> Result<Target, String> {
-            let mut f = try!(File::open(path).map_err(|e| format!("{:?}", e)));
-            let obj = try!(json::from_reader(&mut f).map_err(|e| format!("{:?}", e)));
+            let mut f = try!(File::open(path).map_err(|e| e.to_string()));
+            let mut contents = Vec::new();
+            try!(f.read_to_end(&mut contents).map_err(|e| e.to_string()));
+            let obj = try!(json::from_reader(&mut &contents[..])
+                                .map_err(|e| e.to_string()));
             Ok(Target::from_json(obj))
         }
 
@@ -390,15 +393,16 @@ macro_rules! load_specific {
         let path = {
             let mut target = target.to_string();
             target.push_str(".json");
-            Path::new(target)
+            PathBuf::new(&target)
         };
 
-        let target_path = env::var_os("RUST_TARGET_PATH").unwrap_or(OsString::from_str(""));
+        let target_path = env::var_os("RUST_TARGET_PATH")
+                              .unwrap_or(OsString::from_str(""));
 
         // FIXME 16351: add a sane default search path?
 
-        for dir in os::split_paths(target_path.to_str().unwrap()).iter() {
-            let p =  dir.join(path.clone());
+        for dir in env::split_paths(&target_path) {
+            let p =  dir.join(&path);
             if p.is_file() {
                 return load_file(&p);
             }
diff --git a/src/librustc_back/tempdir.rs b/src/librustc_back/tempdir.rs
new file mode 100644 (file)
index 0000000..4d8619a
--- /dev/null
@@ -0,0 +1,121 @@
+// Copyright 2015 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.
+
+use std::env;
+use std::io::{self, Error, ErrorKind};
+use std::fs;
+use std::path::{self, PathBuf, AsPath};
+use std::rand::{thread_rng, Rng};
+
+/// A wrapper for a path to temporary directory implementing automatic
+/// scope-based deletion.
+pub struct TempDir {
+    path: Option<PathBuf>,
+}
+
+// How many times should we (re)try finding an unused random name? It should be
+// enough that an attacker will run out of luck before we run out of patience.
+const NUM_RETRIES: u32 = 1 << 31;
+// How many characters should we include in a random file name? It needs to
+// be enough to dissuade an attacker from trying to preemptively create names
+// of that length, but not so huge that we unnecessarily drain the random number
+// generator of entropy.
+const NUM_RAND_CHARS: uint = 12;
+
+impl TempDir {
+    /// Attempts to make a temporary directory inside of `tmpdir` whose name
+    /// will have the prefix `prefix`. The directory will be automatically
+    /// deleted once the returned wrapper is destroyed.
+    ///
+    /// If no directory can be created, `Err` is returned.
+    #[allow(deprecated)] // rand usage
+    pub fn new_in<P: AsPath + ?Sized>(tmpdir: &P, prefix: &str)
+                                      -> io::Result<TempDir> {
+        let storage;
+        let mut tmpdir = tmpdir.as_path();
+        if !tmpdir.is_absolute() {
+            let cur_dir = try!(env::current_dir());
+            storage = cur_dir.join(tmpdir);
+            tmpdir = &storage;
+            // return TempDir::new_in(&cur_dir.join(tmpdir), prefix);
+        }
+
+        let mut rng = thread_rng();
+        for _ in 0..NUM_RETRIES {
+            let suffix: String = rng.gen_ascii_chars().take(NUM_RAND_CHARS).collect();
+            let leaf = if prefix.len() > 0 {
+                format!("{}.{}", prefix, suffix)
+            } else {
+                // If we're given an empty string for a prefix, then creating a
+                // directory starting with "." would lead to it being
+                // semi-invisible on some systems.
+                suffix
+            };
+            let path = tmpdir.join(&leaf);
+            match fs::create_dir(&path) {
+                Ok(_) => return Ok(TempDir { path: Some(path) }),
+                Err(ref e) if e.kind() == ErrorKind::PathAlreadyExists => {}
+                Err(e) => return Err(e)
+            }
+        }
+
+        Err(Error::new(ErrorKind::PathAlreadyExists,
+                       "too many temporary directories already exist",
+                       None))
+    }
+
+    /// Attempts to make a temporary directory inside of `env::temp_dir()` whose
+    /// name will have the prefix `prefix`. The directory will be automatically
+    /// deleted once the returned wrapper is destroyed.
+    ///
+    /// If no directory can be created, `Err` is returned.
+    #[allow(deprecated)]
+    pub fn new(prefix: &str) -> io::Result<TempDir> {
+        TempDir::new_in(&env::temp_dir(), prefix)
+    }
+
+    /// Unwrap the wrapped `std::path::Path` from the `TempDir` wrapper.
+    /// This discards the wrapper so that the automatic deletion of the
+    /// temporary directory is prevented.
+    pub fn into_path(mut self) -> PathBuf {
+        self.path.take().unwrap()
+    }
+
+    /// Access the wrapped `std::path::Path` to the temporary directory.
+    pub fn path(&self) -> &path::Path {
+        self.path.as_ref().unwrap()
+    }
+
+    /// Close and remove the temporary directory
+    ///
+    /// Although `TempDir` removes the directory on drop, in the destructor
+    /// any errors are ignored. To detect errors cleaning up the temporary
+    /// directory, call `close` instead.
+    pub fn close(mut self) -> io::Result<()> {
+        self.cleanup_dir()
+    }
+
+    fn cleanup_dir(&mut self) -> io::Result<()> {
+        match self.path {
+            Some(ref p) => fs::remove_dir_all(p),
+            None => Ok(())
+        }
+    }
+}
+
+impl Drop for TempDir {
+    fn drop(&mut self) {
+        let _ = self.cleanup_dir();
+    }
+}
+
+// the tests for this module need to change the path using change_dir,
+// and this doesn't play nicely with other tests so these unit tests are located
+// in src/test/run-pass/tempfile.rs
index 370a5d48decaec85298da73575468e6a98efb5f0..0367130c1320fe3e65fc8b430a2d34ec69b81f30 100644 (file)
@@ -8,6 +8,9 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_bitflags"]
 #![feature(staged_api)]
 #![staged_api]
@@ -83,7 +86,7 @@
 ///     let mut flags = FLAG_A | FLAG_B;
 ///     flags.clear();
 ///     assert!(flags.is_empty());
-///     assert_eq!(format!("{:?}", flags).as_slice(), "hi!");
+///     assert_eq!(format!("{:?}", flags), "hi!");
 /// }
 /// ```
 ///
@@ -316,7 +319,7 @@ mod tests {
 
     bitflags! {
         flags AnotherSetOfFlags: i8 {
-            const AnotherFlag = -1_i8,
+            const AnotherFlag = -1,
         }
     }
 
@@ -327,7 +330,7 @@ fn test_bits(){
         assert_eq!(FlagABC.bits(), 0b00000111);
 
         assert_eq!(AnotherSetOfFlags::empty().bits(), 0b00);
-        assert_eq!(AnotherFlag.bits(), !0_i8);
+        assert_eq!(AnotherFlag.bits(), !0);
     }
 
     #[test]
@@ -338,7 +341,7 @@ fn test_from_bits() {
         assert!(Flags::from_bits(0b11) == Some(FlagA | FlagB));
         assert!(Flags::from_bits(0b1000) == None);
 
-        assert!(AnotherSetOfFlags::from_bits(!0_i8) == Some(AnotherFlag));
+        assert!(AnotherSetOfFlags::from_bits(!0) == Some(AnotherFlag));
     }
 
     #[test]
@@ -350,7 +353,7 @@ fn test_from_bits_truncate() {
         assert!(Flags::from_bits_truncate(0b1000) == Flags::empty());
         assert!(Flags::from_bits_truncate(0b1001) == FlagA);
 
-        assert!(AnotherSetOfFlags::from_bits_truncate(0_i8) == AnotherSetOfFlags::empty());
+        assert!(AnotherSetOfFlags::from_bits_truncate(0) == AnotherSetOfFlags::empty());
     }
 
     #[test]
index 53761eb14713def82f45a671a5a2dc45a3f6daab..84636ebaae42b608d7ce09f161bfbb5574d7e075 100644 (file)
@@ -165,7 +165,7 @@ fn note_move_destination(bccx: &BorrowckCtxt,
         bccx.span_note(
             move_to_span,
             "attempting to move value to here");
-        bccx.span_help(
+        bccx.fileline_help(
             move_to_span,
             &format!("to prevent the move, \
                      use `ref {0}` or `ref mut {0}` to capture value by \
index 67462ab01003e29ec33f3f21e3a1cd1998ee3bfa..b176d8d4118a394cf2186a27c976d9c8ce0d6e99 100644 (file)
@@ -312,7 +312,7 @@ fn to_type(&self) -> ty::Ty<'tcx> { self.ty }
 // FIXME (pnkfelix): See discussion here
 // https://github.com/pnkfelix/rust/commit/
 //     b2b39e8700e37ad32b486b9a8409b50a8a53aa51#commitcomment-7892003
-static DOWNCAST_PRINTED_OPERATOR : &'static str = " as ";
+const DOWNCAST_PRINTED_OPERATOR: &'static str = " as ";
 
 // A local, "cleaned" version of `mc::InteriorKind` that drops
 // information that is not relevant to loan-path analysis. (In
@@ -643,7 +643,7 @@ pub fn report_use_of_moved_value<'b>(&self,
                             ol,
                             moved_lp_msg,
                             pat_ty.user_string(self.tcx)));
-                self.tcx.sess.span_help(span,
+                self.tcx.sess.fileline_help(span,
                     "use `ref` to override");
             }
 
@@ -675,7 +675,7 @@ pub fn report_use_of_moved_value<'b>(&self,
                             moved_lp_msg,
                             expr_ty.user_string(self.tcx),
                             suggestion));
-                self.tcx.sess.span_help(expr_span, help);
+                self.tcx.sess.fileline_help(expr_span, help);
             }
         }
 
@@ -704,9 +704,9 @@ pub fn report_partial_reinitialization_of_uninitialized_structure(
         self.tcx
             .sess
             .span_err(span,
-                      (format!("partial reinitialization of uninitialized \
+                      &format!("partial reinitialization of uninitialized \
                                structure `{}`",
-                               self.loan_path_to_string(lp))).as_slice());
+                               self.loan_path_to_string(lp)));
     }
 
     pub fn report_reassigned_immutable_variable(&self,
@@ -741,6 +741,10 @@ pub fn span_help(&self, s: Span, m: &str) {
         self.tcx.sess.span_help(s, m);
     }
 
+    pub fn fileline_help(&self, s: Span, m: &str) {
+        self.tcx.sess.fileline_help(s, m);
+    }
+
     pub fn bckerr_to_string(&self, err: &BckError<'tcx>) -> String {
         match err.code {
             err_mutbl => {
@@ -870,7 +874,7 @@ pub fn report_aliasability_violation(&self,
         }
 
         if is_closure {
-            self.tcx.sess.span_help(
+            self.tcx.sess.fileline_help(
                 span,
                 "closures behind references must be called via `&mut`");
         }
index 0f7f8e61e37e0a1788c2a20ae0d79a48fd14ff22..8846f70fbd335febf9b005813b07dfc2b885bb03 100644 (file)
@@ -91,8 +91,7 @@ fn clone(&self) -> MovePathIndex {
 }
 
 #[allow(non_upper_case_globals)]
-static InvalidMovePathIndex: MovePathIndex =
-    MovePathIndex(usize::MAX);
+const InvalidMovePathIndex: MovePathIndex = MovePathIndex(usize::MAX);
 
 /// Index into `MoveData.moves`, used like a pointer
 #[derive(Copy, PartialEq)]
@@ -105,8 +104,7 @@ fn get(&self) -> uint {
 }
 
 #[allow(non_upper_case_globals)]
-static InvalidMoveIndex: MoveIndex =
-    MoveIndex(usize::MAX);
+const InvalidMoveIndex: MoveIndex = MoveIndex(usize::MAX);
 
 pub struct MovePath<'tcx> {
     /// Loan path corresponding to this move path
index b7cfda280925701495074fcb68d1955b03b3a058..e09457970e12f776513d60245527aab02288f6c5 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_borrowck"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
index 425ec7ec452eecd4b2347c36a5d32257f7accf01..dc27a30110950454f813cf5ac82003408a379e37 100644 (file)
 use serialize::json;
 
 use std::env;
-use std::os;
 use std::ffi::OsString;
-use std::old_io::fs;
-use std::old_io;
+use std::fs;
+use std::io::{self, Write};
+use std::path::{Path, PathBuf};
 use syntax::ast;
 use syntax::ast_map;
 use syntax::attr;
@@ -48,8 +48,8 @@
 pub fn compile_input(sess: Session,
                      cfg: ast::CrateConfig,
                      input: &Input,
-                     outdir: &Option<Path>,
-                     output: &Option<Path>,
+                     outdir: &Option<PathBuf>,
+                     output: &Option<PathBuf>,
                      addl_plugins: Option<Vec<String>>,
                      control: CompileController) {
     macro_rules! controller_entry_point{($point: ident, $make_state: expr) => ({
@@ -166,7 +166,7 @@ pub fn anon_src() -> String {
 pub fn source_name(input: &Input) -> String {
     match *input {
         // FIXME (#9639): This needs to handle non-utf8 paths
-        Input::File(ref ifile) => ifile.as_str().unwrap().to_string(),
+        Input::File(ref ifile) => ifile.to_str().unwrap().to_string(),
         Input::Str(_) => anon_src()
     }
 }
@@ -243,12 +243,12 @@ pub struct CompileState<'a, 'ast: 'a, 'tcx: 'a> {
 impl<'a, 'ast, 'tcx> CompileState<'a, 'ast, 'tcx> {
     fn empty(input: &'a Input,
              session: &'a Session,
-             out_dir: &'a Option<Path>)
+             out_dir: &'a Option<PathBuf>)
              -> CompileState<'a, 'ast, 'tcx> {
         CompileState {
             input: input,
             session: session,
-            out_dir: out_dir.as_ref(),
+            out_dir: out_dir.as_ref().map(|s| &**s),
             cfg: None,
             krate: None,
             crate_name: None,
@@ -263,7 +263,7 @@ fn empty(input: &'a Input,
 
     fn state_after_parse(input: &'a Input,
                          session: &'a Session,
-                         out_dir: &'a Option<Path>,
+                         out_dir: &'a Option<PathBuf>,
                          krate: &'a ast::Crate)
                          -> CompileState<'a, 'ast, 'tcx> {
         CompileState {
@@ -274,7 +274,7 @@ fn state_after_parse(input: &'a Input,
 
     fn state_after_expand(input: &'a Input,
                           session: &'a Session,
-                          out_dir: &'a Option<Path>,
+                          out_dir: &'a Option<PathBuf>,
                           expanded_crate: &'a ast::Crate,
                           crate_name: &'a str)
                           -> CompileState<'a, 'ast, 'tcx> {
@@ -287,7 +287,7 @@ fn state_after_expand(input: &'a Input,
 
     fn state_after_write_deps(input: &'a Input,
                               session: &'a Session,
-                              out_dir: &'a Option<Path>,
+                              out_dir: &'a Option<PathBuf>,
                               ast_map: &'a ast_map::Map<'ast>,
                               expanded_crate: &'a ast::Crate,
                               crate_name: &'a str)
@@ -302,7 +302,7 @@ fn state_after_write_deps(input: &'a Input,
 
     fn state_after_analysis(input: &'a Input,
                             session: &'a Session,
-                            out_dir: &'a Option<Path>,
+                            out_dir: &'a Option<PathBuf>,
                             expanded_crate: &'a ast::Crate,
                             analysis: &'a ty::CrateAnalysis<'tcx>,
                             tcx: &'a ty::ctxt<'tcx>)
@@ -318,7 +318,7 @@ fn state_after_analysis(input: &'a Input,
 
     fn state_after_llvm(input: &'a Input,
                         session: &'a Session,
-                        out_dir: &'a Option<Path>,
+                        out_dir: &'a Option<PathBuf>,
                         trans: &'a trans::CrateTranslation)
                         -> CompileState<'a, 'ast, 'tcx> {
         CompileState {
@@ -472,7 +472,7 @@ pub fn phase_2_configure_and_expand(sess: &Session,
             if cfg!(windows) {
                 _old_path = env::var_os("PATH").unwrap_or(_old_path);
                 let mut new_path = sess.host_filesearch(PathKind::All).get_dylib_search_paths();
-                new_path.extend(os::split_paths(_old_path.to_str().unwrap()).into_iter());
+                new_path.extend(env::split_paths(&_old_path));
                 env::set_var("PATH", &env::join_paths(new_path.iter()).unwrap());
             }
             let features = sess.features.borrow();
@@ -493,12 +493,16 @@ pub fn phase_2_configure_and_expand(sess: &Session,
         }
     );
 
-    // Needs to go *after* expansion to be able to check the results of macro expansion.
-    time(time_passes, "complete gated feature checking", (), |_| {
+    // Needs to go *after* expansion to be able to check the results
+    // of macro expansion.  This runs before #[cfg] to try to catch as
+    // much as possible (e.g. help the programmer avoid platform
+    // specific differences)
+    time(time_passes, "complete gated feature checking 1", (), |_| {
         let features =
             syntax::feature_gate::check_crate(sess.codemap(),
-                                          &sess.parse_sess.span_diagnostic,
-                                          &krate);
+                                              &sess.parse_sess.span_diagnostic,
+                                              &krate,
+                                              true);
         *sess.features.borrow_mut() = features;
         sess.abort_if_errors();
     });
@@ -521,6 +525,19 @@ pub fn phase_2_configure_and_expand(sess: &Session,
     time(time_passes, "checking that all macro invocations are gone", &krate, |krate|
          syntax::ext::expand::check_for_macros(&sess.parse_sess, krate));
 
+    // One final feature gating of the true AST that gets compiled
+    // later, to make sure we've got everything (e.g. configuration
+    // can insert new attributes via `cfg_attr`)
+    time(time_passes, "complete gated feature checking 2", (), |_| {
+        let features =
+            syntax::feature_gate::check_crate(sess.codemap(),
+                                              &sess.parse_sess.span_diagnostic,
+                                              &krate,
+                                              false);
+        *sess.features.borrow_mut() = features;
+        sess.abort_if_errors();
+    });
+
     Some(krate)
 }
 
@@ -717,7 +734,7 @@ pub fn phase_5_run_llvm_passes(sess: &Session,
 
         // Remove assembly source, unless --save-temps was specified
         if !sess.opts.cg.save_temps {
-            fs::unlink(&outputs.temp_path(config::OutputTypeAssembly)).unwrap();
+            fs::remove_file(&outputs.temp_path(config::OutputTypeAssembly)).unwrap();
         }
     } else {
         time(sess.time_passes(), "LLVM passes", (), |_|
@@ -737,7 +754,7 @@ pub fn phase_6_link_output(sess: &Session,
                            outputs: &OutputFilenames) {
     let old_path = env::var_os("PATH").unwrap_or(OsString::from_str(""));
     let mut new_path = sess.host_filesearch(PathKind::All).get_tools_search_paths();
-    new_path.extend(os::split_paths(old_path.to_str().unwrap()).into_iter());
+    new_path.extend(env::split_paths(&old_path));
     env::set_var("PATH", &env::join_paths(new_path.iter()).unwrap());
 
     time(sess.time_passes(), "linking", (), |_|
@@ -793,17 +810,19 @@ fn write_out_deps(sess: &Session,
         _ => return,
     };
 
-    let result = (|| -> old_io::IoResult<()> {
+    let result = (|| -> io::Result<()> {
         // Build a list of files used to compile the output and
         // write Makefile-compatible dependency rules
         let files: Vec<String> = sess.codemap().files.borrow()
-                                   .iter().filter(|fmap| fmap.is_real_file())
+                                   .iter()
+                                   .filter(|fmap| fmap.is_real_file())
+                                   .filter(|fmap| !fmap.is_imported())
                                    .map(|fmap| escape_dep_filename(&fmap.name))
                                    .collect();
-        let mut file = try!(old_io::File::create(&deps_filename));
+        let mut file = try!(fs::File::create(&deps_filename));
         for path in &out_filenames {
-            try!(write!(&mut file as &mut Writer,
-                          "{}: {}\n\n", path.display(), files.connect(" ")));
+            try!(write!(&mut file,
+                        "{}: {}\n\n", path.display(), files.connect(" ")));
         }
         Ok(())
     })();
@@ -896,8 +915,8 @@ pub fn collect_crate_metadata(session: &Session,
 }
 
 pub fn build_output_filenames(input: &Input,
-                              odir: &Option<Path>,
-                              ofile: &Option<Path>,
+                              odir: &Option<PathBuf>,
+                              ofile: &Option<PathBuf>,
                               attrs: &[ast::Attribute],
                               sess: &Session)
                            -> OutputFilenames {
@@ -908,7 +927,7 @@ pub fn build_output_filenames(input: &Input,
             // We want to toss everything after the final '.'
             let dirpath = match *odir {
                 Some(ref d) => d.clone(),
-                None => Path::new(".")
+                None => PathBuf::new("")
             };
 
             // If a crate name is present, we use it as the link name
@@ -935,9 +954,13 @@ pub fn build_output_filenames(input: &Input,
             if *odir != None {
                 sess.warn("ignoring --out-dir flag due to -o flag.");
             }
+
+            let cur_dir = Path::new("");
+
             OutputFilenames {
-                out_directory: out_file.dir_path(),
-                out_filestem: out_file.filestem_str().unwrap().to_string(),
+                out_directory: out_file.parent().unwrap_or(cur_dir).to_path_buf(),
+                out_filestem: out_file.file_stem().unwrap()
+                                      .to_str().unwrap().to_string(),
                 single_output_file: ofile,
                 extra: sess.opts.cg.extra_filename.clone(),
             }
index d08fb2b313ef6776dde2c2a2ed1486cfbb1f2499..716b1116a2062aba42f2a9ccbc9a0304398f341d 100644 (file)
@@ -14,6 +14,8 @@
 //!
 //! This API is completely unstable and subject to change.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_driver"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
 #![feature(int_uint)]
 #![feature(old_io)]
 #![feature(libc)]
-#![feature(os)]
-#![feature(old_path)]
 #![feature(quote)]
 #![feature(rustc_diagnostic_macros)]
 #![feature(rustc_private)]
 #![feature(unsafe_destructor)]
 #![feature(staged_api)]
-#![feature(unicode)]
 #![feature(exit_status)]
+#![feature(path)]
+#![feature(io)]
 
 extern crate arena;
 extern crate flate;
 use rustc::util::common::time;
 
 use std::cmp::Ordering::Equal;
-use std::old_io::{self, stdio};
-use std::iter::repeat;
 use std::env;
+use std::iter::repeat;
+use std::old_io::{self, stdio};
+use std::path::PathBuf;
 use std::sync::mpsc::channel;
 use std::thread;
 
@@ -93,7 +95,7 @@
 pub mod pretty;
 
 
-static BUG_REPORT_URL: &'static str =
+const BUG_REPORT_URL: &'static str =
     "https://github.com/rust-lang/rust/blob/master/CONTRIBUTING.md#bug-reports";
 
 
@@ -159,14 +161,14 @@ macro_rules! do_or_return {($expr: expr) => {
 }
 
 // Extract output directory and file from matches.
-fn make_output(matches: &getopts::Matches) -> (Option<Path>, Option<Path>) {
-    let odir = matches.opt_str("out-dir").map(|o| Path::new(o));
-    let ofile = matches.opt_str("o").map(|o| Path::new(o));
+fn make_output(matches: &getopts::Matches) -> (Option<PathBuf>, Option<PathBuf>) {
+    let odir = matches.opt_str("out-dir").map(|o| PathBuf::new(&o));
+    let ofile = matches.opt_str("o").map(|o| PathBuf::new(&o));
     (odir, ofile)
 }
 
 // Extract input (string or file and optional path) from matches.
-fn make_input(free_matches: &[String]) -> Option<(Input, Option<Path>)> {
+fn make_input(free_matches: &[String]) -> Option<(Input, Option<PathBuf>)> {
     if free_matches.len() == 1 {
         let ifile = &free_matches[0][..];
         if ifile == "-" {
@@ -174,7 +176,7 @@ fn make_input(free_matches: &[String]) -> Option<(Input, Option<Path>)> {
             let src = String::from_utf8(contents).unwrap();
             Some((Input::Str(src), None))
         } else {
-            Some((Input::File(Path::new(ifile)), Some(Path::new(ifile))))
+            Some((Input::File(PathBuf::new(ifile)), Some(PathBuf::new(ifile))))
         }
     } else {
         None
@@ -215,14 +217,15 @@ fn late_callback(&mut self,
                      &getopts::Matches,
                      &Session,
                      &Input,
-                     &Option<Path>,
-                     &Option<Path>)
+                     &Option<PathBuf>,
+                     &Option<PathBuf>)
                      -> Compilation;
 
     // Called after we extract the input from the arguments. Gives the implementer
     // an opportunity to change the inputs or to add some custom input handling.
     // The default behaviour is to simply pass through the inputs.
-    fn some_input(&mut self, input: Input, input_path: Option<Path>) -> (Input, Option<Path>) {
+    fn some_input(&mut self, input: Input, input_path: Option<PathBuf>)
+                  -> (Input, Option<PathBuf>) {
         (input, input_path)
     }
 
@@ -234,10 +237,10 @@ fn some_input(&mut self, input: Input, input_path: Option<Path>) -> (Input, Opti
     fn no_input(&mut self,
                 &getopts::Matches,
                 &config::Options,
-                &Option<Path>,
-                &Option<Path>,
+                &Option<PathBuf>,
+                &Option<PathBuf>,
                 &diagnostics::registry::Registry)
-                -> Option<(Input, Option<Path>)>;
+                -> Option<(Input, Option<PathBuf>)>;
 
     // Parse pretty printing information from the arguments. The implementer can
     // choose to ignore this (the default will return None) which will skip pretty
@@ -293,10 +296,10 @@ fn early_callback(&mut self,
     fn no_input(&mut self,
                 matches: &getopts::Matches,
                 sopts: &config::Options,
-                odir: &Option<Path>,
-                ofile: &Option<Path>,
+                odir: &Option<PathBuf>,
+                ofile: &Option<PathBuf>,
                 descriptions: &diagnostics::registry::Registry)
-                -> Option<(Input, Option<Path>)> {
+                -> Option<(Input, Option<PathBuf>)> {
         match matches.free.len() {
             0 => {
                 if sopts.describe_lints {
@@ -346,8 +349,8 @@ fn late_callback(&mut self,
                      matches: &getopts::Matches,
                      sess: &Session,
                      input: &Input,
-                     odir: &Option<Path>,
-                     ofile: &Option<Path>)
+                     odir: &Option<PathBuf>,
+                     ofile: &Option<PathBuf>)
                      -> Compilation {
         RustcDefaultCalls::print_crate_info(sess, Some(input), odir, ofile).and_then(
             || RustcDefaultCalls::list_metadata(sess, matches, input))
@@ -400,11 +403,12 @@ pub fn list_metadata(sess: &Session,
         if r.contains(&("ls".to_string())) {
             match input {
                 &Input::File(ref ifile) => {
-                    let mut stdout = old_io::stdout();
                     let path = &(*ifile);
+                    let mut v = Vec::new();
                     metadata::loader::list_file_metadata(sess.target.target.options.is_like_osx,
                                                          path,
-                                                         &mut stdout).unwrap();
+                                                         &mut v).unwrap();
+                    println!("{}", String::from_utf8(v).unwrap());
                 }
                 &Input::Str(_) => {
                     early_error("cannot list metadata for stdin");
@@ -419,8 +423,8 @@ pub fn list_metadata(sess: &Session,
 
     fn print_crate_info(sess: &Session,
                         input: Option<&Input>,
-                        odir: &Option<Path>,
-                        ofile: &Option<Path>)
+                        odir: &Option<PathBuf>,
+                        ofile: &Option<PathBuf>)
                         -> Compilation {
         if sess.opts.prints.len() == 0 {
             return Compilation::Continue;
@@ -457,7 +461,8 @@ fn print_crate_info(sess: &Session,
                                                              style,
                                                              &id,
                                                              &t_outputs.with_extension(""));
-                        println!("{}", fname.filename_display());
+                        println!("{}", fname.file_name().unwrap()
+                                            .to_string_lossy());
                     }
                 }
             }
@@ -612,8 +617,7 @@ fn sort_lint_groups(lints: Vec<(&'static str, Vec<lint::LintId>, bool)>)
 
     let print_lint_groups = |lints: Vec<(&'static str, Vec<lint::LintId>)>| {
         for (name, to) in lints {
-            let name = name.chars().map(|x| x.to_lowercase())
-                           .collect::<String>().replace("_", "-");
+            let name = name.to_lowercase().replace("_", "-");
             let desc = to.into_iter().map(|x| x.as_str().replace("_", "-"))
                          .collect::<Vec<String>>().connect(", ");
             println!("    {}  {}",
@@ -769,8 +773,9 @@ fn parse_crate_attrs(sess: &Session, input: &Input) ->
 ///
 /// The diagnostic emitter yielded to the procedure should be used for reporting
 /// errors of the compiler.
+#[allow(deprecated)]
 pub fn monitor<F:FnOnce()+Send+'static>(f: F) {
-    static STACK_SIZE: uint = 8 * 1024 * 1024; // 8MB
+    const STACK_SIZE: uint = 8 * 1024 * 1024; // 8MB
 
     let (tx, rx) = channel();
     let w = old_io::ChanWriter::new(tx);
index 22473099baf60311fbe59b6e505a56a84e4ad35d..ffb2a05e4374920caea984151cfd91c1b135aa00 100644 (file)
 
 use graphviz as dot;
 
-use std::old_io::{self, MemReader};
+use std::fs::File;
+use std::io::{self, Write};
+use std::old_io;
 use std::option;
+use std::path::PathBuf;
 use std::str::FromStr;
 
 #[derive(Copy, PartialEq, Debug)]
@@ -208,7 +211,7 @@ fn pp_ann<'a>(&'a self) -> &'a pprust::PpAnn { self }
 impl<'ast> pprust::PpAnn for IdentifiedAnnotation<'ast> {
     fn pre(&self,
            s: &mut pprust::State,
-           node: pprust::AnnNode) -> old_io::IoResult<()> {
+           node: pprust::AnnNode) -> io::Result<()> {
         match node {
             pprust::NodeExpr(_) => s.popen(),
             _ => Ok(())
@@ -216,7 +219,7 @@ fn pre(&self,
     }
     fn post(&self,
             s: &mut pprust::State,
-            node: pprust::AnnNode) -> old_io::IoResult<()> {
+            node: pprust::AnnNode) -> io::Result<()> {
         match node {
             pprust::NodeIdent(_) | pprust::NodeName(_) => Ok(()),
 
@@ -259,7 +262,7 @@ fn pp_ann<'a>(&'a self) -> &'a pprust::PpAnn { self }
 impl<'ast> pprust::PpAnn for HygieneAnnotation<'ast> {
     fn post(&self,
             s: &mut pprust::State,
-            node: pprust::AnnNode) -> old_io::IoResult<()> {
+            node: pprust::AnnNode) -> io::Result<()> {
         match node {
             pprust::NodeIdent(&ast::Ident { name: ast::Name(nm), ctxt }) => {
                 try!(pp::space(&mut s.s));
@@ -294,7 +297,7 @@ fn pp_ann<'a>(&'a self) -> &'a pprust::PpAnn { self }
 impl<'tcx> pprust::PpAnn for TypedAnnotation<'tcx> {
     fn pre(&self,
            s: &mut pprust::State,
-           node: pprust::AnnNode) -> old_io::IoResult<()> {
+           node: pprust::AnnNode) -> io::Result<()> {
         match node {
             pprust::NodeExpr(_) => s.popen(),
             _ => Ok(())
@@ -302,7 +305,7 @@ fn pre(&self,
     }
     fn post(&self,
             s: &mut pprust::State,
-            node: pprust::AnnNode) -> old_io::IoResult<()> {
+            node: pprust::AnnNode) -> io::Result<()> {
         let tcx = &self.analysis.ty_cx;
         match node {
             pprust::NodeExpr(expr) => {
@@ -507,7 +510,7 @@ pub fn pretty_print_input(sess: Session,
                           input: &Input,
                           ppm: PpMode,
                           opt_uii: Option<UserIdentifiedItem>,
-                          ofile: Option<Path>) {
+                          ofile: Option<PathBuf>) {
     let krate = driver::phase_1_parse_input(&sess, cfg, input);
 
     let krate = if let PpmSource(PpmEveryBodyLoops) = ppm {
@@ -542,25 +545,20 @@ pub fn pretty_print_input(sess: Session,
 
     let src_name = driver::source_name(input);
     let src = sess.codemap().get_filemap(&src_name[..])
-                            .src.as_bytes().to_vec();
-    let mut rdr = MemReader::new(src);
+                            .src
+                            .as_ref()
+                            .unwrap()
+                            .as_bytes()
+                            .to_vec();
+    let mut rdr = &src[..];
 
-    let out = match ofile {
-        None => box old_io::stdout() as Box<Writer+'static>,
-        Some(p) => {
-            let r = old_io::File::create(&p);
-            match r {
-                Ok(w) => box w as Box<Writer+'static>,
-                Err(e) => panic!("print-print failed to open {} due to {}",
-                                p.display(), e),
-            }
-        }
-    };
+    let mut out = Vec::new();
 
     match (ppm, opt_uii) {
-        (PpmSource(s), None) =>
+        (PpmSource(s), None) => {
+            let out: &mut Write = &mut out;
             s.call_with_pp_support(
-                sess, ast_map, &arenas, id, out, |annotation, out| {
+                sess, ast_map, &arenas, id, box out, |annotation, out| {
                     debug!("pretty printing source code {:?}", s);
                     let sess = annotation.sess();
                     pprust::print_crate(sess.codemap(),
@@ -571,9 +569,11 @@ pub fn pretty_print_input(sess: Session,
                                         out,
                                         annotation.pp_ann(),
                                         is_expanded)
-                }),
+            })
+        }
 
-        (PpmSource(s), Some(uii)) =>
+        (PpmSource(s), Some(uii)) => {
+            let out: &mut Write = &mut out;
             s.call_with_pp_support(
                 sess, ast_map, &arenas, id, (out,uii), |annotation, (out,uii)| {
                     debug!("pretty printing source code {:?}", s);
@@ -585,7 +585,7 @@ pub fn pretty_print_input(sess: Session,
                                                       sess.diagnostic(),
                                                       src_name.to_string(),
                                                       &mut rdr,
-                                                      out,
+                                                      box out,
                                                       annotation.pp_ann(),
                                                       is_expanded);
                     for node_id in uii.all_matching_node_ids(ast_map) {
@@ -596,7 +596,8 @@ pub fn pretty_print_input(sess: Session,
                         try!(pp::hardbreak(&mut pp_state.s));
                     }
                     pp::eof(&mut pp_state.s)
-                }),
+                })
+        }
 
         (PpmFlowGraph(mode), opt_uii) => {
             debug!("pretty printing flow graph for {:?}", opt_uii);
@@ -614,6 +615,7 @@ pub fn pretty_print_input(sess: Session,
             });
 
             let code = blocks::Code::from_node(node);
+            let out: &mut Writer = &mut out;
             match code {
                 Some(code) => {
                     let variants = gather_flowgraph_variants(&sess);
@@ -638,14 +640,25 @@ pub fn pretty_print_input(sess: Session,
                 }
             }
         }
-    }.unwrap()
+    }.unwrap();
+
+    match ofile {
+        None => print!("{}", String::from_utf8(out).unwrap()),
+        Some(p) => {
+            match File::create(&p) {
+                Ok(mut w) => w.write_all(&out).unwrap(),
+                Err(e) => panic!("print-print failed to open {} due to {}",
+                                p.display(), e),
+            }
+        }
+    }
 }
 
 fn print_flowgraph<W:old_io::Writer>(variants: Vec<borrowck_dot::Variant>,
                                  analysis: ty::CrateAnalysis,
                                  code: blocks::Code,
                                  mode: PpFlowGraphMode,
-                                 mut out: W) -> old_io::IoResult<()> {
+                                 mut out: W) -> io::Result<()> {
     let ty_cx = &analysis.ty_cx;
     let cfg = match code {
         blocks::BlockCode(block) => cfg::CFG::new(ty_cx, &*block),
@@ -685,17 +698,10 @@ fn print_flowgraph<W:old_io::Writer>(variants: Vec<borrowck_dot::Variant>,
         }
     }
 
-    fn expand_err_details(r: old_io::IoResult<()>) -> old_io::IoResult<()> {
+    fn expand_err_details(r: old_io::IoResult<()>) -> io::Result<()> {
         r.map_err(|ioerr| {
-            let orig_detail = ioerr.detail.clone();
-            let m = "graphviz::render failed";
-            old_io::IoError {
-                detail: Some(match orig_detail {
-                    None => m.to_string(),
-                    Some(d) => format!("{}: {}", m, d)
-                }),
-                ..ioerr
-            }
+            io::Error::new(io::ErrorKind::Other, "graphviz::render failed",
+                           Some(ioerr.to_string()))
         })
     }
 }
index cdbee9da334228d42b0ea48443c0456d6ce7d7b7..23f07c8e25c1145126c61554503a2e269110d82f 100644 (file)
@@ -44,7 +44,7 @@ struct RH<'a> {
     sub: &'a [RH<'a>]
 }
 
-static EMPTY_SOURCE_STR: &'static str = "#![feature(no_std)] #![no_std]";
+const EMPTY_SOURCE_STR: &'static str = "#![feature(no_std)] #![no_std]";
 
 struct ExpectErrorEmitter {
     messages: Vec<String>
index fe047d2334eecec5650e1fb346339ae2d5a309a0..99febcfe346218290dae18c0b124675e85910dd9 100644 (file)
@@ -432,8 +432,8 @@ fn check_def(&mut self, sp: Span, id: ast::NodeId) {
             }
             def::DefTy(..) => {
                 let tty = match self.cx.tcx.ast_ty_to_ty_cache.borrow().get(&id) {
-                    Some(&ty::atttce_resolved(t)) => t,
-                    _ => panic!("ast_ty_to_ty_cache was incomplete after typeck!")
+                    Some(&t) => t,
+                    None => panic!("ast_ty_to_ty_cache was incomplete after typeck!")
                 };
 
                 if !ty::is_ffi_safe(self.cx.tcx, tty) {
@@ -571,7 +571,7 @@ struct RawPtrDeriveVisitor<'a, 'tcx: 'a> {
 
 impl<'a, 'tcx, 'v> Visitor<'v> for RawPtrDeriveVisitor<'a, 'tcx> {
     fn visit_ty(&mut self, ty: &ast::Ty) {
-        static MSG: &'static str = "use of `#[derive]` with a raw pointer";
+        const MSG: &'static str = "use of `#[derive]` with a raw pointer";
         if let ast::TyPtr(..) = ty.node {
             self.cx.span_lint(RAW_POINTER_DERIVE, ty.span, MSG);
         }
@@ -810,11 +810,11 @@ fn is_camel_case(ident: ast::Ident) -> bool {
         fn to_camel_case(s: &str) -> String {
             s.split('_').flat_map(|word| word.chars().enumerate().map(|(i, c)|
                 if i == 0 {
-                    c.to_uppercase()
+                    c.to_uppercase().collect::<String>()
                 } else {
-                    c
+                    c.to_string()
                 }
-            )).collect()
+            )).collect::<Vec<_>>().concat()
         }
 
         let s = token::get_ident(ident);
@@ -947,7 +947,7 @@ fn to_snake_case(mut str: &str) -> String {
                     buf = String::new();
                 }
                 last_upper = ch.is_uppercase();
-                buf.push(ch.to_lowercase());
+                buf.extend(ch.to_lowercase());
             }
             words.push(buf);
         }
@@ -1064,8 +1064,7 @@ fn check_upper_case(cx: &Context, sort: &str, ident: ast::Ident, span: Span) {
         let s = token::get_ident(ident);
 
         if s.chars().any(|c| c.is_lowercase()) {
-            let uc: String = NonSnakeCase::to_snake_case(&s).chars()
-                                           .map(|c| c.to_uppercase()).collect();
+            let uc = NonSnakeCase::to_snake_case(&s).to_uppercase();
             if uc != &s[..] {
                 cx.span_lint(NON_UPPER_CASE_GLOBALS, span,
                     &format!("{} `{}` should have an upper case name such as `{}`",
@@ -1921,7 +1920,8 @@ fn check_fn(&mut self, cx: &Context, fn_kind: visit::FnKind, _: &ast::FnDecl,
                 for call in &self_call_spans {
                     sess.span_note(*call, "recursive call site")
                 }
-                sess.span_help(sp, "a `loop` may express intention better if this is on purpose")
+                sess.fileline_help(sp, "a `loop` may express intention \
+                                        better if this is on purpose")
             }
         }
 
@@ -2079,7 +2079,7 @@ fn check_item(&mut self, cx: &Context, it: &ast::Item) {
                        !cx.exported_items.contains(&it.id) {
                     let msg = format!("static {} is marked #[no_mangle], but not exported",
                                       it.ident);
-                    cx.span_lint(PRIVATE_NO_MANGLE_STATICS, it.span, msg.as_slice());
+                    cx.span_lint(PRIVATE_NO_MANGLE_STATICS, it.span, &msg);
                 }
             },
             ast::ItemConst(..) => {
index 9eef0f1cf8b0ff75c84f50b60b71fcf687de1447..a49c9db07a0e948fa1b5cb0dac286d3d517256e3 100644 (file)
@@ -19,6 +19,8 @@
 //!
 //! This API is completely unstable and subject to change.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_lint"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
@@ -39,7 +41,6 @@
 #![feature(unsafe_destructor)]
 #![feature(staged_api)]
 #![feature(std_misc)]
-#![feature(unicode)]
 #![cfg_attr(test, feature(test))]
 
 extern crate syntax;
index 14a99026aac8ac18c8e06b377e68981ca534f52b..f54480e3e523c156554aaee021f3f70622930bb6 100644 (file)
@@ -16,6 +16,7 @@
 use std::ffi::CString;
 use std::mem;
 use std::raw;
+use std::path::Path;
 
 pub struct ArchiveRO {
     ptr: ArchiveRef,
@@ -29,14 +30,25 @@ impl ArchiveRO {
     /// If this archive is used with a mutable method, then an error will be
     /// raised.
     pub fn open(dst: &Path) -> Option<ArchiveRO> {
-        unsafe {
-            let s = CString::new(dst.as_vec()).unwrap();
+        return unsafe {
+            let s = path2cstr(dst);
             let ar = ::LLVMRustOpenArchive(s.as_ptr());
             if ar.is_null() {
                 None
             } else {
                 Some(ArchiveRO { ptr: ar })
             }
+        };
+
+        #[cfg(unix)]
+        fn path2cstr(p: &Path) -> CString {
+            use std::os::unix::prelude::*;
+            use std::ffi::AsOsStr;
+            CString::new(p.as_os_str().as_bytes()).unwrap()
+        }
+        #[cfg(windows)]
+        fn path2cstr(p: &Path) -> CString {
+            CString::new(p.to_str().unwrap()).unwrap()
         }
     }
 
index 09a187befb2130ec01ccb05fb84f16265d300e86..0ff96784e58dc4cfd645a7b28ef1b56ac9b203e0 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![allow(non_upper_case_globals)]
 #![allow(non_camel_case_types)]
 #![allow(non_snake_case)]
@@ -28,9 +30,9 @@
 #![feature(int_uint)]
 #![feature(libc)]
 #![feature(link_args)]
-#![feature(old_path)]
 #![feature(staged_api)]
-#![feature(std_misc)]
+#![feature(path)]
+#![cfg_attr(unix, feature(std_misc))]
 
 extern crate libc;
 #[macro_use] #[no_link] extern crate rustc_bitflags;
index 46729988bb6bd976c658bb1c23e4be691c0e8c38..c766b20389e73c8f843161c0ef1b436f65504861 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_privacy"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
@@ -1376,10 +1378,11 @@ fn visit_item(&mut self, item: &ast::Item) {
                             }
                         }
                         Some(ref tr) => {
-                            // Any private types in a trait impl fall into two
+                            // Any private types in a trait impl fall into three
                             // categories.
                             // 1. mentioned in the trait definition
                             // 2. mentioned in the type params/generics
+                            // 3. mentioned in the associated types of the impl
                             //
                             // Those in 1. can only occur if the trait is in
                             // this crate and will've been warned about on the
@@ -1389,6 +1392,16 @@ fn visit_item(&mut self, item: &ast::Item) {
                             // Those in 2. are warned via walk_generics and this
                             // call here.
                             visit::walk_path(self, &tr.path);
+
+                            // Those in 3. are warned with this call.
+                            for impl_item in impl_items {
+                                match *impl_item {
+                                    ast::MethodImplItem(..) => {},
+                                    ast::TypeImplItem(ref typedef) => {
+                                        self.visit_ty(&typedef.typ);
+                                    }
+                                }
+                            }
                         }
                     }
                 } else if trait_ref.is_none() && self_is_public_path {
index 78ce9abe07d92495d9e646a2ae0122845b24231f..ccca99f8b4e4a07637cd0a47f636836e05f9cc17 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_resolve"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
@@ -4115,10 +4117,14 @@ fn resolve_expr(&mut self, expr: &Expr) {
                                           uses it like a function name",
                                          path_name));
 
-                        self.session.span_help(expr.span,
-                            &format!("Did you mean to write: \
-                                     `{} {{ /* fields */ }}`?",
-                                     path_name));
+                        let msg = format!("Did you mean to write: \
+                                           `{} {{ /* fields */ }}`?",
+                                          path_name);
+                        if self.emit_errors {
+                            self.session.fileline_help(expr.span, &msg);
+                        } else {
+                            self.session.span_help(expr.span, &msg);
+                        }
                     } else {
                         // Write the result into the def map.
                         debug!("(resolving expr) resolved `{}`",
@@ -4146,18 +4152,21 @@ fn resolve_expr(&mut self, expr: &Expr) {
                     match type_res.map(|r| r.base_def) {
                         Some(DefTy(struct_id, _))
                             if self.structs.contains_key(&struct_id) => {
-                            self.resolve_error(expr.span,
+                                self.resolve_error(expr.span,
                                     &format!("`{}` is a structure name, but \
                                                 this expression \
                                                 uses it like a function name",
                                                 path_name));
 
-                            self.session.span_help(expr.span,
-                                &format!("Did you mean to write: \
-                                            `{} {{ /* fields */ }}`?",
-                                            path_name));
-
-                        }
+                                let msg = format!("Did you mean to write: \
+                                                     `{} {{ /* fields */ }}`?",
+                                                    path_name);
+                                if self.emit_errors {
+                                    self.session.fileline_help(expr.span, &msg);
+                                } else {
+                                    self.session.span_help(expr.span, &msg);
+                                }
+                            }
                         _ => {
                             // Keep reporting some errors even if they're ignored above.
                             self.resolve_path(expr.id, path, 0, ValueNS, true);
index ea5001aa814b49ab5dab7f8be7c047e8f6456498..3087a8ea45ddc4c9d4ae43ba351c16b0d46b8c9f 100644 (file)
 use util::common::time;
 use util::ppaux;
 use util::sha2::{Digest, Sha256};
+use rustc_back::tempdir::TempDir;
 
-use std::old_io::fs::PathExtensions;
-use std::old_io::{fs, TempDir, Command};
-use std::old_io;
+use std::ffi::OsString;
+use std::fs::{self, PathExt};
+use std::io::{self, Read, Write};
 use std::mem;
+use std::path::{Path, PathBuf};
+use std::process::Command;
 use std::str;
-use std::string::String;
 use flate;
 use serialize::hex::ToHex;
 use syntax::ast;
@@ -156,7 +158,7 @@ pub fn find_crate_name(sess: Option<&Session>,
         return validate(s.to_string(), Some(attr.span));
     }
     if let Input::File(ref path) = *input {
-        if let Some(s) = path.filestem_str() {
+        if let Some(s) = path.file_stem().and_then(|s| s.to_str()) {
             return validate(s.to_string(), None);
         }
     }
@@ -317,7 +319,7 @@ pub fn mangle_exported_name<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>, path: PathEl
     // e.g. `fn foo() { { fn a() {} } { fn a() {} } }`, so we
     // generate unique characters from the node id. For now
     // hopefully 3 characters is enough to avoid collisions.
-    static EXTRA_CHARS: &'static str =
+    const EXTRA_CHARS: &'static str =
         "abcdefghijklmnopqrstuvwxyz\
          ABCDEFGHIJKLMNOPQRSTUVWXYZ\
          0123456789";
@@ -356,7 +358,7 @@ pub fn get_cc_prog(sess: &Session) -> String {
 }
 
 pub fn remove(sess: &Session, path: &Path) {
-    match fs::unlink(path) {
+    match fs::remove_file(path) {
         Ok(..) => {}
         Err(e) => {
             sess.err(&format!("failed to remove {}: {}",
@@ -371,7 +373,7 @@ pub fn remove(sess: &Session, path: &Path) {
 pub fn link_binary(sess: &Session,
                    trans: &CrateTranslation,
                    outputs: &OutputFilenames,
-                   crate_name: &str) -> Vec<Path> {
+                   crate_name: &str) -> Vec<PathBuf> {
     let mut out_filenames = Vec::new();
     for &crate_type in &*sess.crate_types.borrow() {
         if invalid_output_for_target(sess, crate_type) {
@@ -425,35 +427,35 @@ pub fn invalid_output_for_target(sess: &Session,
 }
 
 fn is_writeable(p: &Path) -> bool {
-    match p.stat() {
+    match p.metadata() {
         Err(..) => true,
-        Ok(m) => m.perm & old_io::USER_WRITE == old_io::USER_WRITE
+        Ok(m) => !m.permissions().readonly()
     }
 }
 
 pub fn filename_for_input(sess: &Session,
                           crate_type: config::CrateType,
                           name: &str,
-                          out_filename: &Path) -> Path {
+                          out_filename: &Path) -> PathBuf {
     let libname = format!("{}{}", name, sess.opts.cg.extra_filename);
     match crate_type {
         config::CrateTypeRlib => {
-            out_filename.with_filename(format!("lib{}.rlib", libname))
+            out_filename.with_file_name(&format!("lib{}.rlib", libname))
         }
         config::CrateTypeDylib => {
             let (prefix, suffix) = (&sess.target.target.options.dll_prefix,
                                     &sess.target.target.options.dll_suffix);
-            out_filename.with_filename(format!("{}{}{}",
-                                               prefix,
-                                               libname,
-                                               suffix))
+            out_filename.with_file_name(&format!("{}{}{}",
+                                                  prefix,
+                                                 libname,
+                                                 suffix))
         }
         config::CrateTypeStaticlib => {
-            out_filename.with_filename(format!("lib{}.a", libname))
+            out_filename.with_file_name(&format!("lib{}.a", libname))
         }
         config::CrateTypeExecutable => {
             let suffix = &sess.target.target.options.exe_suffix;
-            out_filename.with_filename(format!("{}{}", libname, suffix))
+            out_filename.with_file_name(&format!("{}{}", libname, suffix))
         }
     }
 }
@@ -462,7 +464,7 @@ fn link_binary_output(sess: &Session,
                       trans: &CrateTranslation,
                       crate_type: config::CrateType,
                       outputs: &OutputFilenames,
-                      crate_name: &str) -> Path {
+                      crate_name: &str) -> PathBuf {
     let obj_filename = outputs.temp_path(OutputTypeObject);
     let out_filename = match outputs.single_output_file {
         Some(ref file) => file.clone(),
@@ -507,10 +509,10 @@ fn link_binary_output(sess: &Session,
     out_filename
 }
 
-fn archive_search_paths(sess: &Session) -> Vec<Path> {
+fn archive_search_paths(sess: &Session) -> Vec<PathBuf> {
     let mut search = Vec::new();
     sess.target_filesearch(PathKind::Native).for_each_lib_search_path(|path, _| {
-        search.push(path.clone());
+        search.push(path.to_path_buf());
         FileDoesntMatch
     });
     return search;
@@ -529,7 +531,7 @@ fn link_rlib<'a>(sess: &'a Session,
     let handler = &sess.diagnostic().handler;
     let config = ArchiveConfig {
         handler: handler,
-        dst: out_filename.clone(),
+        dst: out_filename.to_path_buf(),
         lib_search_paths: archive_search_paths(sess),
         slib_prefix: sess.target.target.options.staticlib_prefix.clone(),
         slib_suffix: sess.target.target.options.staticlib_suffix.clone(),
@@ -588,7 +590,9 @@ fn link_rlib<'a>(sess: &'a Session,
             // the same filename for metadata (stomping over one another)
             let tmpdir = TempDir::new("rustc").ok().expect("needs a temp dir");
             let metadata = tmpdir.path().join(METADATA_FILENAME);
-            match fs::File::create(&metadata).write_all(&trans.metadata) {
+            match fs::File::create(&metadata).and_then(|mut f| {
+                f.write_all(&trans.metadata)
+            }) {
                 Ok(..) => {}
                 Err(e) => {
                     sess.err(&format!("failed to write {}: {}",
@@ -613,28 +617,32 @@ fn link_rlib<'a>(sess: &'a Session,
                 let bc_deflated_filename = obj_filename.with_extension(
                     &format!("{}.bytecode.deflate", i));
 
-                let bc_data = match fs::File::open(&bc_filename).read_to_end() {
-                    Ok(buffer) => buffer,
+                let mut bc_data = Vec::new();
+                match fs::File::open(&bc_filename).and_then(|mut f| {
+                    f.read_to_end(&mut bc_data)
+                }) {
+                    Ok(..) => {}
                     Err(e) => sess.fatal(&format!("failed to read bytecode: {}",
                                                  e))
-                };
+                }
 
                 let bc_data_deflated = match flate::deflate_bytes(&bc_data[..]) {
                     Some(compressed) => compressed,
-                    None => sess.fatal(&format!("failed to compress bytecode from {}",
-                                               bc_filename.display()))
+                    None => sess.fatal(&format!("failed to compress bytecode \
+                                                 from {}",
+                                                 bc_filename.display()))
                 };
 
                 let mut bc_file_deflated = match fs::File::create(&bc_deflated_filename) {
                     Ok(file) => file,
                     Err(e) => {
-                        sess.fatal(&format!("failed to create compressed bytecode \
-                                            file: {}", e))
+                        sess.fatal(&format!("failed to create compressed \
+                                             bytecode file: {}", e))
                     }
                 };
 
                 match write_rlib_bytecode_object_v1(&mut bc_file_deflated,
-                                                    bc_data_deflated.as_slice()) {
+                                                    &bc_data_deflated) {
                     Ok(()) => {}
                     Err(e) => {
                         sess.err(&format!("failed to write compressed bytecode: \
@@ -670,15 +678,23 @@ fn link_rlib<'a>(sess: &'a Session,
     ab
 }
 
-fn write_rlib_bytecode_object_v1<T: Writer>(writer: &mut T,
-                                            bc_data_deflated: &[u8])
-                                         -> ::std::old_io::IoResult<()> {
+fn write_rlib_bytecode_object_v1(writer: &mut Write,
+                                 bc_data_deflated: &[u8]) -> io::Result<()> {
     let bc_data_deflated_size: u64 = bc_data_deflated.len() as u64;
 
-    try! { writer.write_all(RLIB_BYTECODE_OBJECT_MAGIC) };
-    try! { writer.write_le_u32(1) };
-    try! { writer.write_le_u64(bc_data_deflated_size) };
-    try! { writer.write_all(&bc_data_deflated[..]) };
+    try!(writer.write_all(RLIB_BYTECODE_OBJECT_MAGIC));
+    try!(writer.write_all(&[1, 0, 0, 0]));
+    try!(writer.write_all(&[
+        (bc_data_deflated_size >>  0) as u8,
+        (bc_data_deflated_size >>  8) as u8,
+        (bc_data_deflated_size >> 16) as u8,
+        (bc_data_deflated_size >> 24) as u8,
+        (bc_data_deflated_size >> 32) as u8,
+        (bc_data_deflated_size >> 40) as u8,
+        (bc_data_deflated_size >> 48) as u8,
+        (bc_data_deflated_size >> 56) as u8,
+    ]));
+    try!(writer.write_all(&bc_data_deflated));
 
     let number_of_bytes_written_so_far =
         RLIB_BYTECODE_OBJECT_MAGIC.len() +                // magic id
@@ -690,7 +706,7 @@ fn write_rlib_bytecode_object_v1<T: Writer>(writer: &mut T,
     // padding byte to make it even. This works around a crash bug in LLDB
     // (see issue #15950)
     if number_of_bytes_written_so_far % 2 == 1 {
-        try! { writer.write_u8(0) };
+        try!(writer.write_all(&[0]));
     }
 
     return Ok(());
@@ -796,13 +812,13 @@ fn link_natively(sess: &Session, trans: &CrateTranslation, dylib: bool,
                                  pname,
                                  prog.status));
                 sess.note(&format!("{:?}", &cmd));
-                let mut output = prog.error.clone();
-                output.push_all(&prog.output);
+                let mut output = prog.stderr.clone();
+                output.push_all(&prog.stdout);
                 sess.note(str::from_utf8(&output[..]).unwrap());
                 sess.abort_if_errors();
             }
-            debug!("linker stderr:\n{}", String::from_utf8(prog.error).unwrap());
-            debug!("linker stdout:\n{}", String::from_utf8(prog.output).unwrap());
+            debug!("linker stderr:\n{}", String::from_utf8(prog.stderr).unwrap());
+            debug!("linker stdout:\n{}", String::from_utf8(prog.stdout).unwrap());
         },
         Err(e) => {
             sess.err(&format!("could not exec the linker `{}`: {}",
@@ -866,9 +882,9 @@ fn link_args(cmd: &mut Command,
         if t.options.is_like_osx {
             let morestack = lib_path.join("libmorestack.a");
 
-            let mut v = b"-Wl,-force_load,".to_vec();
-            v.push_all(morestack.as_vec());
-            cmd.arg(&v[..]);
+            let mut v = OsString::from_str("-Wl,-force_load,");
+            v.push(&morestack);
+            cmd.arg(&v);
         } else {
             cmd.args(&["-Wl,--whole-archive", "-lmorestack", "-Wl,--no-whole-archive"]);
         }
@@ -878,7 +894,7 @@ fn link_args(cmd: &mut Command,
     // executable. This metadata is in a separate object file from the main
     // object file, so we link that in here.
     if dylib {
-        cmd.arg(obj_filename.with_extension("metadata.o"));
+        cmd.arg(&obj_filename.with_extension("metadata.o"));
     }
 
     if t.options.is_like_osx {
@@ -991,9 +1007,9 @@ fn link_args(cmd: &mut Command,
             cmd.args(&["-dynamiclib", "-Wl,-dylib"]);
 
             if sess.opts.cg.rpath {
-                let mut v = "-Wl,-install_name,@rpath/".as_bytes().to_vec();
-                v.push_all(out_filename.filename().unwrap());
-                cmd.arg(&v[..]);
+                let mut v = OsString::from_str("-Wl,-install_name,@rpath/");
+                v.push(out_filename.file_name().unwrap());
+                cmd.arg(&v);
             }
         } else {
             cmd.arg("-shared");
@@ -1006,23 +1022,23 @@ fn link_args(cmd: &mut Command,
     if sess.opts.cg.rpath {
         let sysroot = sess.sysroot();
         let target_triple = &sess.opts.target_triple;
-        let get_install_prefix_lib_path = || {
+        let mut get_install_prefix_lib_path = || {
             let install_prefix = option_env!("CFG_PREFIX").expect("CFG_PREFIX");
             let tlib = filesearch::relative_target_lib_path(sysroot, target_triple);
-            let mut path = Path::new(install_prefix);
+            let mut path = PathBuf::new(install_prefix);
             path.push(&tlib);
 
             path
         };
-        let rpath_config = RPathConfig {
+        let mut rpath_config = RPathConfig {
             used_crates: sess.cstore.get_used_crates(cstore::RequireDynamic),
-            out_filename: out_filename.clone(),
+            out_filename: out_filename.to_path_buf(),
             has_rpath: sess.target.target.options.has_rpath,
             is_like_osx: sess.target.target.options.is_like_osx,
-            get_install_prefix_lib_path: get_install_prefix_lib_path,
-            realpath: ::util::fs::realpath
+            get_install_prefix_lib_path: &mut get_install_prefix_lib_path,
+            realpath: &mut ::util::fs::realpath
         };
-        cmd.args(&rpath::get_rpath_flags(rpath_config));
+        cmd.args(&rpath::get_rpath_flags(&mut rpath_config));
     }
 
     // Finally add all the linker arguments provided on the command line along
@@ -1082,7 +1098,7 @@ fn add_local_native_libraries(cmd: &mut Command, sess: &Session) {
     let search_path = archive_search_paths(sess);
     for l in staticlibs {
         if takes_hints {
-            cmd.arg(format!("-l{}", l));
+            cmd.arg(&format!("-l{}", l));
         } else {
             // -force_load is the OSX equivalent of --whole-archive, but it
             // involves passing the full path to the library to link.
@@ -1091,9 +1107,9 @@ fn add_local_native_libraries(cmd: &mut Command, sess: &Session) {
                                             &sess.target.target.options.staticlib_suffix,
                                             &search_path[..],
                                             &sess.diagnostic().handler);
-            let mut v = b"-Wl,-force_load,".to_vec();
-            v.push_all(lib.as_vec());
-            cmd.arg(&v[..]);
+            let mut v = OsString::from_str("-Wl,-force_load,");
+            v.push(&lib);
+            cmd.arg(&v);
         }
     }
     if takes_hints {
@@ -1103,7 +1119,7 @@ fn add_local_native_libraries(cmd: &mut Command, sess: &Session) {
     for &(ref l, kind) in others {
         match kind {
             cstore::NativeUnknown => {
-                cmd.arg(format!("-l{}", l));
+                cmd.arg(&format!("-l{}", l));
             }
             cstore::NativeFramework => {
                 cmd.arg("-framework").arg(&l[..]);
@@ -1150,18 +1166,18 @@ fn add_upstream_rust_crates(cmd: &mut Command, sess: &Session,
         let src = sess.cstore.get_used_crate_source(cnum).unwrap();
         match kind {
             cstore::RequireDynamic => {
-                add_dynamic_crate(cmd, sess, src.dylib.unwrap().0)
+                add_dynamic_crate(cmd, sess, &src.dylib.unwrap().0)
             }
             cstore::RequireStatic => {
-                add_static_crate(cmd, sess, tmpdir, src.rlib.unwrap().0)
+                add_static_crate(cmd, sess, tmpdir, &src.rlib.unwrap().0)
             }
         }
 
     }
 
     // Converts a library file-stem into a cc -l argument
-    fn unlib<'a>(config: &config::Config, stem: &'a [u8]) -> &'a [u8] {
-        if stem.starts_with("lib".as_bytes()) && !config.target.options.is_like_windows {
+    fn unlib<'a>(config: &config::Config, stem: &'a str) -> &'a str {
+        if stem.starts_with("lib") && !config.target.options.is_like_windows {
             &stem[3..]
         } else {
             stem
@@ -1170,7 +1186,7 @@ fn unlib<'a>(config: &config::Config, stem: &'a [u8]) -> &'a [u8] {
 
     // Adds the static "rlib" versions of all crates to the command line.
     fn add_static_crate(cmd: &mut Command, sess: &Session, tmpdir: &Path,
-                        cratepath: Path) {
+                        cratepath: &Path) {
         // When performing LTO on an executable output, all of the
         // bytecode from the upstream libraries has already been
         // included in our object file output. We need to modify all of
@@ -1186,12 +1202,12 @@ fn add_static_crate(cmd: &mut Command, sess: &Session, tmpdir: &Path,
         // If we're not doing LTO, then our job is simply to just link
         // against the archive.
         if sess.lto() {
-            let name = cratepath.filename_str().unwrap();
+            let name = cratepath.file_name().unwrap().to_str().unwrap();
             let name = &name[3..name.len() - 5]; // chop off lib/.rlib
             time(sess.time_passes(),
                  &format!("altering {}.rlib", name),
                  (), |()| {
-                let dst = tmpdir.join(cratepath.filename().unwrap());
+                let dst = tmpdir.join(cratepath.file_name().unwrap());
                 match fs::copy(&cratepath, &dst) {
                     Ok(..) => {}
                     Err(e) => {
@@ -1205,7 +1221,11 @@ fn add_static_crate(cmd: &mut Command, sess: &Session, tmpdir: &Path,
                 // Fix up permissions of the copy, as fs::copy() preserves
                 // permissions, but the original file may have been installed
                 // by a package manager and may be read-only.
-                match fs::chmod(&dst, old_io::USER_READ | old_io::USER_WRITE) {
+                match fs::metadata(&dst).and_then(|m| {
+                    let mut perms = m.permissions();
+                    perms.set_readonly(false);
+                    fs::set_permissions(&dst, perms)
+                }) {
                     Ok(..) => {}
                     Err(e) => {
                         sess.err(&format!("failed to chmod {} when preparing \
@@ -1227,7 +1247,7 @@ fn add_static_crate(cmd: &mut Command, sess: &Session, tmpdir: &Path,
                 archive.remove_file(&format!("{}.o", name));
                 let files = archive.files();
                 if files.iter().any(|s| s.ends_with(".o")) {
-                    cmd.arg(dst);
+                    cmd.arg(&dst);
                 }
             });
         } else {
@@ -1236,19 +1256,18 @@ fn add_static_crate(cmd: &mut Command, sess: &Session, tmpdir: &Path,
     }
 
     // Same thing as above, but for dynamic crates instead of static crates.
-    fn add_dynamic_crate(cmd: &mut Command, sess: &Session, cratepath: Path) {
+    fn add_dynamic_crate(cmd: &mut Command, sess: &Session, cratepath: &Path) {
         // If we're performing LTO, then it should have been previously required
         // that all upstream rust dependencies were available in an rlib format.
         assert!(!sess.lto());
 
         // Just need to tell the linker about where the library lives and
         // what its name is
-        let dir = cratepath.dirname();
-        if !dir.is_empty() { cmd.arg("-L").arg(dir); }
-
-        let mut v = "-l".as_bytes().to_vec();
-        v.push_all(unlib(&sess.target, cratepath.filestem().unwrap()));
-        cmd.arg(&v[..]);
+        if let Some(dir) = cratepath.parent() {
+            cmd.arg("-L").arg(dir);
+        }
+        let filestem = cratepath.file_stem().unwrap().to_str().unwrap();
+        cmd.arg(&format!("-l{}", unlib(&sess.target, filestem)));
     }
 }
 
@@ -1286,7 +1305,7 @@ fn add_upstream_native_libraries(cmd: &mut Command, sess: &Session) {
         for &(kind, ref lib) in &libs {
             match kind {
                 cstore::NativeUnknown => {
-                    cmd.arg(format!("-l{}", *lib));
+                    cmd.arg(&format!("-l{}", *lib));
                 }
                 cstore::NativeFramework => {
                     cmd.arg("-framework");
index d8a296bf0410cdde29e5c64362037ecc5b009937..db9966e05487d4466ab2ab5398fa0e0a9a9211a1 100644 (file)
@@ -59,7 +59,7 @@ pub fn run(sess: &session::Session, llmod: ModuleRef,
         };
 
         let archive = ArchiveRO::open(&path).expect("wanted an rlib");
-        let file = path.filename_str().unwrap();
+        let file = path.file_name().unwrap().to_str().unwrap();
         let file = &file[3..file.len() - 5]; // chop off lib/.rlib
         debug!("reading {}", file);
         for i in iter::count(0, 1) {
index cd14fe529b1a7b45453c19a141c7d168116b2b5a..156cfa6c4b23a852ebd6076da31617770f1b55a0 100644 (file)
 use llvm::SMDiagnosticRef;
 use trans::{CrateTranslation, ModuleTranslation};
 use util::common::time;
+use util::common::path2cstr;
 use syntax::codemap;
 use syntax::diagnostic;
 use syntax::diagnostic::{Emitter, Handler, Level, mk_handler};
 
 use std::ffi::{CStr, CString};
-use std::old_io::Command;
-use std::old_io::fs;
+use std::fs;
 use std::iter::Unfold;
+use std::mem;
+use std::path::Path;
+use std::process::{Command, Stdio};
 use std::ptr;
 use std::str;
-use std::mem;
 use std::sync::{Arc, Mutex};
 use std::sync::mpsc::channel;
 use std::thread;
@@ -67,7 +69,7 @@ pub fn write_output_file(
         output: &Path,
         file_type: llvm::FileType) {
     unsafe {
-        let output_c = CString::new(output.as_vec()).unwrap();
+        let output_c = path2cstr(output);
         let result = llvm::LLVMRustWriteOutputFile(
                 target, pm, m, output_c.as_ptr(), file_type);
         if !result {
@@ -424,7 +426,7 @@ unsafe fn optimize_and_codegen(cgcx: &CodegenContext,
     if config.emit_no_opt_bc {
         let ext = format!("{}.no-opt.bc", name_extra);
         let out = output_names.with_extension(&ext);
-        let out = CString::new(out.as_vec()).unwrap();
+        let out = path2cstr(&out);
         llvm::LLVMWriteBitcodeToFile(llmod, out.as_ptr());
     }
 
@@ -477,7 +479,7 @@ unsafe fn optimize_and_codegen(cgcx: &CodegenContext,
                     if config.emit_lto_bc {
                         let name = format!("{}.lto.bc", name_extra);
                         let out = output_names.with_extension(&name);
-                        let out = CString::new(out.as_vec()).unwrap();
+                        let out = path2cstr(&out);
                         llvm::LLVMWriteBitcodeToFile(llmod, out.as_ptr());
                     }
                 },
@@ -511,7 +513,7 @@ unsafe fn with_codegen<F>(tm: TargetMachineRef,
     if config.emit_bc {
         let ext = format!("{}.bc", name_extra);
         let out = output_names.with_extension(&ext);
-        let out = CString::new(out.as_vec()).unwrap();
+        let out = path2cstr(&out);
         llvm::LLVMWriteBitcodeToFile(llmod, out.as_ptr());
     }
 
@@ -519,7 +521,7 @@ unsafe fn with_codegen<F>(tm: TargetMachineRef,
         if config.emit_ir {
             let ext = format!("{}.ll", name_extra);
             let out = output_names.with_extension(&ext);
-            let out = CString::new(out.as_vec()).unwrap();
+            let out = path2cstr(&out);
             with_codegen(tm, llmod, config.no_builtins, |cpm| {
                 llvm::LLVMRustPrintModule(cpm, llmod, out.as_ptr());
             })
@@ -717,12 +719,11 @@ pub fn run_passes(sess: &Session,
         cmd.arg("-nostdlib");
 
         for index in 0..trans.modules.len() {
-            cmd.arg(crate_output.with_extension(&format!("{}.o", index)));
+            cmd.arg(&crate_output.with_extension(&format!("{}.o", index)));
         }
 
-        cmd.arg("-r")
-           .arg("-o")
-           .arg(windows_output_path.as_ref().unwrap_or(output_path));
+        cmd.arg("-r").arg("-o")
+           .arg(windows_output_path.as_ref().map(|s| &**s).unwrap_or(output_path));
 
         cmd.args(&sess.target.target.options.post_link_args);
 
@@ -730,9 +731,7 @@ pub fn run_passes(sess: &Session,
             println!("{:?}", &cmd);
         }
 
-        cmd.stdin(::std::old_io::process::Ignored)
-           .stdout(::std::old_io::process::InheritFd(1))
-           .stderr(::std::old_io::process::InheritFd(2));
+        cmd.stdin(Stdio::null());
         match cmd.status() {
             Ok(status) => {
                 if !status.success() {
@@ -964,9 +963,9 @@ pub fn run_assembler(sess: &Session, outputs: &OutputFilenames) {
     let pname = get_cc_prog(sess);
     let mut cmd = Command::new(&pname[..]);
 
-    cmd.arg("-c").arg("-o").arg(outputs.path(config::OutputTypeObject))
-                           .arg(outputs.temp_path(config::OutputTypeAssembly));
-    debug!("{:?}", &cmd);
+    cmd.arg("-c").arg("-o").arg(&outputs.path(config::OutputTypeObject))
+                           .arg(&outputs.temp_path(config::OutputTypeAssembly));
+    debug!("{:?}", cmd);
 
     match cmd.output() {
         Ok(prog) => {
@@ -975,8 +974,8 @@ pub fn run_assembler(sess: &Session, outputs: &OutputFilenames) {
                                  pname,
                                  prog.status));
                 sess.note(&format!("{:?}", &cmd));
-                let mut note = prog.error.clone();
-                note.push_all(&prog.output);
+                let mut note = prog.stderr.clone();
+                note.push_all(&prog.stdout);
                 sess.note(str::from_utf8(&note[..]).unwrap());
                 sess.abort_if_errors();
             }
index 71317d5875b84fcdb1d3351632dfd0fa0dae1c06..b74f85aa866102d43d6bc1f3f00bf2bfc593d71d 100644 (file)
@@ -14,6 +14,8 @@
 //!
 //! This API is completely unstable and subject to change.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_trans"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
 #![feature(collections)]
 #![feature(core)]
 #![feature(int_uint)]
-#![feature(old_io)]
 #![feature(libc)]
-#![feature(old_path)]
 #![feature(quote)]
 #![feature(rustc_diagnostic_macros)]
 #![feature(rustc_private)]
 #![feature(unsafe_destructor)]
 #![feature(staged_api)]
-#![feature(std_misc)]
 #![feature(unicode)]
+#![feature(io)]
+#![feature(path)]
+#![feature(path_ext)]
+#![feature(fs)]
+#![feature(hash)]
 
 extern crate arena;
 extern crate flate;
index 371b9268fba0de800de32544ce97f95de7f9b707..3c6cb5f9de9892f6f040aaf47be27ce8bb8d3baa 100644 (file)
@@ -33,8 +33,9 @@
 use middle::ty::{self, Ty};
 
 use std::cell::Cell;
-use std::old_io::{self, File, fs};
 use std::env;
+use std::fs::{self, File};
+use std::path::{Path, PathBuf};
 
 use syntax::ast_util::{self, PostExpansionMethod};
 use syntax::ast::{self, NodeId, DefId};
@@ -1537,6 +1538,7 @@ fn visit_local(&mut self, l: &ast::Local) {
     }
 }
 
+#[allow(deprecated)]
 pub fn process_crate(sess: &Session,
                      krate: &ast::Crate,
                      analysis: &ty::CrateAnalysis,
@@ -1557,15 +1559,15 @@ pub fn process_crate(sess: &Session,
     info!("Dumping crate {}", cratename);
 
     // find a path to dump our data to
-    let mut root_path = match env::var("DXR_RUST_TEMP_FOLDER") {
-        Ok(val) => Path::new(val),
-        Err(..) => match odir {
+    let mut root_path = match env::var_os("DXR_RUST_TEMP_FOLDER") {
+        Some(val) => PathBuf::new(&val),
+        None => match odir {
             Some(val) => val.join("dxr"),
-            None => Path::new("dxr-temp"),
+            None => PathBuf::new("dxr-temp"),
         },
     };
 
-    match fs::mkdir_recursive(&root_path, old_io::USER_RWX) {
+    match fs::create_dir_all(&root_path) {
         Err(e) => sess.err(&format!("Could not create directory {}: {}",
                            root_path.display(), e)),
         _ => (),
@@ -1579,7 +1581,7 @@ pub fn process_crate(sess: &Session,
     // Create output file.
     let mut out_name = cratename.clone();
     out_name.push_str(".csv");
-    root_path.push(out_name);
+    root_path.push(&out_name);
     let output_file = match File::create(&root_path) {
         Ok(f) => box f,
         Err(e) => {
@@ -1595,7 +1597,7 @@ pub fn process_crate(sess: &Session,
         collected_paths: vec!(),
         collecting: false,
         fmt: FmtStrs::new(box Recorder {
-                            out: output_file as Box<Writer+'static>,
+                            out: output_file,
                             dump_spans: false,
                         },
                         SpanUtils {
index 937f2d07677aa790141757ee034ee08135735f5f..f7c0d6a983fb77899f9f9aef1e284b02bd13fd28 100644 (file)
@@ -13,7 +13,7 @@
 use super::escape;
 use super::span_utils::SpanUtils;
 
-use std::vec::Vec;
+use std::io::Write;
 
 use syntax::ast;
 use syntax::ast::{NodeId,DefId};
@@ -23,7 +23,7 @@
 
 pub struct Recorder {
     // output file
-    pub out: Box<Writer+'static>,
+    pub out: Box<Write+'static>,
     pub dump_spans: bool,
 }
 
index 3ea14d3c58929dd5967c0a9893bb29a7e1233ca8..61214f65c87ea2d60951f044df44de9944aa97d3 100644 (file)
@@ -169,7 +169,7 @@ fn represent_type_uncached<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
 
             Univariant(mk_struct(cx, &ftys[..], packed, t), dtor)
         }
-        ty::ty_closure(def_id, _, substs) => {
+        ty::ty_closure(def_id, substs) => {
             let typer = NormalizingClosureTyper::new(cx.tcx());
             let upvars = typer.closure_upvars(def_id, substs).unwrap();
             let upvar_types = upvars.iter().map(|u| u.ty).collect::<Vec<_>>();
@@ -487,12 +487,12 @@ fn range_to_inttype(cx: &CrateContext, hint: Hint, bounds: &IntBounds) -> IntTyp
     debug!("range_to_inttype: {:?} {:?}", hint, bounds);
     // Lists of sizes to try.  u64 is always allowed as a fallback.
     #[allow(non_upper_case_globals)]
-    static choose_shortest: &'static[IntType] = &[
+    const choose_shortest: &'static [IntType] = &[
         attr::UnsignedInt(ast::TyU8), attr::SignedInt(ast::TyI8),
         attr::UnsignedInt(ast::TyU16), attr::SignedInt(ast::TyI16),
         attr::UnsignedInt(ast::TyU32), attr::SignedInt(ast::TyI32)];
     #[allow(non_upper_case_globals)]
-    static at_least_32: &'static[IntType] = &[
+    const at_least_32: &'static [IntType] = &[
         attr::UnsignedInt(ast::TyU32), attr::SignedInt(ast::TyI32)];
 
     let attempts;
@@ -778,7 +778,9 @@ fn load_discr(bcx: Block, ity: IntType, ptr: ValueRef, min: Disr, max: Disr)
     assert!(bits <= 64);
     let  bits = bits as uint;
     let mask = (-1u64 >> (64 - bits)) as Disr;
-    if (max + 1) & mask == min & mask {
+    // For a (max) discr of -1, max will be `-1 as usize`, which overflows.
+    // However, that is fine here (it would still represent the full range),
+    if (max.wrapping_add(1)) & mask == min & mask {
         // i.e., if the range is everything.  The lo==hi case would be
         // rejected by the LLVM verifier (it would mean either an
         // empty set, which is impossible, or the entire range of the
@@ -787,7 +789,7 @@ fn load_discr(bcx: Block, ity: IntType, ptr: ValueRef, min: Disr, max: Disr)
     } else {
         // llvm::ConstantRange can deal with ranges that wrap around,
         // so an overflow on (max + 1) is fine.
-        LoadRangeAssert(bcx, ptr, min, (max+1), /* signed: */ True)
+        LoadRangeAssert(bcx, ptr, min, (max.wrapping_add(1)), /* signed: */ True)
     }
 }
 
@@ -1000,7 +1002,7 @@ pub fn trans_drop_flag_ptr<'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>, r: &Repr<'tcx
             let fcx = bcx.fcx;
             let custom_cleanup_scope = fcx.push_custom_cleanup_scope();
             let scratch = unpack_datum!(bcx, datum::lvalue_scratch_datum(
-                bcx, tcx.types.bool, "drop_flag", false,
+                bcx, tcx.types.bool, "drop_flag",
                 cleanup::CustomScope(custom_cleanup_scope), (), |_, bcx, _| bcx
             ));
             bcx = fold_variants(bcx, r, val, |variant_cx, st, value| {
index 1f578ac0bdbab2b8d80d354d73af7934cec02137..f49905613d24cbd2a241880971d395022b2dd4a8 100644 (file)
@@ -291,7 +291,7 @@ pub fn decl_rust_fn<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
         ty::ty_bare_fn(_, ref f) => {
             (&f.sig, f.abi, None)
         }
-        ty::ty_closure(closure_did, _, substs) => {
+        ty::ty_closure(closure_did, substs) => {
             let typer = common::NormalizingClosureTyper::new(ccx.tcx());
             function_type = typer.closure_type(closure_did, substs);
             let self_type = self_type_for_closure(ccx, closure_did, fn_ty);
@@ -685,7 +685,7 @@ fn iter_variant<'blk, 'tcx, F>(cx: Block<'blk, 'tcx>,
               }
           })
       }
-      ty::ty_closure(def_id, _, substs) => {
+      ty::ty_closure(def_id, substs) => {
           let repr = adt::represent_type(cx.ccx(), t);
           let typer = common::NormalizingClosureTyper::new(cx.tcx());
           let upvars = typer.closure_upvars(def_id, substs).unwrap();
@@ -833,11 +833,11 @@ pub fn fail_if_zero_or_overflows<'blk, 'tcx>(
 
     let (is_zero, is_signed) = match rhs_t.sty {
         ty::ty_int(t) => {
-            let zero = C_integral(Type::int_from_ty(cx.ccx(), t), 0u64, false);
+            let zero = C_integral(Type::int_from_ty(cx.ccx(), t), 0, false);
             (ICmp(cx, llvm::IntEQ, rhs, zero, debug_loc), true)
         }
         ty::ty_uint(t) => {
-            let zero = C_integral(Type::uint_from_ty(cx.ccx(), t), 0u64, false);
+            let zero = C_integral(Type::uint_from_ty(cx.ccx(), t), 0, false);
             (ICmp(cx, llvm::IntEQ, rhs, zero, debug_loc), false)
         }
         _ => {
@@ -1203,21 +1203,6 @@ pub fn alloca_no_lifetime(cx: Block, ty: Type, name: &str) -> ValueRef {
     Alloca(cx, ty, name)
 }
 
-pub fn alloca_zeroed<'blk, 'tcx>(cx: Block<'blk, 'tcx>, ty: Ty<'tcx>,
-                                 name: &str) -> ValueRef {
-    let llty = type_of::type_of(cx.ccx(), ty);
-    if cx.unreachable.get() {
-        unsafe {
-            return llvm::LLVMGetUndef(llty.ptr_to().to_ref());
-        }
-    }
-    let p = alloca_no_lifetime(cx, llty, name);
-    let b = cx.fcx.ccx.builder();
-    b.position_before(cx.fcx.alloca_insert_pt.get().unwrap());
-    memzero(&b, p, ty);
-    p
-}
-
 // Creates the alloca slot which holds the pointer to the slot for the final return value
 pub fn make_return_slot_pointer<'a, 'tcx>(fcx: &FunctionContext<'a, 'tcx>,
                                           output_type: Ty<'tcx>) -> ValueRef {
@@ -1547,7 +1532,6 @@ fn create_datums_for_fn_args_under_call_abi<'blk, 'tcx>(
                                   datum::lvalue_scratch_datum(bcx,
                                                               arg_ty,
                                                               "tupled_args",
-                                                              false,
                                                               tuple_args_scope_id,
                                                               (),
                                                               |(),
@@ -2437,7 +2421,7 @@ pub fn get_fn_llvm_attributes<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>, fn_ty: Ty<
     let function_type;
     let (fn_sig, abi, env_ty) = match fn_ty.sty {
         ty::ty_bare_fn(_, ref f) => (&f.sig, f.abi, None),
-        ty::ty_closure(closure_did, _, substs) => {
+        ty::ty_closure(closure_did, substs) => {
             let typer = common::NormalizingClosureTyper::new(ccx.tcx());
             function_type = typer.closure_type(closure_did, substs);
             let self_type = self_type_for_closure(ccx, closure_did, fn_ty);
@@ -2454,7 +2438,7 @@ pub fn get_fn_llvm_attributes<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>, fn_ty: Ty<
     // These have an odd calling convention, so we need to manually
     // unpack the input ty's
     let input_tys = match fn_ty.sty {
-        ty::ty_closure(_, _, _) => {
+        ty::ty_closure(..) => {
             assert!(abi == RustCall);
 
             match fn_sig.inputs[0].sty {
@@ -2985,7 +2969,7 @@ pub fn write_metadata(cx: &SharedCrateContext, krate: &ast::Crate) -> Vec<u8> {
     }
 
     let encode_inlined_item: encoder::EncodeInlinedItem =
-        box |ecx, rbml_w, ii| astencode::encode_inlined_item(ecx, rbml_w, ii);
+        Box::new(|ecx, rbml_w, ii| astencode::encode_inlined_item(ecx, rbml_w, ii));
 
     let encode_parms = crate_ctxt_to_encode_parms(cx, encode_inlined_item);
     let metadata = encoder::encode_metadata(encode_parms, krate);
@@ -3102,6 +3086,12 @@ pub fn trans_crate<'tcx>(analysis: ty::CrateAnalysis<'tcx>)
     let ty::CrateAnalysis { ty_cx: tcx, export_map, reachable, name, .. } = analysis;
     let krate = tcx.map.krate();
 
+    let check_overflow = if let Some(v) = tcx.sess.opts.debugging_opts.force_overflow_checks {
+        v
+    } else {
+        tcx.sess.opts.debug_assertions
+    };
+
     // Before we touch LLVM, make sure that multithreading is enabled.
     unsafe {
         use std::sync::{Once, ONCE_INIT};
@@ -3129,7 +3119,8 @@ pub fn trans_crate<'tcx>(analysis: ty::CrateAnalysis<'tcx>)
                                              export_map,
                                              Sha256::new(),
                                              link_meta.clone(),
-                                             reachable);
+                                             reachable,
+                                             check_overflow);
 
     {
         let ccx = shared_ccx.get_ccx(0);
index 5d1e6d2c9e84400a54e52c8ae6ac96351ce0acde..03496a966bf30e8d617652b6746b176a186f5162 100644 (file)
@@ -117,7 +117,7 @@ fn classify_arg_ty(ccx: &CrateContext, ty: Type) -> ArgType {
     let size = ty_size(ty);
     if size <= 16 {
         let llty = if size == 0 {
-            Type::array(&Type::i64(ccx), 0u64)
+            Type::array(&Type::i64(ccx), 0)
         } else if size == 1 {
             Type::i8(ccx)
         } else if size == 2 {
index 1d4bbd79d71057baecdc624201e5d7a367355068..7fa26a7c1284196292c92c22ffe6bf4d5f30c3c3 100644 (file)
@@ -138,7 +138,7 @@ pub fn get_or_create_declaration_if_closure<'a, 'tcx>(ccx: &CrateContext<'a, 'tc
     // duplicate declarations
     let function_type = erase_regions(ccx.tcx(), &function_type);
     let params = match function_type.sty {
-        ty::ty_closure(_, _, substs) => &substs.types,
+        ty::ty_closure(_, substs) => &substs.types,
         _ => unreachable!()
     };
     let mono_id = MonoId {
index c1d22cc973c240c209b88dce5d1d5c8728c2eb70..39b430b7ad51ed1a6ddcb5eaeaa9baea1311e89e 100644 (file)
@@ -173,7 +173,7 @@ pub fn get_const_expr<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
         &**expr
     } else {
         ccx.sess().span_bug(ref_expr.span,
-                            &format!("get_const_val given non-constant item {}",
+                            &format!("get_const_expr given non-constant item {}",
                                      item.repr(ccx.tcx())));
     }
 }
@@ -462,9 +462,9 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
 
           ast::ExprIndex(ref base, ref index) => {
               let (bv, bt) = const_expr(cx, &**base, param_substs);
-              let iv = match const_eval::eval_const_expr(cx.tcx(), &**index) {
-                  const_eval::const_int(i) => i as u64,
-                  const_eval::const_uint(u) => u,
+              let iv = match const_eval::eval_const_expr_partial(cx.tcx(), &**index, None) {
+                  Ok(const_eval::const_int(i)) => i as u64,
+                  Ok(const_eval::const_uint(u)) => u,
                   _ => cx.sess().span_bug(index.span,
                                           "index is not an integer-constant expression")
               };
@@ -650,9 +650,9 @@ fn const_expr_unadjusted<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
           ast::ExprRepeat(ref elem, ref count) => {
             let unit_ty = ty::sequence_element_type(cx.tcx(), ety);
             let llunitty = type_of::type_of(cx, unit_ty);
-            let n = match const_eval::eval_const_expr(cx.tcx(), &**count) {
-                const_eval::const_int(i)  => i as uint,
-                const_eval::const_uint(i) => i as uint,
+            let n = match const_eval::eval_const_expr_partial(cx.tcx(), &**count, None) {
+                Ok(const_eval::const_int(i))  => i as uint,
+                Ok(const_eval::const_uint(i)) => i as uint,
                 _ => cx.sess().span_bug(count.span, "count must be integral const expression.")
             };
             let unit_val = const_expr(cx, &**elem, param_substs).0;
index 3586a9dda20675bbc89752d0a45f6cd9d6d24750..9777398bddcc324fad4b0a840afe6970cb0e0278 100644 (file)
@@ -69,6 +69,7 @@ pub struct SharedCrateContext<'tcx> {
     symbol_hasher: RefCell<Sha256>,
     tcx: ty::ctxt<'tcx>,
     stats: Stats,
+    check_overflow: bool,
 
     available_monomorphizations: RefCell<FnvHashSet<String>>,
     available_drop_glues: RefCell<FnvHashMap<Ty<'tcx>, String>>,
@@ -245,7 +246,8 @@ pub fn new(crate_name: &str,
                export_map: ExportMap,
                symbol_hasher: Sha256,
                link_meta: LinkMeta,
-               reachable: NodeSet)
+               reachable: NodeSet,
+               check_overflow: bool)
                -> SharedCrateContext<'tcx> {
         let (metadata_llcx, metadata_llmod) = unsafe {
             create_context_and_module(&tcx.sess, "metadata")
@@ -274,6 +276,7 @@ pub fn new(crate_name: &str,
                 llvm_insns: RefCell::new(FnvHashMap()),
                 fn_stats: RefCell::new(Vec::new()),
             },
+            check_overflow: check_overflow,
             available_monomorphizations: RefCell::new(FnvHashSet()),
             available_drop_glues: RefCell::new(FnvHashMap()),
         };
@@ -743,6 +746,10 @@ pub fn report_overbig_object(&self, obj: Ty<'tcx>) -> ! {
             &format!("the type `{}` is too big for the current architecture",
                     obj.repr(self.tcx())))
     }
+
+    pub fn check_overflow(&self) -> bool {
+        self.shared.check_overflow
+    }
 }
 
 fn declare_intrinsic(ccx: &CrateContext, key: & &'static str) -> Option<ValueRef> {
index 6ca71254868f3f62d339852a4276319acf9d7f45..e181df545e6fc06aa63f4b0e2a39f2ea835d9dea 100644 (file)
@@ -195,24 +195,18 @@ pub fn immediate_rvalue_bcx<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
 
 /// Allocates temporary space on the stack using alloca() and returns a by-ref Datum pointing to
 /// it. The memory will be dropped upon exit from `scope`. The callback `populate` should
-/// initialize the memory. If `zero` is true, the space will be zeroed when it is allocated; this
-/// is not necessary unless `bcx` does not dominate the end of `scope`.
+/// initialize the memory.
 pub fn lvalue_scratch_datum<'blk, 'tcx, A, F>(bcx: Block<'blk, 'tcx>,
                                               ty: Ty<'tcx>,
                                               name: &str,
-                                              zero: bool,
                                               scope: cleanup::ScopeId,
                                               arg: A,
                                               populate: F)
                                               -> DatumBlock<'blk, 'tcx, Lvalue> where
     F: FnOnce(A, Block<'blk, 'tcx>, ValueRef) -> Block<'blk, 'tcx>,
 {
-    let scratch = if zero {
-        alloca_zeroed(bcx, ty, name)
-    } else {
-        let llty = type_of::type_of(bcx.ccx(), ty);
-        alloca(bcx, llty, name)
-    };
+    let llty = type_of::type_of(bcx.ccx(), ty);
+    let scratch = alloca(bcx, llty, name);
 
     // Subtle. Populate the scratch memory *before* scheduling cleanup.
     let bcx = populate(arg, bcx, scratch);
@@ -383,7 +377,7 @@ pub fn to_lvalue_datum_in_scope<'blk>(self,
 
             ByValue => {
                 lvalue_scratch_datum(
-                    bcx, self.ty, name, false, scope, self,
+                    bcx, self.ty, name, scope, self,
                     |this, bcx, llval| this.store_to(bcx, llval))
             }
         }
index d70a904b81189fde012837d6b320799e493eabe5..95c39270cc6d9f18c56dd2e98145009c39f74ae3 100644 (file)
 use session::config::{self, FullDebugInfo, LimitedDebugInfo, NoDebugInfo};
 use util::nodemap::{DefIdMap, NodeMap, FnvHashMap, FnvHashSet};
 use util::ppaux;
+use util::common::path2cstr;
 
 use libc::{c_uint, c_longlong};
-use std::ffi::CString;
 use std::cell::{Cell, RefCell};
+use std::ffi::CString;
+use std::path::Path;
 use std::ptr;
 use std::rc::{Rc, Weak};
 use syntax::util::interner::Interner;
@@ -472,7 +474,7 @@ fn get_unique_type_id_of_type<'a>(&mut self, cx: &CrateContext<'a, 'tcx>,
                     }
                 }
             },
-            ty::ty_closure(def_id, _, substs) => {
+            ty::ty_closure(def_id, substs) => {
                 let typer = NormalizingClosureTyper::new(cx.tcx());
                 let closure_ty = typer.closure_type(def_id, substs);
                 self.get_unique_type_id_of_closure_type(cx,
@@ -695,6 +697,7 @@ struct FunctionDebugContextData {
     fn_metadata: DISubprogram,
     argument_counter: Cell<uint>,
     source_locations_enabled: Cell<bool>,
+    source_location_override: Cell<bool>,
 }
 
 enum VariableAccess<'a> {
@@ -1174,6 +1177,12 @@ pub fn set_source_location(fcx: &FunctionContext,
             return;
         }
         FunctionDebugContext::RegularContext(box ref function_debug_context) => {
+            if function_debug_context.source_location_override.get() {
+                // Just ignore any attempts to set a new debug location while
+                // the override is active.
+                return;
+            }
+
             let cx = fcx.ccx;
 
             debug!("set_source_location: {}", cx.sess().codemap().span_to_string(span));
@@ -1192,6 +1201,35 @@ pub fn set_source_location(fcx: &FunctionContext,
     }
 }
 
+/// This function makes sure that all debug locations emitted while executing
+/// `wrapped_function` are set to the given `debug_loc`.
+pub fn with_source_location_override<F, R>(fcx: &FunctionContext,
+                                           debug_loc: DebugLoc,
+                                           wrapped_function: F) -> R
+    where F: FnOnce() -> R
+{
+    match fcx.debug_context {
+        FunctionDebugContext::DebugInfoDisabled => {
+            wrapped_function()
+        }
+        FunctionDebugContext::FunctionWithoutDebugInfo => {
+            set_debug_location(fcx.ccx, UnknownLocation);
+            wrapped_function()
+        }
+        FunctionDebugContext::RegularContext(box ref function_debug_context) => {
+            if function_debug_context.source_location_override.get() {
+                wrapped_function()
+            } else {
+                debug_loc.apply(fcx);
+                function_debug_context.source_location_override.set(true);
+                let result = wrapped_function();
+                function_debug_context.source_location_override.set(false);
+                result
+            }
+        }
+    }
+}
+
 /// Clears the current debug location.
 ///
 /// Instructions generated hereafter won't be assigned a source location.
@@ -1412,6 +1450,7 @@ pub fn create_function_debug_context<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
         fn_metadata: fn_metadata,
         argument_counter: Cell::new(1),
         source_locations_enabled: Cell::new(false),
+        source_location_override: Cell::new(false),
     };
 
 
@@ -1588,20 +1627,13 @@ fn compile_unit_metadata(cx: &CrateContext) -> DIDescriptor {
                 cx.sess().warn("debuginfo: Invalid path to crate's local root source file!");
                 fallback_path(cx)
             } else {
-                match abs_path.path_relative_from(work_dir) {
+                match abs_path.relative_from(work_dir) {
                     Some(ref p) if p.is_relative() => {
-                        // prepend "./" if necessary
-                        let dotdot = b"..";
-                        let prefix: &[u8] = &[dotdot[0], ::std::old_path::SEP_BYTE];
-                        let mut path_bytes = p.as_vec().to_vec();
-
-                        if &path_bytes[..2] != prefix &&
-                           &path_bytes[..2] != dotdot {
-                            path_bytes.insert(0, prefix[0]);
-                            path_bytes.insert(1, prefix[1]);
+                        if p.starts_with(Path::new("./")) {
+                            path2cstr(p)
+                        } else {
+                            path2cstr(&Path::new(".").join(p))
                         }
-
-                        CString::new(path_bytes).unwrap()
                     }
                     _ => fallback_path(cx)
                 }
@@ -1614,7 +1646,7 @@ fn compile_unit_metadata(cx: &CrateContext) -> DIDescriptor {
                            (option_env!("CFG_VERSION")).expect("CFG_VERSION"));
 
     let compile_unit_name = compile_unit_name.as_ptr();
-    let work_dir = CString::new(work_dir.as_vec()).unwrap();
+    let work_dir = path2cstr(&work_dir);
     let producer = CString::new(producer).unwrap();
     let flags = "\0";
     let split_name = "\0";
@@ -1716,7 +1748,7 @@ fn file_metadata(cx: &CrateContext, full_path: &str) -> DIFile {
     debug!("file_metadata: {}", full_path);
 
     // FIXME (#9639): This needs to handle non-utf8 paths
-    let work_dir = cx.sess().working_dir.as_str().unwrap();
+    let work_dir = cx.sess().working_dir.to_str().unwrap();
     let file_name =
         if full_path.starts_with(work_dir) {
             &full_path[work_dir.len() + 1..full_path.len()]
@@ -2983,7 +3015,7 @@ fn type_metadata<'a, 'tcx>(cx: &CrateContext<'a, 'tcx>,
         ty::ty_bare_fn(_, ref barefnty) => {
             subroutine_type_metadata(cx, unique_type_id, &barefnty.sig, usage_site_span)
         }
-        ty::ty_closure(def_id, _, substs) => {
+        ty::ty_closure(def_id, substs) => {
             let typer = NormalizingClosureTyper::new(cx.tcx());
             let sig = typer.closure_type(def_id, substs).sig;
             subroutine_type_metadata(cx, unique_type_id, &sig, usage_site_span)
index 27f9b9506a58a12e7848f441b98fbda733f22877..ecdc7c06bb19dfa8eb629b1a16f17b0d8e763bc8 100644 (file)
@@ -82,6 +82,7 @@
 use trans::type_::Type;
 
 use syntax::{ast, ast_util, codemap};
+use syntax::parse::token::InternedString;
 use syntax::ptr::P;
 use syntax::parse::token;
 use std::iter::repeat;
@@ -146,7 +147,7 @@ pub fn trans_into<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
                 ast::ExprPath(..) => {
                     match bcx.def(expr.id) {
                         def::DefConst(did) => {
-                            let expr = consts::get_const_expr(bcx.ccx(), did, expr);
+                            let const_expr = consts::get_const_expr(bcx.ccx(), did, expr);
                             // Temporarily get cleanup scopes out of the way,
                             // as they require sub-expressions to be contained
                             // inside the current AST scope.
@@ -154,7 +155,13 @@ pub fn trans_into<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
                             // can't have destructors.
                             let scopes = mem::replace(&mut *bcx.fcx.scopes.borrow_mut(),
                                                       vec![]);
-                            bcx = trans_into(bcx, expr, dest);
+                            // Lock emitted debug locations to the location of
+                            // the constant reference expression.
+                            debuginfo::with_source_location_override(bcx.fcx,
+                                                                     expr.debug_loc(),
+                                                                     || {
+                                bcx = trans_into(bcx, const_expr, dest)
+                            });
                             let scopes = mem::replace(&mut *bcx.fcx.scopes.borrow_mut(),
                                                       scopes);
                             assert!(scopes.is_empty());
@@ -1493,8 +1500,45 @@ pub fn trans_adt<'a, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>,
     // panic occur before the ADT as a whole is ready.
     let custom_cleanup_scope = fcx.push_custom_cleanup_scope();
 
-    // First we trans the base, if we have one, to the dest
-    if let Some(base) = optbase {
+    if ty::type_is_simd(bcx.tcx(), ty) {
+        // Issue 23112: The original logic appeared vulnerable to same
+        // order-of-eval bug. But, SIMD values are tuple-structs;
+        // i.e. functional record update (FRU) syntax is unavailable.
+        //
+        // To be safe, double-check that we did not get here via FRU.
+        assert!(optbase.is_none());
+
+        // This is the constructor of a SIMD type, such types are
+        // always primitive machine types and so do not have a
+        // destructor or require any clean-up.
+        let llty = type_of::type_of(bcx.ccx(), ty);
+
+        // keep a vector as a register, and running through the field
+        // `insertelement`ing them directly into that register
+        // (i.e. avoid GEPi and `store`s to an alloca) .
+        let mut vec_val = C_undef(llty);
+
+        for &(i, ref e) in fields {
+            let block_datum = trans(bcx, &**e);
+            bcx = block_datum.bcx;
+            let position = C_uint(bcx.ccx(), i);
+            let value = block_datum.datum.to_llscalarish(bcx);
+            vec_val = InsertElement(bcx, vec_val, value, position);
+        }
+        Store(bcx, vec_val, addr);
+    } else if let Some(base) = optbase {
+        // Issue 23112: If there is a base, then order-of-eval
+        // requires field expressions eval'ed before base expression.
+
+        // First, trans field expressions to temporary scratch values.
+        let scratch_vals: Vec<_> = fields.iter().map(|&(i, ref e)| {
+            let datum = unpack_datum!(bcx, trans(bcx, &**e));
+            (i, datum)
+        }).collect();
+
+        debug_location.apply(bcx.fcx);
+
+        // Second, trans the base to the dest.
         assert_eq!(discr, 0);
 
         match ty::expr_kind(bcx.tcx(), &*base.expr) {
@@ -1513,31 +1557,14 @@ pub fn trans_adt<'a, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>,
                 }
             }
         }
-    }
-
-    debug_location.apply(bcx.fcx);
-
-    if ty::type_is_simd(bcx.tcx(), ty) {
-        // This is the constructor of a SIMD type, such types are
-        // always primitive machine types and so do not have a
-        // destructor or require any clean-up.
-        let llty = type_of::type_of(bcx.ccx(), ty);
 
-        // keep a vector as a register, and running through the field
-        // `insertelement`ing them directly into that register
-        // (i.e. avoid GEPi and `store`s to an alloca) .
-        let mut vec_val = C_undef(llty);
-
-        for &(i, ref e) in fields {
-            let block_datum = trans(bcx, &**e);
-            bcx = block_datum.bcx;
-            let position = C_uint(bcx.ccx(), i);
-            let value = block_datum.datum.to_llscalarish(bcx);
-            vec_val = InsertElement(bcx, vec_val, value, position);
+        // Finally, move scratch field values into actual field locations
+        for (i, datum) in scratch_vals.into_iter() {
+            let dest = adt::trans_field_ptr(bcx, &*repr, addr, discr, i);
+            bcx = datum.store_to(bcx, dest);
         }
-        Store(bcx, vec_val, addr);
     } else {
-        // Now, we just overwrite the fields we've explicitly specified
+        // No base means we can write all fields directly in place.
         for &(i, ref e) in fields {
             let dest = adt::trans_field_ptr(bcx, &*repr, addr, discr, i);
             let e_ty = expr_ty_adjusted(bcx, &**e);
@@ -1709,8 +1736,8 @@ fn trans_eager_binop<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
     };
     let is_float = ty::type_is_fp(intype);
     let is_signed = ty::type_is_signed(intype);
-
     let rhs = base::cast_shift_expr_rhs(bcx, op, lhs, rhs);
+    let info = expr_info(binop_expr);
 
     let binop_debug_loc = binop_expr.debug_loc();
 
@@ -1720,21 +1747,30 @@ fn trans_eager_binop<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
         if is_float {
             FAdd(bcx, lhs, rhs, binop_debug_loc)
         } else {
-            Add(bcx, lhs, rhs, binop_debug_loc)
+            let (newbcx, res) = with_overflow_check(
+                bcx, OverflowOp::Add, info, lhs_t, lhs, rhs, binop_debug_loc);
+            bcx = newbcx;
+            res
         }
       }
       ast::BiSub => {
         if is_float {
             FSub(bcx, lhs, rhs, binop_debug_loc)
         } else {
-            Sub(bcx, lhs, rhs, binop_debug_loc)
+            let (newbcx, res) = with_overflow_check(
+                bcx, OverflowOp::Sub, info, lhs_t, lhs, rhs, binop_debug_loc);
+            bcx = newbcx;
+            res
         }
       }
       ast::BiMul => {
         if is_float {
             FMul(bcx, lhs, rhs, binop_debug_loc)
         } else {
-            Mul(bcx, lhs, rhs, binop_debug_loc)
+            let (newbcx, res) = with_overflow_check(
+                bcx, OverflowOp::Mul, info, lhs_t, lhs, rhs, binop_debug_loc);
+            bcx = newbcx;
+            res
         }
       }
       ast::BiDiv => {
@@ -2314,3 +2350,110 @@ fn deref_owned_pointer<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
         DatumBlock { bcx: bcx, datum: datum }
     }
 }
+
+enum OverflowOp {
+    Add,
+    Sub,
+    Mul,
+}
+
+impl OverflowOp {
+    fn to_intrinsic_name(&self, tcx: &ty::ctxt, ty: Ty) -> &'static str {
+        use syntax::ast::IntTy::*;
+        use syntax::ast::UintTy::*;
+        use middle::ty::{ty_int, ty_uint};
+
+        let new_sty = match ty.sty {
+            ty_int(TyIs(_)) => match &tcx.sess.target.target.target_pointer_width[..] {
+                "32" => ty_int(TyI32),
+                "64" => ty_int(TyI64),
+                _ => panic!("unsupported target word size")
+            },
+            ty_uint(TyUs(_)) => match &tcx.sess.target.target.target_pointer_width[..] {
+                "32" => ty_uint(TyU32),
+                "64" => ty_uint(TyU64),
+                _ => panic!("unsupported target word size")
+            },
+            ref t @ ty_uint(_) | ref t @ ty_int(_) => t.clone(),
+            _ => panic!("tried to get overflow intrinsic for non-int type")
+        };
+
+        match *self {
+            OverflowOp::Add => match new_sty {
+                ty_int(TyI8) => "llvm.sadd.with.overflow.i8",
+                ty_int(TyI16) => "llvm.sadd.with.overflow.i16",
+                ty_int(TyI32) => "llvm.sadd.with.overflow.i32",
+                ty_int(TyI64) => "llvm.sadd.with.overflow.i64",
+
+                ty_uint(TyU8) => "llvm.uadd.with.overflow.i8",
+                ty_uint(TyU16) => "llvm.uadd.with.overflow.i16",
+                ty_uint(TyU32) => "llvm.uadd.with.overflow.i32",
+                ty_uint(TyU64) => "llvm.uadd.with.overflow.i64",
+
+                _ => unreachable!(),
+            },
+            OverflowOp::Sub => match new_sty {
+                ty_int(TyI8) => "llvm.ssub.with.overflow.i8",
+                ty_int(TyI16) => "llvm.ssub.with.overflow.i16",
+                ty_int(TyI32) => "llvm.ssub.with.overflow.i32",
+                ty_int(TyI64) => "llvm.ssub.with.overflow.i64",
+
+                ty_uint(TyU8) => "llvm.usub.with.overflow.i8",
+                ty_uint(TyU16) => "llvm.usub.with.overflow.i16",
+                ty_uint(TyU32) => "llvm.usub.with.overflow.i32",
+                ty_uint(TyU64) => "llvm.usub.with.overflow.i64",
+
+                _ => unreachable!(),
+            },
+            OverflowOp::Mul => match new_sty {
+                ty_int(TyI8) => "llvm.smul.with.overflow.i8",
+                ty_int(TyI16) => "llvm.smul.with.overflow.i16",
+                ty_int(TyI32) => "llvm.smul.with.overflow.i32",
+                ty_int(TyI64) => "llvm.smul.with.overflow.i64",
+
+                ty_uint(TyU8) => "llvm.umul.with.overflow.i8",
+                ty_uint(TyU16) => "llvm.umul.with.overflow.i16",
+                ty_uint(TyU32) => "llvm.umul.with.overflow.i32",
+                ty_uint(TyU64) => "llvm.umul.with.overflow.i64",
+
+                _ => unreachable!(),
+            },
+        }
+    }
+}
+
+
+fn with_overflow_check<'a, 'b>(bcx: Block<'a, 'b>, oop: OverflowOp, info: NodeIdAndSpan,
+                               lhs_t: Ty, lhs: ValueRef, rhs: ValueRef, binop_debug_loc: DebugLoc)
+                               -> (Block<'a, 'b>, ValueRef) {
+    if bcx.unreachable.get() { return (bcx, _Undef(lhs)); }
+    if bcx.ccx().check_overflow() {
+        let name = oop.to_intrinsic_name(bcx.tcx(), lhs_t);
+        let llfn = bcx.ccx().get_intrinsic(&name);
+
+        let val = Call(bcx, llfn, &[lhs, rhs], None, binop_debug_loc);
+        let result = ExtractValue(bcx, val, 0); // iN operation result
+        let overflow = ExtractValue(bcx, val, 1); // i1 "did it overflow?"
+
+        let cond = ICmp(bcx, llvm::IntEQ, overflow, C_integral(Type::i1(bcx.ccx()), 1, false),
+                        binop_debug_loc);
+
+        let expect = bcx.ccx().get_intrinsic(&"llvm.expect.i1");
+        Call(bcx, expect, &[cond, C_integral(Type::i1(bcx.ccx()), 0, false)],
+             None, binop_debug_loc);
+
+        let bcx =
+            base::with_cond(bcx, cond, |bcx|
+                controlflow::trans_fail(bcx, info,
+                    InternedString::new("arithmetic operation overflowed")));
+
+        (bcx, result)
+    } else {
+        let res = match oop {
+            OverflowOp::Add => Add(bcx, lhs, rhs, binop_debug_loc),
+            OverflowOp::Sub => Sub(bcx, lhs, rhs, binop_debug_loc),
+            OverflowOp::Mul => Mul(bcx, lhs, rhs, binop_debug_loc),
+        };
+        (bcx, res)
+    }
+}
index efae76c5ef41c76027b149666d001858e9f058ae..b0383e355e489477f2ac37c2612f0d35b1cf701c 100644 (file)
@@ -440,7 +440,7 @@ fn gate_simd_ffi(tcx: &ty::ctxt, decl: &ast::FnDecl, ty: &ty::BareFnTy) {
                               &format!("use of SIMD type `{}` in FFI is highly experimental and \
                                         may result in invalid code",
                                        pprust::ty_to_string(ast_ty)));
-                tcx.sess.span_help(ast_ty.span,
+                tcx.sess.fileline_help(ast_ty.span,
                                    "add #![feature(simd_ffi)] to the crate attributes to enable");
             }
         };
index 9491c8377a655fdbe10eee9e63cc2200f29092f2..1151b11d21f35ce4faebacb7c8b606b7c0062c25 100644 (file)
@@ -313,8 +313,7 @@ fn trans_struct_drop<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
                                      ty::mk_nil(bcx.tcx()));
         let (_, variant_cx) = invoke(variant_cx, dtor_addr, &args[..], dtor_ty, DebugLoc::None);
 
-        variant_cx.fcx.pop_and_trans_custom_cleanup_scope(variant_cx, field_scope);
-        variant_cx
+        variant_cx.fcx.pop_and_trans_custom_cleanup_scope(variant_cx, field_scope)
     })
 }
 
index 56fda20e0e8dcdc79d666da21b94e4f10247fc32..14f92334073720d38d212e1d787cf1641408b517 100644 (file)
@@ -40,7 +40,7 @@ fn instantiate_inline(ccx: &CrateContext, fn_id: ast::DefId)
     let csearch_result =
         csearch::maybe_get_item_ast(
             ccx.tcx(), fn_id,
-            box |a,b,c,d| astencode::decode_inlined_item(a, b, c, d));
+            Box::new(|a,b,c,d| astencode::decode_inlined_item(a, b, c, d)));
 
     let inline_def = match csearch_result {
         csearch::FoundAst::NotFound => {
index 54644c92869cfe0ea83c7c6d780545e1a2dd32d1..916492195c2583fdc6105f15167f90be33a8ac10 100644 (file)
@@ -660,6 +660,11 @@ pub fn trans_intrinsic_call<'a, 'blk, 'tcx>(mut bcx: Block<'blk, 'tcx>,
                                     llargs[0],
                                     llargs[1],
                                     call_debug_location),
+
+        (_, "overflowing_add") => Add(bcx, llargs[0], llargs[1], call_debug_location),
+        (_, "overflowing_sub") => Sub(bcx, llargs[0], llargs[1], call_debug_location),
+        (_, "overflowing_mul") => Mul(bcx, llargs[0], llargs[1], call_debug_location),
+
         (_, "return_address") => {
             if !fcx.caller_expects_out_pointer {
                 tcx.sess.span_err(call_info.span,
index 67f1c39c6e094f114d4f2b7a423bc1e6557442cb..0c82d681eed15ece14aafa2f71b9022cc224e0d4 100644 (file)
@@ -45,7 +45,7 @@
 use syntax::codemap::DUMMY_SP;
 
 // drop_glue pointer, size, align.
-static VTABLE_OFFSET: uint = 3;
+const VTABLE_OFFSET: uint = 3;
 
 /// The main "translation" pass for methods.  Generates code
 /// for non-monomorphized methods only.  Other methods will
@@ -300,7 +300,10 @@ pub fn trans_static_method_callee<'a, 'tcx>(ccx: &CrateContext<'a, 'tcx>,
                                   .position(|item| item.def_id() == method_id)
                                   .unwrap();
             let (llfn, ty) =
-                trans_object_shim(ccx, data.object_ty, trait_id, method_offset_in_trait);
+                trans_object_shim(ccx,
+                                  data.object_ty,
+                                  data.upcast_trait_ref.clone(),
+                                  method_offset_in_trait);
             immediate_rvalue(llfn, ty)
         }
         _ => {
@@ -386,7 +389,10 @@ fn trans_monomorphized_callee<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
             Callee { bcx: bcx, data: Fn(llfn) }
         }
         traits::VtableObject(ref data) => {
-            let (llfn, _) = trans_object_shim(bcx.ccx(), data.object_ty, trait_id, n_method);
+            let (llfn, _) = trans_object_shim(bcx.ccx(),
+                                              data.object_ty,
+                                              data.upcast_trait_ref.clone(),
+                                              n_method);
             Callee { bcx: bcx, data: Fn(llfn) }
         }
         traits::VtableBuiltin(..) |
@@ -551,16 +557,17 @@ pub fn trans_trait_callee_from_llval<'blk, 'tcx>(bcx: Block<'blk, 'tcx>,
 pub fn trans_object_shim<'a, 'tcx>(
     ccx: &'a CrateContext<'a, 'tcx>,
     object_ty: Ty<'tcx>,
-    trait_id: ast::DefId,
+    upcast_trait_ref: ty::PolyTraitRef<'tcx>,
     method_offset_in_trait: uint)
     -> (ValueRef, Ty<'tcx>)
 {
     let _icx = push_ctxt("trans_object_shim");
     let tcx = ccx.tcx();
+    let trait_id = upcast_trait_ref.def_id();
 
-    debug!("trans_object_shim(object_ty={}, trait_id={}, method_offset_in_trait={})",
+    debug!("trans_object_shim(object_ty={}, upcast_trait_ref={}, method_offset_in_trait={})",
            object_ty.repr(tcx),
-           trait_id.repr(tcx),
+           upcast_trait_ref.repr(tcx),
            method_offset_in_trait);
 
     let object_trait_ref =
@@ -575,7 +582,6 @@ pub fn trans_object_shim<'a, 'tcx>(
         };
 
     // Upcast to the trait in question and extract out the substitutions.
-    let upcast_trait_ref = traits::upcast(ccx.tcx(), object_trait_ref.clone(), trait_id).unwrap();
     let upcast_trait_ref = ty::erase_late_bound_regions(tcx, &upcast_trait_ref);
     let object_substs = upcast_trait_ref.substs.clone().erase_regions();
     debug!("trans_object_shim: object_substs={}", object_substs.repr(tcx));
index d9dc050aebf10d13e251f192e9f9113187b9af79..2c7a9bf8020c3f324602f7d7089511979b6f1c7a 100644 (file)
@@ -59,7 +59,6 @@
 use rscope::{self, UnelidableRscope, RegionScope, ElidableRscope,
              ObjectLifetimeDefaultRscope, ShiftedRscope, BindingRscope};
 use util::common::{ErrorReported, FN_OUTPUT_NAME};
-use util::nodemap::DefIdMap;
 use util::ppaux::{self, Repr, UserString};
 
 use std::iter::{repeat, AdditiveIterator};
 pub trait AstConv<'tcx> {
     fn tcx<'a>(&'a self) -> &'a ty::ctxt<'tcx>;
 
+    /// Identify the type scheme for an item with a type, like a type
+    /// alias, fn, or struct. This allows you to figure out the set of
+    /// type parameters defined on the item.
     fn get_item_type_scheme(&self, span: Span, id: ast::DefId)
                             -> Result<ty::TypeScheme<'tcx>, ErrorReported>;
 
+    /// Returns the `TraitDef` for a given trait. This allows you to
+    /// figure out the set of type parameters defined on the trait.
     fn get_trait_def(&self, span: Span, id: ast::DefId)
                      -> Result<Rc<ty::TraitDef<'tcx>>, ErrorReported>;
 
+    /// Ensure that the super-predicates for the trait with the given
+    /// id are available and also for the transitive set of
+    /// super-predicates.
+    fn ensure_super_predicates(&self, span: Span, id: ast::DefId)
+                               -> Result<(), ErrorReported>;
+
+    /// Returns the set of bounds in scope for the type parameter with
+    /// the given id.
     fn get_type_parameter_bounds(&self, span: Span, def_id: ast::NodeId)
                                  -> Result<Vec<ty::PolyTraitRef<'tcx>>, ErrorReported>;
 
+    /// Returns true if the trait with id `trait_def_id` defines an
+    /// associated type with the name `name`.
+    fn trait_defines_associated_type_named(&self, trait_def_id: ast::DefId, name: ast::Name)
+                                           -> bool;
+
     /// Return an (optional) substitution to convert bound type parameters that
     /// are in scope into free ones. This function should only return Some
     /// within a fn body.
@@ -205,25 +222,25 @@ pub fn opt_ast_region_to_region<'tcx>(
 
                                 if len == 2 && i == 0 {
                                     m.push_str(" or ");
-                                } else if i == len - 2 {
+                                } else if i + 2 == len {
                                     m.push_str(", or ");
-                                } else if i != len - 1 {
+                                } else if i + 1 != len {
                                     m.push_str(", ");
                                 }
                             }
                             if len == 1 {
-                                span_help!(this.tcx().sess, default_span,
+                                fileline_help!(this.tcx().sess, default_span,
                                     "this function's return type contains a borrowed value, but \
                                      the signature does not say which {} it is borrowed from",
                                     m);
                             } else if len == 0 {
-                                span_help!(this.tcx().sess, default_span,
+                                fileline_help!(this.tcx().sess, default_span,
                                     "this function's return type contains a borrowed value, but \
                                      there is no value for it to be borrowed from");
-                                span_help!(this.tcx().sess, default_span,
+                                fileline_help!(this.tcx().sess, default_span,
                                     "consider giving it a 'static lifetime");
                             } else {
-                                span_help!(this.tcx().sess, default_span,
+                                fileline_help!(this.tcx().sess, default_span,
                                     "this function's return type contains a borrowed value, but \
                                      the signature does not say whether it is borrowed from {}",
                                     m);
@@ -705,7 +722,7 @@ fn ast_path_to_trait_ref<'a,'tcx>(
                 span_err!(this.tcx().sess, span, E0215,
                                          "angle-bracket notation is not stable when \
                                          used with the `Fn` family of traits, use parentheses");
-                span_help!(this.tcx().sess, span,
+                fileline_help!(this.tcx().sess, span,
                            "add `#![feature(unboxed_closures)]` to \
                             the crate attributes to enable");
             }
@@ -719,7 +736,7 @@ fn ast_path_to_trait_ref<'a,'tcx>(
                 span_err!(this.tcx().sess, span, E0216,
                                          "parenthetical notation is only stable when \
                                          used with the `Fn` family of traits");
-                span_help!(this.tcx().sess, span,
+                fileline_help!(this.tcx().sess, span,
                            "add `#![feature(unboxed_closures)]` to \
                             the crate attributes to enable");
             }
@@ -783,7 +800,7 @@ fn ast_type_binding_to_projection_predicate<'tcx>(
     // We want to produce `<B as SuperTrait<int>>::T == foo`.
 
     // Simple case: X is defined in the current trait.
-    if trait_defines_associated_type_named(this, trait_ref.def_id, binding.item_name) {
+    if this.trait_defines_associated_type_named(trait_ref.def_id, binding.item_name) {
         return Ok(ty::ProjectionPredicate {
             projection_ty: ty::ProjectionTy {
                 trait_ref: trait_ref,
@@ -810,9 +827,11 @@ fn ast_type_binding_to_projection_predicate<'tcx>(
                                               tcx.mk_substs(dummy_substs)));
     }
 
+    try!(this.ensure_super_predicates(binding.span, trait_ref.def_id));
+
     let mut candidates: Vec<ty::PolyTraitRef> =
         traits::supertraits(tcx, trait_ref.to_poly_trait_ref())
-        .filter(|r| trait_defines_associated_type_named(this, r.def_id(), binding.item_name))
+        .filter(|r| this.trait_defines_associated_type_named(r.def_id(), binding.item_name))
         .collect();
 
     // If converting for an object type, then remove the dummy-ty from `Self` now.
@@ -944,14 +963,14 @@ fn ast_ty_to_trait_ref<'tcx>(this: &AstConv<'tcx>,
                       pprust::ty_to_string(ty));
             match ty.node {
                 ast::TyRptr(None, ref mut_ty) => {
-                    span_help!(this.tcx().sess, ty.span,
+                    fileline_help!(this.tcx().sess, ty.span,
                                "perhaps you meant `&{}({} +{})`? (per RFC 438)",
                                ppaux::mutability_to_string(mut_ty.mutbl),
                                pprust::ty_to_string(&*mut_ty.ty),
                                pprust::bounds_to_string(bounds));
                 }
                ast::TyRptr(Some(ref lt), ref mut_ty) => {
-                    span_help!(this.tcx().sess, ty.span,
+                    fileline_help!(this.tcx().sess, ty.span,
                                "perhaps you meant `&{} {}({} +{})`? (per RFC 438)",
                                pprust::lifetime_to_string(lt),
                                ppaux::mutability_to_string(mut_ty.mutbl),
@@ -960,7 +979,7 @@ fn ast_ty_to_trait_ref<'tcx>(this: &AstConv<'tcx>,
                 }
 
                 _ => {
-                    span_help!(this.tcx().sess, ty.span,
+                    fileline_help!(this.tcx().sess, ty.span,
                                "perhaps you forgot parentheses? (per RFC 438)");
                 }
             }
@@ -1029,14 +1048,19 @@ fn associated_path_def_to_ty<'tcx>(this: &AstConv<'tcx>,
 
     let ty_param_name = tcx.ty_param_defs.borrow()[ty_param_node_id].name;
 
-    // FIXME(#20300) -- search where clauses, not bounds
-    let bounds =
-        this.get_type_parameter_bounds(span, ty_param_node_id)
-            .unwrap_or(Vec::new());
+    let bounds = match this.get_type_parameter_bounds(span, ty_param_node_id) {
+        Ok(v) => v,
+        Err(ErrorReported) => { return (tcx.types.err, ty_path_def); }
+    };
+
+    // ensure the super predicates and stop if we encountered an error
+    if bounds.iter().any(|b| this.ensure_super_predicates(span, b.def_id()).is_err()) {
+        return (this.tcx().types.err, ty_path_def);
+    }
 
     let mut suitable_bounds: Vec<_> =
         traits::transitive_bounds(tcx, &bounds)
-        .filter(|b| trait_defines_associated_type_named(this, b.def_id(), assoc_name))
+        .filter(|b| this.trait_defines_associated_type_named(b.def_id(), assoc_name))
         .collect();
 
     if suitable_bounds.len() == 0 {
@@ -1090,16 +1114,6 @@ fn associated_path_def_to_ty<'tcx>(this: &AstConv<'tcx>,
     (ty, def::DefAssociatedTy(trait_did, item_did))
 }
 
-fn trait_defines_associated_type_named(this: &AstConv,
-                                       trait_def_id: ast::DefId,
-                                       assoc_name: ast::Name)
-                                       -> bool
-{
-    let tcx = this.tcx();
-    let trait_def = ty::lookup_trait_def(tcx, trait_def_id);
-    trait_def.associated_type_names.contains(&assoc_name)
-}
-
 fn qpath_to_ty<'tcx>(this: &AstConv<'tcx>,
                      rscope: &RegionScope,
                      span: Span,
@@ -1233,17 +1247,18 @@ pub fn finish_resolving_def_to_ty<'tcx>(this: &AstConv<'tcx>,
             if segments.is_empty() {
                 opt_self_ty.expect("missing T in <T>::a::b::c")
             } else {
-                tcx.sess.span_bug(span,
-                                  &format!("found module name used as a type: {}",
-                                           tcx.map.node_to_string(id.node)));
+                span_err!(tcx.sess, span, E0247, "found module name used as a type: {}",
+                          tcx.map.node_to_string(id.node));
+                return this.tcx().types.err;
             }
         }
         def::DefPrimTy(prim_ty) => {
             prim_ty_to_ty(tcx, segments, prim_ty)
         }
         _ => {
-            span_fatal!(tcx.sess, span, E0248,
-                        "found value name used as a type: {:?}", *def);
+            span_err!(tcx.sess, span, E0248,
+                      "found value name used as a type: {:?}", *def);
+            return this.tcx().types.err;
         }
     };
 
@@ -1274,19 +1289,9 @@ pub fn ast_ty_to_ty<'tcx>(this: &AstConv<'tcx>,
 
     let tcx = this.tcx();
 
-    let mut ast_ty_to_ty_cache = tcx.ast_ty_to_ty_cache.borrow_mut();
-    match ast_ty_to_ty_cache.get(&ast_ty.id) {
-        Some(&ty::atttce_resolved(ty)) => return ty,
-        Some(&ty::atttce_unresolved) => {
-            span_fatal!(tcx.sess, ast_ty.span, E0246,
-                                "illegal recursive type; insert an enum \
-                                 or struct in the cycle, if this is \
-                                 desired");
-        }
-        None => { /* go on */ }
+    if let Some(&ty) = tcx.ast_ty_to_ty_cache.borrow().get(&ast_ty.id) {
+        return ty;
     }
-    ast_ty_to_ty_cache.insert(ast_ty.id, ty::atttce_unresolved);
-    drop(ast_ty_to_ty_cache);
 
     let typ = match ast_ty.node {
         ast::TyVec(ref ty) => {
@@ -1388,14 +1393,22 @@ pub fn ast_ty_to_ty<'tcx>(this: &AstConv<'tcx>,
                             ty::mk_vec(tcx, ast_ty_to_ty(this, rscope, &**ty),
                                         Some(i as uint)),
                         _ => {
-                            span_fatal!(tcx.sess, ast_ty.span, E0249,
-                                        "expected constant expr for array length");
+                            span_err!(tcx.sess, ast_ty.span, E0249,
+                                      "expected constant expr for array length");
+                            this.tcx().types.err
                         }
                     }
                 }
-                Err(r) => {
-                    span_fatal!(tcx.sess, ast_ty.span, E0250,
-                                "expected constant expr for array length: {}", r);
+                Err(ref r) => {
+                    let subspan  =
+                        ast_ty.span.lo <= r.span.lo && r.span.hi <= ast_ty.span.hi;
+                    span_err!(tcx.sess, r.span, E0250,
+                              "array length constant evaluation error: {}",
+                              r.description());
+                    if !subspan {
+                        span_note!(tcx.sess, ast_ty.span, "for array length here")
+                    }
+                    this.tcx().types.err
                 }
             }
         }
@@ -1411,7 +1424,7 @@ pub fn ast_ty_to_ty<'tcx>(this: &AstConv<'tcx>,
         }
     };
 
-    tcx.ast_ty_to_ty_cache.borrow_mut().insert(ast_ty.id, ty::atttce_resolved(typ));
+    tcx.ast_ty_to_ty_cache.borrow_mut().insert(ast_ty.id, typ);
     return typ;
 }
 
@@ -1828,6 +1841,10 @@ fn compute_object_lifetime_bound<'tcx>(
         return ast_region_to_region(tcx, r);
     }
 
+    if let Err(ErrorReported) = this.ensure_super_predicates(span,principal_trait_ref.def_id()) {
+        return ty::ReStatic;
+    }
+
     // No explicit region bound specified. Therefore, examine trait
     // bounds and see if we can derive region bounds from those.
     let derived_region_bounds =
@@ -1913,34 +1930,11 @@ pub fn partition_bounds<'a>(tcx: &ty::ctxt,
     let mut builtin_bounds = ty::empty_builtin_bounds();
     let mut region_bounds = Vec::new();
     let mut trait_bounds = Vec::new();
-    let mut trait_def_ids = DefIdMap();
     for ast_bound in ast_bounds {
         match *ast_bound {
             ast::TraitTyParamBound(ref b, ast::TraitBoundModifier::None) => {
                 match ::lookup_full_def(tcx, b.trait_ref.path.span, b.trait_ref.ref_id) {
                     def::DefTrait(trait_did) => {
-                        match trait_def_ids.get(&trait_did) {
-                            // Already seen this trait. We forbid
-                            // duplicates in the list (for some
-                            // reason).
-                            Some(span) => {
-                                span_err!(
-                                    tcx.sess, b.trait_ref.path.span, E0127,
-                                    "trait `{}` already appears in the \
-                                     list of bounds",
-                                    b.trait_ref.path.user_string(tcx));
-                                tcx.sess.span_note(
-                                    *span,
-                                    "previous appearance is here");
-
-                                continue;
-                            }
-
-                            None => { }
-                        }
-
-                        trait_def_ids.insert(trait_did, b.trait_ref.path.span);
-
                         if ty::try_add_builtin_trait(tcx,
                                                      trait_did,
                                                      &mut builtin_bounds) {
index 0ad15456df98f16daab554c59b289287426b0523..6ba21e25e1fe5c62d48f4ca1c1f65465893005a5 100644 (file)
@@ -63,7 +63,7 @@ pub fn check_legal_trait_for_method_call(ccx: &CrateCtxt, span: Span, trait_id:
         span_err!(tcx.sess, span, E0174,
                   "explicit use of unboxed closure method `{}` is experimental",
                   method);
-        span_help!(tcx.sess, span,
+        fileline_help!(tcx.sess, span,
                    "add `#![feature(unboxed_closures)]` to the crate attributes to enable");
     }
 }
@@ -137,7 +137,7 @@ fn try_overloaded_call_step<'a, 'tcx>(fcx: &FnCtxt<'a, 'tcx>,
             return Some(CallStep::Builtin);
         }
 
-        ty::ty_closure(def_id, _, substs) => {
+        ty::ty_closure(def_id, substs) => {
             assert_eq!(def_id.krate, ast::LOCAL_CRATE);
 
             // Check whether this is a call to a closure where we
@@ -152,12 +152,12 @@ fn try_overloaded_call_step<'a, 'tcx>(fcx: &FnCtxt<'a, 'tcx>,
                                                                           &closure_ty.sig).0;
                 fcx.record_deferred_call_resolution(
                     def_id,
-                    box CallResolution {call_expr: call_expr,
-                                        callee_expr: callee_expr,
-                                        adjusted_ty: adjusted_ty,
-                                        autoderefref: autoderefref,
-                                        fn_sig: fn_sig.clone(),
-                                        closure_def_id: def_id});
+                    Box::new(CallResolution {call_expr: call_expr,
+                                         callee_expr: callee_expr,
+                                         adjusted_ty: adjusted_ty,
+                                         autoderefref: autoderefref,
+                                         fn_sig: fn_sig.clone(),
+                                         closure_def_id: def_id}));
                 return Some(CallStep::DeferredClosure(fn_sig));
             }
         }
index 0b7c5b04aaa44d5802f117f8312ed294b6018ad9..0d4edc01a4c1d73ae16c821e52de1a940b8d6f09 100644 (file)
@@ -16,7 +16,6 @@
 use middle::region;
 use middle::subst;
 use middle::ty::{self, ToPolyTraitRef, Ty};
-use rscope::RegionScope;
 use syntax::abi;
 use syntax::ast;
 use syntax::ast_util;
@@ -61,17 +60,8 @@ fn check_closure<'a,'tcx>(fcx: &FnCtxt<'a,'tcx>,
         abi::RustCall,
         expected_sig);
 
-    let region = match fcx.anon_regions(expr.span, 1) {
-        Err(_) => {
-            fcx.ccx.tcx.sess.span_bug(expr.span,
-                                      "can't make anon regions here?!")
-        }
-        Ok(regions) => regions[0],
-    };
-
     let closure_type = ty::mk_closure(fcx.ccx.tcx,
                                       expr_def_id,
-                                      fcx.ccx.tcx.mk_region(region),
                                       fcx.ccx.tcx.mk_substs(
                                         fcx.inh.param_env.free_substs.clone()));
 
index cffd74ccd7218c3da9458131a756bfd3e1578cb6..9c48ac43ee468bb94c38cd3adb65b4766202981b 100644 (file)
@@ -298,8 +298,8 @@ fn iterate_over_potentially_unsafe_regions_in_type<'a, 'tcx>(
                 match rcx.tcx().region_maps.opt_encl_scope(scope) {
                     Some(parent_scope) => ty::ReScope(parent_scope),
                     None => rcx.tcx().sess.span_bug(
-                        span, format!("no enclosing scope found for scope: {:?}",
-                                      scope).as_slice()),
+                        span, &format!("no enclosing scope found for scope: {:?}",
+                                       scope)),
                 };
 
             regionck::type_must_outlive(rcx, origin(), typ, parent_region);
index f65e585d23edd3c8c11e2ac3c11db443db9bd7ed..6b4a7761d0a9b836bf913d611d03aea86f7b3bac 100644 (file)
@@ -22,6 +22,7 @@
 use syntax::codemap::Span;
 
 use util::common::ErrorReported;
+use util::nodemap::FnvHashSet;
 use util::ppaux::Repr;
 
 // Helper functions related to manipulating region types.
@@ -29,6 +30,7 @@
 pub enum Implication<'tcx> {
     RegionSubRegion(Option<Ty<'tcx>>, ty::Region, ty::Region),
     RegionSubGeneric(Option<Ty<'tcx>>, ty::Region, GenericKind<'tcx>),
+    RegionSubClosure(Option<Ty<'tcx>>, ty::Region, ast::DefId, &'tcx Substs<'tcx>),
     Predicate(ast::DefId, ty::Predicate<'tcx>),
 }
 
@@ -39,6 +41,7 @@ struct Implicator<'a, 'tcx: 'a> {
     stack: Vec<(ty::Region, Option<Ty<'tcx>>)>,
     span: Span,
     out: Vec<Implication<'tcx>>,
+    visited: FnvHashSet<Ty<'tcx>>,
 }
 
 /// This routine computes the well-formedness constraints that must hold for the type `ty` to
@@ -64,7 +67,8 @@ pub fn implications<'a,'tcx>(
                               body_id: body_id,
                               span: span,
                               stack: stack,
-                              out: Vec::new() };
+                              out: Vec::new(),
+                              visited: FnvHashSet() };
     wf.accumulate_from_ty(ty);
     debug!("implications: out={}", wf.out.repr(closure_typer.tcx()));
     wf.out
@@ -79,6 +83,12 @@ fn accumulate_from_ty(&mut self, ty: Ty<'tcx>) {
         debug!("accumulate_from_ty(ty={})",
                ty.repr(self.tcx()));
 
+        // When expanding out associated types, we can visit a cyclic
+        // set of types. Issue #23003.
+        if !self.visited.insert(ty) {
+            return;
+        }
+
         match ty.sty {
             ty::ty_bool |
             ty::ty_char |
@@ -91,29 +101,9 @@ fn accumulate_from_ty(&mut self, ty: Ty<'tcx>) {
                 // No borrowed content reachable here.
             }
 
-            ty::ty_closure(_, region, _) => {
-                // An "closure type" is basically
-                // modeled here as equivalent to a struct like
-                //
-                //     struct TheClosure<'b> {
-                //         ...
-                //     }
-                //
-                // where the `'b` is the lifetime bound of the
-                // contents (i.e., all contents must outlive 'b).
-                //
-                // Even though closures are glorified structs
-                // of upvars, we do not need to consider them as they
-                // can't generate any new constraints.  The
-                // substitutions on the closure are equal to the free
-                // substitutions of the enclosing parameter
-                // environment.  An upvar captured by value has the
-                // same type as the original local variable which is
-                // already checked for consistency.  If the upvar is
-                // captured by reference it must also outlive the
-                // region bound on the closure, but this is explicitly
-                // handled by logic in regionck.
-                self.push_region_constraint_from_top(*region);
+            ty::ty_closure(def_id, substs) => {
+                let &(r_a, opt_ty) = self.stack.last().unwrap();
+                self.out.push(Implication::RegionSubClosure(opt_ty, r_a, def_id, substs));
             }
 
             ty::ty_trait(ref t) => {
@@ -448,6 +438,13 @@ fn repr(&self, tcx: &ty::ctxt<'tcx>) -> String {
                         p.repr(tcx))
             }
 
+            Implication::RegionSubClosure(_, ref a, ref b, ref c) => {
+                format!("RegionSubClosure({}, {}, {})",
+                        a.repr(tcx),
+                        b.repr(tcx),
+                        c.repr(tcx))
+            }
+
             Implication::Predicate(ref def_id, ref p) => {
                 format!("Predicate({}, {})",
                         def_id.repr(tcx),
index d7db21f3a2f762350f94f0636886695f8b203fbf..6ef6953f707fb2d6ef310eb97df5770cc0ae6ccc 100644 (file)
@@ -634,16 +634,21 @@ fn upcast(&mut self,
               target_trait_def_id: ast::DefId)
               -> ty::PolyTraitRef<'tcx>
     {
-        match traits::upcast(self.tcx(), source_trait_ref.clone(), target_trait_def_id) {
-            Some(super_trait_ref) => super_trait_ref,
-            None => {
-                self.tcx().sess.span_bug(
-                    self.span,
-                    &format!("cannot upcast `{}` to `{}`",
-                             source_trait_ref.repr(self.tcx()),
-                             target_trait_def_id.repr(self.tcx())));
-            }
+        let upcast_trait_refs = traits::upcast(self.tcx(),
+                                               source_trait_ref.clone(),
+                                               target_trait_def_id);
+
+        // must be exactly one trait ref or we'd get an ambig error etc
+        if upcast_trait_refs.len() != 1 {
+            self.tcx().sess.span_bug(
+                self.span,
+                &format!("cannot uniquely upcast `{}` to `{}`: `{}`",
+                         source_trait_ref.repr(self.tcx()),
+                         target_trait_def_id.repr(self.tcx()),
+                         upcast_trait_refs.repr(self.tcx())));
         }
+
+        upcast_trait_refs.into_iter().next().unwrap()
     }
 
     fn replace_late_bound_regions_with_fresh_var<T>(&self, value: &ty::Binder<T>) -> T
index f24da78bc7d3974ea304f5c8f38f9d1f80a237ec..718804d317fb09c6a8169b5562d7fdc888a674d4 100644 (file)
@@ -278,7 +278,7 @@ fn assemble_probe(&mut self, self_ty: Ty<'tcx>) {
             }
             ty::ty_enum(did, _) |
             ty::ty_struct(did, _) |
-            ty::ty_closure(did, _, _) => {
+            ty::ty_closure(did, _) => {
                 self.assemble_inherent_impl_candidates_for_type(did);
             }
             ty::ty_uniq(_) => {
@@ -456,13 +456,7 @@ fn elaborate_bounds<F>(
         debug!("elaborate_bounds(bounds={})", bounds.repr(self.tcx()));
 
         let tcx = self.tcx();
-        let mut cache = HashSet::new();
         for bound_trait_ref in traits::transitive_bounds(tcx, bounds) {
-            // Already visited this trait, skip it.
-            if !cache.insert(bound_trait_ref.def_id()) {
-                continue;
-            }
-
             let (pos, method) = match trait_method(tcx,
                                                    bound_trait_ref.def_id(),
                                                    self.method_name) {
@@ -641,8 +635,8 @@ fn assemble_closure_candidates(&mut self,
         // If so, add "synthetic impls".
         let steps = self.steps.clone();
         for step in &*steps {
-            let (closure_def_id, _, _) = match step.self_ty.sty {
-                ty::ty_closure(a, b, ref c) => (a, b, c),
+            let closure_def_id = match step.self_ty.sty {
+                ty::ty_closure(a, _) => a,
                 _ => continue,
             };
 
@@ -1269,10 +1263,12 @@ fn to_source(&self) -> CandidateSource {
 
     fn to_trait_data(&self) -> Option<(ast::DefId,MethodIndex)> {
         match self.kind {
-            InherentImplCandidate(..) |
-            ObjectCandidate(..) => {
+            InherentImplCandidate(..) => {
                 None
             }
+            ObjectCandidate(trait_def_id, method_num, _) => {
+                Some((trait_def_id, method_num))
+            }
             ClosureCandidate(trait_def_id, method_num) => {
                 Some((trait_def_id, method_num))
             }
index fd6ba79ec21bb87955d3c237fa1ca707edc1a5f4..44500ce0bbb7f01aed30d960944d14ac4059c409 100644 (file)
@@ -1218,6 +1218,11 @@ fn get_trait_def(&self, _: Span, id: ast::DefId)
         Ok(ty::lookup_trait_def(self.tcx(), id))
     }
 
+    fn ensure_super_predicates(&self, _: Span, _: ast::DefId) -> Result<(), ErrorReported> {
+        // all super predicates are ensured during collect pass
+        Ok(())
+    }
+
     fn get_free_substs(&self) -> Option<&Substs<'tcx>> {
         Some(&self.inh.param_env.free_substs)
     }
@@ -1248,6 +1253,15 @@ fn get_type_parameter_bounds(&self,
         Ok(r)
     }
 
+    fn trait_defines_associated_type_named(&self,
+                                           trait_def_id: ast::DefId,
+                                           assoc_name: ast::Name)
+                                           -> bool
+    {
+        let trait_def = ty::lookup_trait_def(self.ccx.tcx, trait_def_id);
+        trait_def.associated_type_names.contains(&assoc_name)
+    }
+
     fn ty_infer(&self, _span: Span) -> Ty<'tcx> {
         self.infcx().next_ty_var()
     }
@@ -1363,10 +1377,10 @@ pub fn local_ty(&self, span: Span, nid: ast::NodeId) -> Ty<'tcx> {
         match self.inh.locals.borrow().get(&nid) {
             Some(&t) => t,
             None => {
-                self.tcx().sess.span_bug(
+                self.tcx().sess.span_err(
                     span,
-                    &format!("no type for local variable {}",
-                            nid));
+                    &format!("no type for local variable {}", nid));
+                self.tcx().types.err
             }
         }
     }
@@ -3098,7 +3112,7 @@ fn check_field<'a,'tcx>(fcx: &FnCtxt<'a,'tcx>,
                 },
                 expr_t, None);
 
-            tcx.sess.span_help(field.span,
+            tcx.sess.fileline_help(field.span,
                                "maybe a `()` to call it is missing? \
                                If not, try an anonymous function");
         } else {
@@ -4480,7 +4494,7 @@ pub fn check_instantiable(tcx: &ty::ctxt,
         span_err!(tcx.sess, sp, E0073,
             "this type cannot be instantiated without an \
              instance of itself");
-        span_help!(tcx.sess, sp, "consider using `Option<{}>`",
+        fileline_help!(tcx.sess, sp, "consider using `Option<{}>`",
             ppaux::ty_to_string(tcx, item_ty));
         false
     } else {
@@ -4554,6 +4568,7 @@ fn do_check<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
                           id: ast::NodeId,
                           hint: attr::ReprAttr)
                           -> Vec<Rc<ty::VariantInfo<'tcx>>> {
+        use std::num::Int;
 
         let rty = ty::node_id_to_type(ccx.tcx, id);
         let mut variants: Vec<Rc<ty::VariantInfo>> = Vec::new();
@@ -4565,7 +4580,13 @@ fn do_check<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
             // If the discriminant value is specified explicitly in the enum check whether the
             // initialization expression is valid, otherwise use the last value plus one.
             let mut current_disr_val = match prev_disr_val {
-                Some(prev_disr_val) => prev_disr_val + 1,
+                Some(prev_disr_val) => {
+                    if let Some(v) = prev_disr_val.checked_add(1) {
+                        v
+                    } else {
+                        ty::INITIAL_DISCRIMINANT_VALUE
+                    }
+                }
                 None => ty::INITIAL_DISCRIMINANT_VALUE
             };
 
@@ -4597,8 +4618,9 @@ fn do_check<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
                                 "expected signed integer constant");
                         }
                         Err(ref err) => {
-                            span_err!(ccx.tcx.sess, e.span, E0080,
-                                "expected constant: {}", *err);
+                            span_err!(ccx.tcx.sess, err.span, E0080,
+                                      "constant evaluation error: {}",
+                                      err.description());
                         }
                     }
                 },
@@ -5491,6 +5513,9 @@ fn param<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, n: u32) -> Ty<'tcx> {
                 (0, vec!(tcx.types.u64, tcx.types.u64),
                 ty::mk_tup(tcx, vec!(tcx.types.u64, tcx.types.bool))),
 
+            "overflowing_add" | "overflowing_sub" | "overflowing_mul" =>
+                (1, vec![param(ccx, 0), param(ccx, 0)], param(ccx, 0)),
+
             "return_address" => (0, vec![], ty::mk_imm_ptr(tcx, tcx.types.u8)),
 
             "assume" => (0, vec![tcx.types.bool], ty::mk_nil(tcx)),
index 1518a09e7dc063656d2dba73782be746a686cbb7..e1bcad2af37d627f0590fd5cf216d508f39b6df5 100644 (file)
 use check::FnCtxt;
 use check::implicator;
 use check::vtable;
-use middle::def;
 use middle::mem_categorization as mc;
 use middle::region::CodeExtent;
+use middle::subst::Substs;
 use middle::traits;
-use middle::ty::{ReScope};
-use middle::ty::{self, Ty, MethodCall};
+use middle::ty::{self, ClosureTyper, ReScope, Ty, MethodCall};
 use middle::infer::{self, GenericKind};
 use middle::pat_util;
 use util::ppaux::{ty_to_string, Repr};
@@ -179,20 +178,6 @@ pub struct Rcx<'a, 'tcx: 'a> {
 
 }
 
-/// Returns the validity region of `def` -- that is, how long is `def` valid?
-fn region_of_def(fcx: &FnCtxt, def: def::Def) -> ty::Region {
-    let tcx = fcx.tcx();
-    match def {
-        def::DefLocal(node_id) | def::DefUpvar(node_id, _) => {
-            tcx.region_maps.var_region(node_id)
-        }
-        _ => {
-            tcx.sess.bug(&format!("unexpected def in region_of_def: {:?}",
-                                 def))
-        }
-    }
-}
-
 struct RepeatingScope(ast::NodeId);
 pub enum SubjectNode { Subject(ast::NodeId), None }
 
@@ -368,7 +353,15 @@ fn relate_free_regions(&mut self,
                                                              ty::ReInfer(ty::ReVar(vid_b))) => {
                         self.fcx.inh.infcx.add_given(free_a, vid_b);
                     }
-                    implicator::Implication::RegionSubRegion(..) => {
+                    implicator::Implication::RegionSubGeneric(_, r_a, ref generic_b) => {
+                        debug!("RegionSubGeneric: {} <= {}",
+                               r_a.repr(tcx), generic_b.repr(tcx));
+
+                        self.region_bound_pairs.push((r_a, generic_b.clone()));
+                    }
+                    implicator::Implication::RegionSubRegion(..) |
+                    implicator::Implication::RegionSubClosure(..) |
+                    implicator::Implication::Predicate(..) => {
                         // In principle, we could record (and take
                         // advantage of) every relationship here, but
                         // we are also free not to -- it simply means
@@ -379,13 +372,6 @@ fn relate_free_regions(&mut self,
                         // relationship that arises here, but
                         // presently we do not.)
                     }
-                    implicator::Implication::RegionSubGeneric(_, r_a, ref generic_b) => {
-                        debug!("RegionSubGeneric: {} <= {}",
-                               r_a.repr(tcx), generic_b.repr(tcx));
-
-                        self.region_bound_pairs.push((r_a, generic_b.clone()));
-                    }
-                    implicator::Implication::Predicate(..) => { }
                 }
             }
         }
@@ -792,124 +778,9 @@ fn walk_cast<'a, 'tcx>(rcx: &mut Rcx<'a, 'tcx>,
 fn check_expr_fn_block(rcx: &mut Rcx,
                        expr: &ast::Expr,
                        body: &ast::Block) {
-    let tcx = rcx.fcx.tcx();
-    let function_type = rcx.resolve_node_type(expr.id);
-
-    match function_type.sty {
-        ty::ty_closure(_, region, _) => {
-            ty::with_freevars(tcx, expr.id, |freevars| {
-                constrain_captured_variables(rcx, *region, expr, freevars);
-            })
-        }
-        _ => { }
-    }
-
     let repeating_scope = rcx.set_repeating_scope(body.id);
     visit::walk_expr(rcx, expr);
     rcx.set_repeating_scope(repeating_scope);
-
-    match function_type.sty {
-        ty::ty_closure(_, region, _) => {
-            ty::with_freevars(tcx, expr.id, |freevars| {
-                let bounds = ty::region_existential_bound(*region);
-                ensure_free_variable_types_outlive_closure_bound(rcx, &bounds, expr, freevars);
-            })
-        }
-        _ => {}
-    }
-
-    /// Make sure that the type of all free variables referenced inside a closure/proc outlive the
-    /// closure/proc's lifetime bound. This is just a special case of the usual rules about closed
-    /// over values outliving the object's lifetime bound.
-    fn ensure_free_variable_types_outlive_closure_bound(
-        rcx: &mut Rcx,
-        bounds: &ty::ExistentialBounds,
-        expr: &ast::Expr,
-        freevars: &[ty::Freevar])
-    {
-        let tcx = rcx.fcx.ccx.tcx;
-
-        debug!("ensure_free_variable_types_outlive_closure_bound({}, {})",
-               bounds.region_bound.repr(tcx), expr.repr(tcx));
-
-        for freevar in freevars {
-            let var_node_id = {
-                let def_id = freevar.def.def_id();
-                assert!(def_id.krate == ast::LOCAL_CRATE);
-                def_id.node
-            };
-
-            // Compute the type of the field in the environment that
-            // represents `var_node_id`.  For a by-value closure, this
-            // will be the same as the type of the variable.  For a
-            // by-reference closure, this will be `&T` where `T` is
-            // the type of the variable.
-            let raw_var_ty = rcx.resolve_node_type(var_node_id);
-            let upvar_id = ty::UpvarId { var_id: var_node_id,
-                                         closure_expr_id: expr.id };
-            let var_ty = match rcx.fcx.inh.upvar_capture_map.borrow()[upvar_id] {
-                ty::UpvarCapture::ByRef(ref upvar_borrow) => {
-                    ty::mk_rptr(rcx.tcx(),
-                                rcx.tcx().mk_region(upvar_borrow.region),
-                                ty::mt { mutbl: upvar_borrow.kind.to_mutbl_lossy(),
-                                         ty: raw_var_ty })
-                }
-                ty::UpvarCapture::ByValue => raw_var_ty,
-            };
-
-            // Check that the type meets the criteria of the existential bounds:
-            for builtin_bound in &bounds.builtin_bounds {
-                let code = traits::ClosureCapture(var_node_id, expr.span, builtin_bound);
-                let cause = traits::ObligationCause::new(freevar.span, rcx.fcx.body_id, code);
-                rcx.fcx.register_builtin_bound(var_ty, builtin_bound, cause);
-            }
-
-            type_must_outlive(
-                rcx, infer::FreeVariable(expr.span, var_node_id),
-                var_ty, bounds.region_bound);
-        }
-    }
-
-    /// Make sure that all free variables referenced inside the closure outlive the closure's
-    /// lifetime bound. Also, create an entry in the upvar_borrows map with a region.
-    fn constrain_captured_variables(
-        rcx: &mut Rcx,
-        region_bound: ty::Region,
-        expr: &ast::Expr,
-        freevars: &[ty::Freevar])
-    {
-        let tcx = rcx.fcx.ccx.tcx;
-        debug!("constrain_captured_variables({}, {})",
-               region_bound.repr(tcx), expr.repr(tcx));
-        for freevar in freevars {
-            debug!("constrain_captured_variables: freevar.def={:?}", freevar.def);
-
-            // Identify the variable being closed over and its node-id.
-            let def = freevar.def;
-            let var_node_id = {
-                let def_id = def.def_id();
-                assert!(def_id.krate == ast::LOCAL_CRATE);
-                def_id.node
-            };
-            let upvar_id = ty::UpvarId { var_id: var_node_id,
-                                         closure_expr_id: expr.id };
-
-            match rcx.fcx.inh.upvar_capture_map.borrow()[upvar_id] {
-                ty::UpvarCapture::ByValue => { }
-                ty::UpvarCapture::ByRef(upvar_borrow) => {
-                    rcx.fcx.mk_subr(infer::FreeVariable(freevar.span, var_node_id),
-                                    region_bound, upvar_borrow.region);
-
-                    // Guarantee that the closure does not outlive the variable itself.
-                    let enclosing_region = region_of_def(rcx.fcx, def);
-                    debug!("constrain_captured_variables: enclosing_region = {}",
-                           enclosing_region.repr(tcx));
-                    rcx.fcx.mk_subr(infer::FreeVariable(freevar.span, var_node_id),
-                                    region_bound, enclosing_region);
-                }
-            }
-        }
-    }
 }
 
 fn constrain_callee(rcx: &mut Rcx,
@@ -1092,9 +963,9 @@ fn check_safety_of_rvalue_destructor_if_necessary<'a, 'tcx>(rcx: &mut Rcx<'a, 't
                     rcx.tcx()
                        .sess
                        .span_bug(span,
-                                 format!("unexpected rvalue region in rvalue \
-                                          destructor safety checking: `{}`",
-                                         region.repr(rcx.tcx())).as_slice());
+                                 &format!("unexpected rvalue region in rvalue \
+                                           destructor safety checking: `{}`",
+                                          region.repr(rcx.tcx())));
                 }
             }
         }
@@ -1538,6 +1409,9 @@ pub fn type_must_outlive<'a, 'tcx>(rcx: &mut Rcx<'a, 'tcx>,
                 let o1 = infer::ReferenceOutlivesReferent(ty, origin.span());
                 generic_must_outlive(rcx, o1, r_a, generic_b);
             }
+            implicator::Implication::RegionSubClosure(_, r_a, def_id, substs) => {
+                closure_must_outlive(rcx, origin.clone(), r_a, def_id, substs);
+            }
             implicator::Implication::Predicate(def_id, predicate) => {
                 let cause = traits::ObligationCause::new(origin.span(),
                                                          rcx.body_id,
@@ -1549,6 +1423,23 @@ pub fn type_must_outlive<'a, 'tcx>(rcx: &mut Rcx<'a, 'tcx>,
     }
 }
 
+fn closure_must_outlive<'a, 'tcx>(rcx: &mut Rcx<'a, 'tcx>,
+                                  origin: infer::SubregionOrigin<'tcx>,
+                                  region: ty::Region,
+                                  def_id: ast::DefId,
+                                  substs: &'tcx Substs<'tcx>) {
+    debug!("closure_must_outlive(region={}, def_id={}, substs={})",
+           region.repr(rcx.tcx()), def_id.repr(rcx.tcx()), substs.repr(rcx.tcx()));
+
+    let upvars = rcx.fcx.closure_upvars(def_id, substs).unwrap();
+    for upvar in upvars {
+        let var_id = upvar.def.def_id().local_id();
+        type_must_outlive(
+            rcx, infer::FreeVariable(origin.span(), var_id),
+            upvar.ty, region);
+    }
+}
+
 fn generic_must_outlive<'a, 'tcx>(rcx: &Rcx<'a, 'tcx>,
                                   origin: infer::SubregionOrigin<'tcx>,
                                   region: ty::Region,
index e024526d0016f7756c18baa0e2036f2379b0a213..32bd40ebda2de26d944e12a4130752af65419405 100644 (file)
@@ -118,7 +118,7 @@ fn check_item_well_formed(&mut self, item: &ast::Item) {
 
                 self.check_variances_for_type_defn(item, ast_generics);
             }
-            ast::ItemTrait(_, ref ast_generics, _, _) => {
+            ast::ItemTrait(_, ref ast_generics, _, ref items) => {
                 let trait_predicates =
                     ty::lookup_predicates(ccx.tcx, local_def(item.id));
                 reject_non_type_param_bounds(
@@ -127,6 +127,14 @@ fn check_item_well_formed(&mut self, item: &ast::Item) {
                     &trait_predicates);
                 self.check_variances(item, ast_generics, &trait_predicates,
                                      self.tcx().lang_items.phantom_fn());
+                if ty::trait_has_default_impl(ccx.tcx, local_def(item.id)) {
+                    if !items.is_empty() {
+                        ccx.tcx.sess.span_err(
+                            item.span,
+                            "traits with default impls (`e.g. unsafe impl Trait for ..`) must \
+                            have no methods or associated items")
+                    }
+                }
             }
             _ => {}
         }
@@ -281,12 +289,13 @@ fn check_impl(&mut self,
 
             // Find the supertrait bounds. This will add `int:Bar`.
             let poly_trait_ref = ty::Binder(trait_ref);
-            let predicates = ty::predicates_for_trait_ref(fcx.tcx(), &poly_trait_ref);
+            let predicates = ty::lookup_super_predicates(fcx.tcx(), poly_trait_ref.def_id());
+            let predicates = predicates.instantiate_supertrait(fcx.tcx(), &poly_trait_ref);
             let predicates = {
                 let selcx = &mut traits::SelectionContext::new(fcx.infcx(), fcx);
                 traits::normalize(selcx, cause.clone(), &predicates)
             };
-            for predicate in predicates.value {
+            for predicate in predicates.value.predicates {
                 fcx.register_predicate(traits::Obligation::new(cause.clone(), predicate));
             }
             for obligation in predicates.obligations {
@@ -400,11 +409,11 @@ fn report_bivariance(&self,
 
         match suggested_marker_id {
             Some(def_id) => {
-                self.tcx().sess.span_help(
+                self.tcx().sess.fileline_help(
                     span,
-                    format!("consider removing `{}` or using a marker such as `{}`",
-                            param_name.user_string(self.tcx()),
-                            ty::item_path_str(self.tcx(), def_id)).as_slice());
+                    &format!("consider removing `{}` or using a marker such as `{}`",
+                             param_name.user_string(self.tcx()),
+                             ty::item_path_str(self.tcx(), def_id)));
             }
             None => {
                 // no lang items, no help!
diff --git a/src/librustc_typeck/coherence/impls.rs b/src/librustc_typeck/coherence/impls.rs
deleted file mode 100644 (file)
index e89c96b..0000000
+++ /dev/null
@@ -1,47 +0,0 @@
-// Copyright 2015 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.
-
-//! Implementations checker: builtin traits and default impls are allowed just
-//! for structs and enums.
-
-use middle::ty;
-use syntax::ast::{Item, ItemImpl};
-use syntax::ast;
-use syntax::visit;
-
-pub fn check(tcx: &ty::ctxt) {
-    let mut impls = ImplsChecker { tcx: tcx };
-    visit::walk_crate(&mut impls, tcx.map.krate());
-}
-
-struct ImplsChecker<'cx, 'tcx:'cx> {
-    tcx: &'cx ty::ctxt<'tcx>
-}
-
-impl<'cx, 'tcx,'v> visit::Visitor<'v> for ImplsChecker<'cx, 'tcx> {
-    fn visit_item(&mut self, item: &'v ast::Item) {
-        match item.node {
-            ast::ItemImpl(_, _, _, Some(_), _, _) => {
-                let trait_ref = ty::impl_id_to_trait_ref(self.tcx, item.id);
-                if let Some(_) = self.tcx.lang_items.to_builtin_kind(trait_ref.def_id) {
-                    match trait_ref.self_ty().sty {
-                        ty::ty_struct(..) | ty::ty_enum(..) => {}
-                        _ => {
-                            span_err!(self.tcx.sess, item.span, E0209,
-                                "builtin traits can only be \
-                                          implemented on structs or enums");
-                        }
-                    }
-                }
-            }
-            _ => {}
-        }
-    }
-}
index 1913b55f1d8e69d03da3fc0b368345b055522ed5..a06dcbaf556bdd7ea032914df2b415844c8dfdb1 100644 (file)
@@ -49,7 +49,6 @@
 use util::nodemap::{DefIdMap, FnvHashMap};
 use util::ppaux::Repr;
 
-mod impls;
 mod orphan;
 mod overlap;
 mod unsafety;
@@ -397,7 +396,7 @@ fn populate_destructor_table(&self) {
             match self_type.ty.sty {
                 ty::ty_enum(type_def_id, _) |
                 ty::ty_struct(type_def_id, _) |
-                ty::ty_closure(type_def_id, _, _) => {
+                ty::ty_closure(type_def_id, _) => {
                     tcx.destructor_for_type
                        .borrow_mut()
                        .insert(type_def_id, method_def_id.def_id());
@@ -524,7 +523,7 @@ fn enforce_trait_manually_implementable(tcx: &ty::ctxt, sp: Span, trait_def_id:
         return // everything OK
     };
     span_err!(tcx.sess, sp, E0183, "manual implementations of `{}` are experimental", trait_name);
-    span_help!(tcx.sess, sp,
+    fileline_help!(tcx.sess, sp,
                "add `#![feature(unboxed_closures)]` to the crate attributes to enable");
 }
 
@@ -583,7 +582,6 @@ pub fn check_coherence(crate_context: &CrateCtxt) {
         inference_context: new_infer_ctxt(crate_context.tcx),
         inherent_impls: RefCell::new(FnvHashMap()),
     }.check(crate_context.tcx.map.krate());
-    impls::check(crate_context.tcx);
     unsafety::check(crate_context.tcx);
     orphan::check(crate_context.tcx);
     overlap::check(crate_context.tcx);
index 95dafccd866bf3369136c8f936b31edf362e7397..5dfe80cfcb213fd4a441b650af5b3b59802005d4 100644 (file)
@@ -37,10 +37,13 @@ fn check_def_id(&self, item: &ast::Item, def_id: ast::DefId) {
                        a trait or new type instead");
         }
     }
-}
 
-impl<'cx, 'tcx,'v> visit::Visitor<'v> for OrphanChecker<'cx, 'tcx> {
-    fn visit_item(&mut self, item: &ast::Item) {
+    /// Checks exactly one impl for orphan rules and other such
+    /// restrictions.  In this fn, it can happen that multiple errors
+    /// apply to a specific impl, so just return after reporting one
+    /// to prevent inundating the user with a bunch of similar error
+    /// reports.
+    fn check_item(&self, item: &ast::Item) {
         let def_id = ast_util::local_def(item.id);
         match item.node {
             ast::ItemImpl(_, _, _, None, _, _) => {
@@ -63,13 +66,15 @@ fn visit_item(&mut self, item: &ast::Item) {
                         span_err!(self.tcx.sess, item.span, E0118,
                                   "no base type found for inherent implementation; \
                                    implement a trait or new type instead");
+                        return;
                     }
                 }
             }
             ast::ItemImpl(_, _, _, Some(_), _, _) => {
                 // "Trait" impl
                 debug!("coherence2::orphan check: trait impl {}", item.repr(self.tcx));
-                let trait_def_id = ty::impl_trait_ref(self.tcx, def_id).unwrap().def_id;
+                let trait_ref = ty::impl_trait_ref(self.tcx, def_id).unwrap();
+                let trait_def_id = trait_ref.def_id;
                 match traits::orphan_check(self.tcx, def_id) {
                     Ok(()) => { }
                     Err(traits::OrphanCheckErr::NoLocalInputType) => {
@@ -80,6 +85,7 @@ fn visit_item(&mut self, item: &ast::Item) {
                                  types defined in this crate; \
                                  only traits defined in the current crate can be \
                                  implemented for arbitrary types");
+                            return;
                         }
                     }
                     Err(traits::OrphanCheckErr::UncoveredTy(param_ty)) => {
@@ -89,9 +95,100 @@ fn visit_item(&mut self, item: &ast::Item) {
                                      some local type (e.g. `MyStruct<T>`); only traits defined in \
                                      the current crate can be implemented for a type parameter",
                                     param_ty.user_string(self.tcx));
+                            return;
                         }
                     }
                 }
+
+                // In addition to the above rules, we restrict impls of defaulted traits
+                // so that they can only be implemented on structs/enums. To see why this
+                // restriction exists, consider the following example (#22978). Imagine
+                // that crate A defines a defaulted trait `Foo` and a fn that operates
+                // on pairs of types:
+                //
+                // ```
+                // // Crate A
+                // trait Foo { }
+                // impl Foo for .. { }
+                // fn two_foos<A:Foo,B:Foo>(..) {
+                //     one_foo::<(A,B)>(..)
+                // }
+                // fn one_foo<T:Foo>(..) { .. }
+                // ```
+                //
+                // This type-checks fine; in particular the fn
+                // `two_foos` is able to conclude that `(A,B):Foo`
+                // because `A:Foo` and `B:Foo`.
+                //
+                // Now imagine that crate B comes along and does the following:
+                //
+                // ```
+                // struct A { }
+                // struct B { }
+                // impl Foo for A { }
+                // impl Foo for B { }
+                // impl !Send for (A, B) { }
+                // ```
+                //
+                // This final impl is legal according to the orpan
+                // rules, but it invalidates the reasoning from
+                // `two_foos` above.
+                debug!("trait_ref={} trait_def_id={} trait_has_default_impl={}",
+                       trait_ref.repr(self.tcx),
+                       trait_def_id.repr(self.tcx),
+                       ty::trait_has_default_impl(self.tcx, trait_def_id));
+                if
+                    ty::trait_has_default_impl(self.tcx, trait_def_id) &&
+                    trait_def_id.krate != ast::LOCAL_CRATE
+                {
+                    let self_ty = trait_ref.self_ty();
+                    let opt_self_def_id = match self_ty.sty {
+                        ty::ty_struct(self_def_id, _) | ty::ty_enum(self_def_id, _) =>
+                            Some(self_def_id),
+                        ty::ty_uniq(..) =>
+                            self.tcx.lang_items.owned_box(),
+                        _ =>
+                            None
+                    };
+
+                    let msg = match opt_self_def_id {
+                        // We only want to permit structs/enums, but not *all* structs/enums.
+                        // They must be local to the current crate, so that people
+                        // can't do `unsafe impl Send for Rc<SomethingLocal>` or
+                        // `impl !Send for Box<SomethingLocalAndSend>`.
+                        Some(self_def_id) => {
+                            if self_def_id.krate == ast::LOCAL_CRATE {
+                                None
+                            } else {
+                                Some(format!(
+                                    "cross-crate traits with a default impl, like `{}`, \
+                                     can only be implemented for a struct/enum type \
+                                     defined in the current crate",
+                                    ty::item_path_str(self.tcx, trait_def_id)))
+                            }
+                        }
+                        _ => {
+                            Some(format!(
+                                "cross-crate traits with a default impl, like `{}`, \
+                                 can only be implemented for a struct/enum type, \
+                                 not `{}`",
+                                ty::item_path_str(self.tcx, trait_def_id),
+                                self_ty.user_string(self.tcx)))
+                        }
+                    };
+
+                    if let Some(msg) = msg {
+                        span_err!(self.tcx.sess, item.span, E0321, "{}", msg);
+                        return;
+                    }
+                }
+
+                // Disallow *all* explicit impls of `Sized` for now.
+                if Some(trait_def_id) == self.tcx.lang_items.sized_trait() {
+                    span_err!(self.tcx.sess, item.span, E0322,
+                              "explicit impls for the `Sized` trait are not permitted");
+                    return;
+                }
             }
             ast::ItemDefaultImpl(..) => {
                 // "Trait" impl
@@ -100,14 +197,20 @@ fn visit_item(&mut self, item: &ast::Item) {
                 if trait_ref.def_id.krate != ast::LOCAL_CRATE {
                     span_err!(self.tcx.sess, item.span, E0318,
                               "cannot create default implementations for traits outside the \
-                               crate they're defined in; define a new trait instead.");
+                               crate they're defined in; define a new trait instead");
+                    return;
                 }
             }
             _ => {
                 // Not an impl
             }
         }
+    }
+}
 
+impl<'cx, 'tcx,'v> visit::Visitor<'v> for OrphanChecker<'cx, 'tcx> {
+    fn visit_item(&mut self, item: &ast::Item) {
+        self.check_item(item);
         visit::walk_item(self, item);
     }
 }
index a6ecafb6241316382fd516b7236ff6527b80571a..466d00b348b94d33d029c7a34ecbb43b30f71030 100644 (file)
 use syntax::ast_util;
 use syntax::visit;
 use syntax::codemap::Span;
+use util::nodemap::DefIdMap;
 use util::ppaux::Repr;
 
 pub fn check(tcx: &ty::ctxt) {
-    let mut overlap = OverlapChecker { tcx: tcx };
+    let mut overlap = OverlapChecker { tcx: tcx, default_impls: DefIdMap() };
     overlap.check_for_overlapping_impls();
 
     // this secondary walk specifically checks for impls of defaulted
@@ -33,6 +34,9 @@ pub fn check(tcx: &ty::ctxt) {
 
 struct OverlapChecker<'cx, 'tcx:'cx> {
     tcx: &'cx ty::ctxt<'tcx>,
+
+    // maps from a trait def-id to an impl id
+    default_impls: DefIdMap<ast::NodeId>,
 }
 
 impl<'cx, 'tcx> OverlapChecker<'cx, 'tcx> {
@@ -134,24 +138,19 @@ impl<'cx, 'tcx,'v> visit::Visitor<'v> for OverlapChecker<'cx, 'tcx> {
     fn visit_item(&mut self, item: &'v ast::Item) {
         match item.node {
             ast::ItemDefaultImpl(_, _) => {
+                // look for another default impl; note that due to the
+                // general orphan/coherence rules, it must always be
+                // in this crate.
                 let impl_def_id = ast_util::local_def(item.id);
-                match ty::impl_trait_ref(self.tcx, impl_def_id) {
-                    Some(ref trait_ref) => {
-                        match ty::trait_default_impl(self.tcx, trait_ref.def_id) {
-                            Some(other_impl) if other_impl != impl_def_id => {
-                                self.report_overlap_error(trait_ref.def_id,
-                                                          other_impl,
-                                                          impl_def_id);
-                            }
-                            Some(_) => {}
-                            None => {
-                                self.tcx.sess.bug(
-                                          &format!("no default implementation recorded for `{:?}`",
-                                          item));
-                            }
-                        }
+                let trait_ref = ty::impl_trait_ref(self.tcx, impl_def_id).unwrap();
+                let prev_default_impl = self.default_impls.insert(trait_ref.def_id, item.id);
+                match prev_default_impl {
+                    Some(prev_id) => {
+                        self.report_overlap_error(trait_ref.def_id,
+                                                  impl_def_id,
+                                                  ast_util::local_def(prev_id));
                     }
-                    _ => {}
+                    None => { }
                 }
             }
             _ => {}
index 74fed6cbf3937364db6459f02cb83cd4b3975509..bd68802f262c1a1a532b1a03f8ea30d75b328f04 100644 (file)
 core type along with a list of the bounds for each parameter. Type
 parameters themselves are represented as `ty_param()` instances.
 
-The phasing of type conversion is somewhat complicated. There are a
-number of possible cycles that can arise.
-
-Converting types can require:
-
-1. `Foo<X>` where `Foo` is a type alias, or trait requires knowing:
-   - number of region / type parameters
-   - for type parameters, `T:'a` annotations to control defaults for object lifetimes
-   - defaults for type parameters (which are themselves types!)
-2. `Foo<X>` where `Foo` is a type alias requires knowing what `Foo` expands to
-3. Translating `SomeTrait` with no explicit lifetime bound requires knowing
-   - supertraits of `SomeTrait`
-4. Translating `T::X` (vs `<T as Trait>::X`) requires knowing
-   - bounds on `T`
-   - supertraits of those bounds
-
-So as you can see, in general translating types requires knowing the
-trait hierarchy. But this gets a bit tricky because translating the
-trait hierarchy requires converting the types that appear in trait
-references. One potential saving grace is that in general knowing the
-trait hierarchy is only necessary for shorthands like `T::X` or
-handling omitted lifetime bounds on object types. Therefore, if we are
-lazy about expanding out the trait hierachy, users can sever cycles if
-necessary. Lazy expansion is also needed for type aliases.
-
-This system is not perfect yet. Currently, we "convert" types and
-traits in three phases (note that conversion only affects the types of
-items / enum variants / methods; it does not e.g. compute the types of
-individual expressions):
+The phasing of type conversion is somewhat complicated. There is no
+clear set of phases we can enforce (e.g., converting traits first,
+then types, or something like that) because the user can introduce
+arbitrary interdependencies. So instead we generally convert things
+lazilly and on demand, and include logic that checks for cycles.
+Demand is driven by calls to `AstConv::get_item_type_scheme` or
+`AstConv::lookup_trait_def`.
+
+Currently, we "convert" types and traits in three phases (note that
+conversion only affects the types of items / enum variants / methods;
+it does not e.g. compute the types of individual expressions):
 
 0. Intrinsics
 1. Trait definitions
@@ -64,16 +46,13 @@ trait hierarchy is only necessary for shorthands like `T::X` or
 and invoking an appropriate function (e.g., `trait_def_of_item` or
 `convert_item`). However, it is possible that while converting an
 item, we may need to compute the *type scheme* or *trait definition*
-for other items. This is a kind of shallow conversion that is
-triggered on demand by calls to `AstConv::get_item_type_scheme` or
-`AstConv::lookup_trait_def`. It is possible for cycles to result from
-this (e.g., `type A = B; type B = A;`), in which case astconv
-(currently) reports the error.
+for other items.
 
 There are some shortcomings in this design:
 
-- Cycles through trait definitions (e.g. supertraits) are not currently
-  detected by astconv. (#12511)
+- Before walking the set of supertraits for a given trait, you must
+  call `ensure_super_predicates` on that trait def-id. Otherwise,
+  `lookup_super_predicates` will result in ICEs.
 - Because the type scheme includes defaults, cycles through type
   parameter defaults are illegal even if those defaults are never
   employed. This is not necessarily a bug.
@@ -169,6 +148,7 @@ struct ItemCtxt<'a,'tcx:'a> {
 enum AstConvRequest {
     GetItemTypeScheme(ast::DefId),
     GetTraitDef(ast::DefId),
+    EnsureSuperPredicates(ast::DefId),
     GetTypeParameterBounds(ast::NodeId),
 }
 
@@ -245,7 +225,7 @@ fn cycle_check<F,R>(&self,
                         request: AstConvRequest,
                         code: F)
                         -> Result<R,ErrorReported>
-        where F: FnOnce() -> R
+        where F: FnOnce() -> Result<R,ErrorReported>
     {
         {
             let mut stack = self.stack.borrow_mut();
@@ -263,7 +243,7 @@ fn cycle_check<F,R>(&self,
         let result = code();
 
         self.stack.borrow_mut().pop();
-        Ok(result)
+        result
     }
 
     fn report_cycle(&self,
@@ -284,6 +264,11 @@ fn report_cycle(&self,
                     &format!("the cycle begins when processing `{}`...",
                              ty::item_path_str(tcx, def_id)));
             }
+            AstConvRequest::EnsureSuperPredicates(def_id) => {
+                tcx.sess.note(
+                    &format!("the cycle begins when computing the supertraits of `{}`...",
+                             ty::item_path_str(tcx, def_id)));
+            }
             AstConvRequest::GetTypeParameterBounds(id) => {
                 let def = tcx.type_parameter_def(id);
                 tcx.sess.note(
@@ -301,6 +286,11 @@ fn report_cycle(&self,
                         &format!("...which then requires processing `{}`...",
                                  ty::item_path_str(tcx, def_id)));
                 }
+                AstConvRequest::EnsureSuperPredicates(def_id) => {
+                    tcx.sess.note(
+                        &format!("...which then requires computing the supertraits of `{}`...",
+                                 ty::item_path_str(tcx, def_id)));
+                }
                 AstConvRequest::GetTypeParameterBounds(id) => {
                     let def = tcx.type_parameter_def(id);
                     tcx.sess.note(
@@ -318,6 +308,12 @@ fn report_cycle(&self,
                     &format!("...which then again requires processing `{}`, completing the cycle.",
                              ty::item_path_str(tcx, def_id)));
             }
+            AstConvRequest::EnsureSuperPredicates(def_id) => {
+                tcx.sess.note(
+                    &format!("...which then again requires computing the supertraits of `{}`, \
+                              completing the cycle.",
+                             ty::item_path_str(tcx, def_id)));
+            }
             AstConvRequest::GetTypeParameterBounds(id) => {
                 let def = tcx.type_parameter_def(id);
                 tcx.sess.note(
@@ -327,6 +323,41 @@ fn report_cycle(&self,
             }
         }
     }
+
+    /// Loads the trait def for a given trait, returning ErrorReported if a cycle arises.
+    fn get_trait_def(&self, trait_id: ast::DefId)
+                     -> Rc<ty::TraitDef<'tcx>>
+    {
+        let tcx = self.tcx;
+
+        if trait_id.krate != ast::LOCAL_CRATE {
+            return ty::lookup_trait_def(tcx, trait_id)
+        }
+
+        let item = match tcx.map.get(trait_id.node) {
+            ast_map::NodeItem(item) => item,
+            _ => tcx.sess.bug(&format!("get_trait_def({}): not an item", trait_id.repr(tcx)))
+        };
+
+        trait_def_of_item(self, &*item)
+    }
+
+    /// Ensure that the (transitive) super predicates for
+    /// `trait_def_id` are available. This will report a cycle error
+    /// if a trait `X` (transitively) extends itself in some form.
+    fn ensure_super_predicates(&self, span: Span, trait_def_id: ast::DefId)
+                               -> Result<(), ErrorReported>
+    {
+        self.cycle_check(span, AstConvRequest::EnsureSuperPredicates(trait_def_id), || {
+            let def_ids = ensure_super_predicates_step(self, trait_def_id);
+
+            for def_id in def_ids {
+                try!(self.ensure_super_predicates(span, def_id));
+            }
+
+            Ok(())
+        })
+    }
 }
 
 impl<'a,'tcx> ItemCtxt<'a,'tcx> {
@@ -342,7 +373,7 @@ fn get_item_type_scheme(&self, span: Span, id: ast::DefId)
                             -> Result<ty::TypeScheme<'tcx>, ErrorReported>
     {
         self.ccx.cycle_check(span, AstConvRequest::GetItemTypeScheme(id), || {
-            type_scheme_of_def_id(self.ccx, id)
+            Ok(type_scheme_of_def_id(self.ccx, id))
         })
     }
 
@@ -350,20 +381,49 @@ fn get_trait_def(&self, span: Span, id: ast::DefId)
                      -> Result<Rc<ty::TraitDef<'tcx>>, ErrorReported>
     {
         self.ccx.cycle_check(span, AstConvRequest::GetTraitDef(id), || {
-            get_trait_def(self.ccx, id)
+            Ok(self.ccx.get_trait_def(id))
         })
     }
 
+    fn ensure_super_predicates(&self,
+                               span: Span,
+                               trait_def_id: ast::DefId)
+                               -> Result<(), ErrorReported>
+    {
+        debug!("ensure_super_predicates(trait_def_id={})",
+               trait_def_id.repr(self.tcx()));
+
+        self.ccx.ensure_super_predicates(span, trait_def_id)
+    }
+
+
     fn get_type_parameter_bounds(&self,
                                  span: Span,
                                  node_id: ast::NodeId)
                                  -> Result<Vec<ty::PolyTraitRef<'tcx>>, ErrorReported>
     {
         self.ccx.cycle_check(span, AstConvRequest::GetTypeParameterBounds(node_id), || {
-            self.param_bounds.get_type_parameter_bounds(self, span, node_id)
+            let v = self.param_bounds.get_type_parameter_bounds(self, span, node_id)
+                                     .into_iter()
+                                     .filter_map(|p| p.to_opt_poly_trait_ref())
+                                     .collect();
+            Ok(v)
         })
     }
 
+    fn trait_defines_associated_type_named(&self,
+                                           trait_def_id: ast::DefId,
+                                           assoc_name: ast::Name)
+                                           -> bool
+    {
+        if trait_def_id.krate == ast::LOCAL_CRATE {
+            trait_defines_associated_type_named(self.ccx, trait_def_id.node, assoc_name)
+        } else {
+            let trait_def = ty::lookup_trait_def(self.tcx(), trait_def_id);
+            trait_def.associated_type_names.contains(&assoc_name)
+        }
+    }
+
     fn ty_infer(&self, span: Span) -> Ty<'tcx> {
         span_err!(self.tcx().sess, span, E0121,
                   "the type placeholder `_` is not allowed within types on item signatures");
@@ -387,7 +447,7 @@ fn get_type_parameter_bounds(&self,
                                  astconv: &AstConv<'tcx>,
                                  span: Span,
                                  node_id: ast::NodeId)
-                                 -> Vec<ty::PolyTraitRef<'tcx>>;
+                                 -> Vec<ty::Predicate<'tcx>>;
 }
 
 /// Find bounds from both elements of the tuple.
@@ -398,7 +458,7 @@ fn get_type_parameter_bounds(&self,
                                  astconv: &AstConv<'tcx>,
                                  span: Span,
                                  node_id: ast::NodeId)
-                                 -> Vec<ty::PolyTraitRef<'tcx>>
+                                 -> Vec<ty::Predicate<'tcx>>
     {
         let mut v = self.0.get_type_parameter_bounds(astconv, span, node_id);
         v.extend(self.1.get_type_parameter_bounds(astconv, span, node_id).into_iter());
@@ -412,7 +472,7 @@ fn get_type_parameter_bounds(&self,
                                  _astconv: &AstConv<'tcx>,
                                  _span: Span,
                                  _node_id: ast::NodeId)
-                                 -> Vec<ty::PolyTraitRef<'tcx>>
+                                 -> Vec<ty::Predicate<'tcx>>
     {
         Vec::new()
     }
@@ -426,29 +486,28 @@ fn get_type_parameter_bounds(&self,
                                  astconv: &AstConv<'tcx>,
                                  _span: Span,
                                  node_id: ast::NodeId)
-                                 -> Vec<ty::PolyTraitRef<'tcx>>
+                                 -> Vec<ty::Predicate<'tcx>>
     {
         let def = astconv.tcx().type_parameter_def(node_id);
 
         self.predicates
             .iter()
-            .filter_map(|predicate| {
-                match *predicate {
+            .filter(|predicate| {
+                match **predicate {
                     ty::Predicate::Trait(ref data) => {
-                        if data.0.self_ty().is_param(def.space, def.index) {
-                            Some(data.to_poly_trait_ref())
-                        } else {
-                            None
-                        }
+                        data.skip_binder().self_ty().is_param(def.space, def.index)
+                    }
+                    ty::Predicate::TypeOutlives(ref data) => {
+                        data.skip_binder().0.is_param(def.space, def.index)
                     }
                     ty::Predicate::Equate(..) |
                     ty::Predicate::RegionOutlives(..) |
-                    ty::Predicate::TypeOutlives(..) |
                     ty::Predicate::Projection(..) => {
-                        None
+                        false
                     }
                 }
             })
+            .cloned()
             .collect()
     }
 }
@@ -462,7 +521,7 @@ fn get_type_parameter_bounds(&self,
                                  astconv: &AstConv<'tcx>,
                                  _: Span,
                                  node_id: ast::NodeId)
-                                 -> Vec<ty::PolyTraitRef<'tcx>>
+                                 -> Vec<ty::Predicate<'tcx>>
     {
         // In the AST, bounds can derive from two places. Either
         // written inline like `<T:Foo>` or in a where clause like
@@ -476,7 +535,7 @@ fn get_type_parameter_bounds(&self,
                 .iter()
                 .filter(|p| p.id == node_id)
                 .flat_map(|p| p.bounds.iter())
-                .filter_map(|b| poly_trait_ref_from_bound(astconv, ty, b, &mut Vec::new()));
+                .flat_map(|b| predicates_from_bound(astconv, ty, b).into_iter());
 
         let from_where_clauses =
             self.where_clause
@@ -488,7 +547,7 @@ fn get_type_parameter_bounds(&self,
                 })
                 .filter(|bp| is_param(astconv.tcx(), &bp.bounded_ty, node_id))
                 .flat_map(|bp| bp.bounds.iter())
-                .filter_map(|b| poly_trait_ref_from_bound(astconv, ty, b, &mut Vec::new()));
+                .flat_map(|b| predicates_from_bound(astconv, ty, b).into_iter());
 
         from_ty_params.chain(from_where_clauses).collect()
     }
@@ -505,10 +564,15 @@ fn is_param<'tcx>(tcx: &ty::ctxt<'tcx>,
 {
     if let ast::TyPath(None, _) = ast_ty.node {
         let path_res = tcx.def_map.borrow()[ast_ty.id];
-        if let def::DefTyParam(_, _, def_id, _) = path_res.base_def {
-            path_res.depth == 0 && def_id == local_def(param_id)
-        } else {
-            false
+        match path_res.base_def {
+            def::DefSelfTy(node_id) =>
+                path_res.depth == 0 && node_id == param_id,
+
+            def::DefTyParam(_, _, def_id, _) =>
+                path_res.depth == 0 && def_id == local_def(param_id),
+
+            _ =>
+                false,
         }
     } else {
         false
@@ -777,9 +841,10 @@ fn convert_methods<'a,'tcx,'i,I>(ccx: &CrateCtxt<'a, 'tcx>,
                                  rcvr_visibility: ast::Visibility)
                                  where I: Iterator<Item=&'i ast::Method>
 {
-    debug!("convert_methods(untransformed_rcvr_ty={}, rcvr_ty_generics={})",
+    debug!("convert_methods(untransformed_rcvr_ty={}, rcvr_ty_generics={}, rcvr_ty_predicates={})",
            untransformed_rcvr_ty.repr(ccx.tcx),
-           rcvr_ty_generics.repr(ccx.tcx));
+           rcvr_ty_generics.repr(ccx.tcx),
+           rcvr_ty_predicates.repr(ccx.tcx));
 
     let tcx = ccx.tcx;
     let mut seen_methods = FnvHashSet();
@@ -914,7 +979,7 @@ fn convert_item(ccx: &CrateCtxt, it: &ast::Item) {
                                                            None,
                                                            None);
 
-            ty::record_default_trait_implementation(tcx, trait_ref.def_id, local_def(it.id))
+            ty::record_trait_has_default_impl(tcx, trait_ref.def_id);
         }
         ast::ItemImpl(_, _,
                       ref generics,
@@ -1023,6 +1088,8 @@ fn convert_item(ccx: &CrateCtxt, it: &ast::Item) {
         },
         ast::ItemTrait(_, _, _, ref trait_items) => {
             let trait_def = trait_def_of_item(ccx, it);
+            let _: Result<(), ErrorReported> = // any error is already reported, can ignore
+                ccx.ensure_super_predicates(it.span, local_def(it.id));
             convert_trait_predicates(ccx, it);
             let trait_predicates = ty::lookup_predicates(ccx.tcx, local_def(it.id));
 
@@ -1168,22 +1235,89 @@ fn convert_struct<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
     }
 }
 
-fn get_trait_def<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
-                           trait_id: ast::DefId)
-                           -> Rc<ty::TraitDef<'tcx>> {
+/// Ensures that the super-predicates of the trait with def-id
+/// trait_def_id are converted and stored. This does NOT ensure that
+/// the transitive super-predicates are converted; that is the job of
+/// the `ensure_super_predicates()` method in the `AstConv` impl
+/// above. Returns a list of trait def-ids that must be ensured as
+/// well to guarantee that the transitive superpredicates are
+/// converted.
+fn ensure_super_predicates_step(ccx: &CrateCtxt,
+                                trait_def_id: ast::DefId)
+                                -> Vec<ast::DefId>
+{
     let tcx = ccx.tcx;
 
-    if trait_id.krate != ast::LOCAL_CRATE {
-        return ty::lookup_trait_def(tcx, trait_id)
-    }
+    debug!("ensure_super_predicates_step(trait_def_id={})", trait_def_id.repr(tcx));
 
-    match tcx.map.get(trait_id.node) {
-        ast_map::NodeItem(item) => trait_def_of_item(ccx, &*item),
-        _ => {
-            tcx.sess.bug(&format!("get_trait_def({}): not an item",
-                                  trait_id.node))
-        }
+    if trait_def_id.krate != ast::LOCAL_CRATE {
+        // If this trait comes from an external crate, then all of the
+        // supertraits it may depend on also must come from external
+        // crates, and hence all of them already have their
+        // super-predicates "converted" (and available from crate
+        // meta-data), so there is no need to transitively test them.
+        return Vec::new();
     }
+
+    let superpredicates = tcx.super_predicates.borrow().get(&trait_def_id).cloned();
+    let superpredicates = superpredicates.unwrap_or_else(|| {
+        let trait_node_id = trait_def_id.node;
+
+        let item = match ccx.tcx.map.get(trait_node_id) {
+            ast_map::NodeItem(item) => item,
+            _ => ccx.tcx.sess.bug(&format!("trait_node_id {} is not an item", trait_node_id))
+        };
+
+        let (generics, bounds) = match item.node {
+            ast::ItemTrait(_, ref generics, ref supertraits, _) => (generics, supertraits),
+            _ => tcx.sess.span_bug(item.span,
+                                   "ensure_super_predicates_step invoked on non-trait"),
+        };
+
+        // In-scope when converting the superbounds for `Trait` are
+        // that `Self:Trait` as well as any bounds that appear on the
+        // generic types:
+        let trait_def = trait_def_of_item(ccx, item);
+        let self_predicate = ty::GenericPredicates {
+            predicates: VecPerParamSpace::new(vec![],
+                                              vec![trait_def.trait_ref.as_predicate()],
+                                              vec![])
+        };
+        let scope = &(generics, &self_predicate);
+
+        // Convert the bounds that follow the colon, e.g. `Bar+Zed` in `trait Foo : Bar+Zed`.
+        let self_param_ty = ty::mk_self_type(tcx);
+        let superbounds1 = compute_bounds(&ccx.icx(scope), self_param_ty, bounds,
+                                          SizedByDefault::No, item.span);
+        let superbounds1 = ty::predicates(tcx, self_param_ty, &superbounds1);
+
+        // Convert any explicit superbounds in the where clause,
+        // e.g. `trait Foo where Self : Bar`:
+        let superbounds2 = generics.get_type_parameter_bounds(&ccx.icx(scope), item.span, item.id);
+
+        // Combine the two lists to form the complete set of superbounds:
+        let superbounds = superbounds1.into_iter().chain(superbounds2.into_iter()).collect();
+        let superpredicates = ty::GenericPredicates {
+            predicates: VecPerParamSpace::new(superbounds, vec![], vec![])
+        };
+        debug!("superpredicates for trait {} = {}",
+               local_def(item.id).repr(ccx.tcx),
+               superpredicates.repr(ccx.tcx));
+
+        tcx.super_predicates.borrow_mut().insert(trait_def_id, superpredicates.clone());
+
+        superpredicates
+    });
+
+    let def_ids: Vec<_> = superpredicates.predicates
+                                         .iter()
+                                         .filter_map(|p| p.to_opt_poly_trait_ref())
+                                         .map(|tr| tr.def_id())
+                                         .collect();
+
+    debug!("ensure_super_predicates_step: def_ids={}", def_ids.repr(tcx));
+
+    def_ids
 }
 
 fn trait_def_of_item<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
@@ -1197,18 +1331,9 @@ fn trait_def_of_item<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
         return def.clone();
     }
 
-    let (unsafety, generics, bounds, items) = match it.node {
-        ast::ItemTrait(unsafety,
-                       ref generics,
-                       ref supertraits,
-                       ref items) => {
-            (unsafety, generics, supertraits, items)
-        }
-        ref s => {
-            tcx.sess.span_bug(
-                it.span,
-                &format!("trait_def_of_item invoked on {:?}", s));
-        }
+    let (unsafety, generics, items) = match it.node {
+        ast::ItemTrait(unsafety, ref generics, _, ref items) => (unsafety, generics, items),
+        _ => tcx.sess.span_bug(it.span, "trait_def_of_item invoked on non-trait"),
     };
 
     let paren_sugar = ty::has_attr(tcx, def_id, "rustc_paren_sugar");
@@ -1217,7 +1342,7 @@ fn trait_def_of_item<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
             it.span,
             "the `#[rustc_paren_sugar]` attribute is a temporary means of controlling \
              which traits can use parenthetical notation");
-        span_help!(ccx.tcx.sess, it.span,
+        fileline_help!(ccx.tcx.sess, it.span,
                    "add `#![feature(unboxed_closures)]` to \
                     the crate attributes to use it");
     }
@@ -1226,15 +1351,6 @@ fn trait_def_of_item<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
 
     let ty_generics = ty_generics_for_trait(ccx, it.id, substs, generics);
 
-    let self_param_ty = ty::ParamTy::for_self().to_ty(ccx.tcx);
-
-    // supertraits:
-    let bounds = compute_bounds(&ccx.icx(generics),
-                                self_param_ty,
-                                bounds,
-                                SizedByDefault::No,
-                                it.span);
-
     let associated_type_names: Vec<_> =
         items.iter()
              .filter_map(|item| {
@@ -1254,7 +1370,6 @@ fn trait_def_of_item<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
         paren_sugar: paren_sugar,
         unsafety: unsafety,
         generics: ty_generics,
-        bounds: bounds,
         trait_ref: trait_ref,
         associated_type_names: associated_type_names,
     });
@@ -1296,6 +1411,30 @@ fn mk_trait_substs<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>,
     }
 }
 
+fn trait_defines_associated_type_named(ccx: &CrateCtxt,
+                                       trait_node_id: ast::NodeId,
+                                       assoc_name: ast::Name)
+                                       -> bool
+{
+    let item = match ccx.tcx.map.get(trait_node_id) {
+        ast_map::NodeItem(item) => item,
+        _ => ccx.tcx.sess.bug(&format!("trait_node_id {} is not an item", trait_node_id))
+    };
+
+    let trait_items = match item.node {
+        ast::ItemTrait(_, _, _, ref trait_items) => trait_items,
+        _ => ccx.tcx.sess.bug(&format!("trait_node_id {} is not a trait", trait_node_id))
+    };
+
+    trait_items.iter()
+               .any(|trait_item| {
+                   match *trait_item {
+                       ast::TypeTraitItem(ref t) => t.ty_param.ident.name == assoc_name,
+                       ast::RequiredMethod(..) | ast::ProvidedMethod(..) => false,
+                   }
+               })
+}
+
 fn convert_trait_predicates<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &ast::Item) {
     let tcx = ccx.tcx;
     let trait_def = trait_def_of_item(ccx, it);
@@ -1311,19 +1450,14 @@ fn convert_trait_predicates<'a, 'tcx>(ccx: &CrateCtxt<'a, 'tcx>, it: &ast::Item)
         }
     };
 
-    let self_param_ty = ty::ParamTy::for_self().to_ty(ccx.tcx);
-
-    let super_predicates = ty::predicates(ccx.tcx, self_param_ty, &trait_def.bounds);
+    let super_predicates = ty::lookup_super_predicates(ccx.tcx, def_id);
 
     // `ty_generic_predicates` below will consider the bounds on the type
     // parameters (including `Self`) and the explicit where-clauses,
     // but to get the full set of predicates on a trait we need to add
     // in the supertrait bounds and anything declared on the
     // associated types.
-    let mut base_predicates =
-        ty::GenericPredicates {
-            predicates: VecPerParamSpace::new(super_predicates, vec![], vec![])
-        };
+    let mut base_predicates = super_predicates;
 
     // Add in a predicate that `Self:Trait` (where `Trait` is the
     // current trait).  This is needed for builtin bounds.
@@ -1456,8 +1590,8 @@ fn compute_type_scheme_of_item<'a,'tcx>(ccx: &CrateCtxt<'a,'tcx>,
         ast::ItemMac(..) => {
             tcx.sess.span_bug(
                 it.span,
-                format!("compute_type_scheme_of_item: unexpected item type: {:?}",
-                        it.node).as_slice());
+                &format!("compute_type_scheme_of_item: unexpected item type: {:?}",
+                         it.node));
         }
     }
 }
@@ -1953,7 +2087,7 @@ fn from_predicates<'a,'tcx>(ccx: &CrateCtxt<'a,'tcx>,
     }
 }
 
-enum SizedByDefault { Yes, No }
+enum SizedByDefault { Yes, No, }
 
 /// Translate the AST's notion of ty param bounds (which are an enum consisting of a newtyped Ty or
 /// a region) to ty's notion of ty param bounds, which can either be user-defined traits, or the
@@ -1975,11 +2109,6 @@ fn compute_bounds<'tcx>(astconv: &AstConv<'tcx>,
                           &mut param_bounds.builtin_bounds,
                           ast_bounds,
                           span);
-
-        check_bounds_compatible(astconv,
-                                param_ty,
-                                &param_bounds,
-                                span);
     }
 
     param_bounds.trait_bounds.sort_by(|a,b| a.def_id().cmp(&b.def_id()));
@@ -1987,48 +2116,32 @@ fn compute_bounds<'tcx>(astconv: &AstConv<'tcx>,
     param_bounds
 }
 
-fn check_bounds_compatible<'tcx>(astconv: &AstConv<'tcx>,
-                                 param_ty: Ty<'tcx>,
-                                 param_bounds: &ty::ParamBounds<'tcx>,
-                                 span: Span) {
-    let tcx = astconv.tcx();
-    if !param_bounds.builtin_bounds.contains(&ty::BoundSized) {
-        ty::each_bound_trait_and_supertraits(
-            tcx,
-            &param_bounds.trait_bounds,
-            |trait_ref| {
-                match astconv.get_trait_def(span, trait_ref.def_id()) {
-                    Ok(trait_def) => {
-                        if trait_def.bounds.builtin_bounds.contains(&ty::BoundSized) {
-                            span_err!(tcx.sess, span, E0129,
-                                      "incompatible bounds on `{}`, \
-                                        bound `{}` does not allow unsized type",
-                                      param_ty.user_string(tcx),
-                                      trait_ref.user_string(tcx));
-                        }
-                    }
-                    Err(ErrorReported) => { }
-                }
-                true
-            });
-    }
-}
-
-/// Converts a specific TyParamBound from the AST into the
-/// appropriate poly-trait-reference.
-fn poly_trait_ref_from_bound<'tcx>(astconv: &AstConv<'tcx>,
-                                   param_ty: Ty<'tcx>,
-                                   bound: &ast::TyParamBound,
-                                   projections: &mut Vec<ty::PolyProjectionPredicate<'tcx>>)
-                                   -> Option<ty::PolyTraitRef<'tcx>>
+/// Converts a specific TyParamBound from the AST into a set of
+/// predicates that apply to the self-type. A vector is returned
+/// because this can be anywhere from 0 predicates (`T:?Sized` adds no
+/// predicates) to 1 (`T:Foo`) to many (`T:Bar<X=i32>` adds `T:Bar`
+/// and `<T as Bar>::X == i32`).
+fn predicates_from_bound<'tcx>(astconv: &AstConv<'tcx>,
+                               param_ty: Ty<'tcx>,
+                               bound: &ast::TyParamBound)
+                               -> Vec<ty::Predicate<'tcx>>
 {
     match *bound {
         ast::TraitTyParamBound(ref tr, ast::TraitBoundModifier::None) => {
-            Some(conv_poly_trait_ref(astconv, param_ty, tr, projections))
+            let mut projections = Vec::new();
+            let pred = conv_poly_trait_ref(astconv, param_ty, tr, &mut projections);
+            projections.into_iter()
+                       .map(|p| p.as_predicate())
+                       .chain(Some(pred.as_predicate()).into_iter())
+                       .collect()
         }
-        ast::TraitTyParamBound(_, ast::TraitBoundModifier::Maybe) |
-        ast::RegionTyParamBound(_) => {
-            None
+        ast::RegionTyParamBound(ref lifetime) => {
+            let region = ast_region_to_region(astconv.tcx(), lifetime);
+            let pred = ty::Binder(ty::OutlivesPredicate(param_ty, region));
+            vec![ty::Predicate::TypeOutlives(pred)]
+        }
+        ast::TraitTyParamBound(_, ast::TraitBoundModifier::Maybe) => {
+            Vec::new()
         }
     }
 }
index 3bd15fbc7dbea774fb55ebad140bd1ab85fed0ff..03fa269ccf82908651b7056cbba5ed3f63fa1078 100644 (file)
     E0250, // expected constant expr for array length
     E0318, // can't create default impls for traits outside their crates
     E0319, // trait impls for defaulted traits allowed just for structs/enums
-    E0320  // recursive overflow during dropck
+    E0320, // recursive overflow during dropck
+    E0321, // extended coherence rules for defaulted traits violated
+    E0322  // cannot implement Sized explicitly
 }
 
 __build_diagnostic_array! { DIAGNOSTICS }
index 78dd66c8e7dbbd02e80bc8f197f2d014a2bf990e..bbc64a54013b717b7dc11e8287f9da17180b425c 100644 (file)
@@ -62,7 +62,8 @@
 This API is completely unstable and subject to change.
 
 */
-
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustc_typeck"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
index 1fba4a21ccd376a61ab08fbc52609e1cb9b32b50..9b27128ce2ffd5409b40b2694187031b54475684 100644 (file)
@@ -644,9 +644,9 @@ fn visit_item(&mut self, item: &ast::Item) {
 
             ast::ItemTrait(..) => {
                 let trait_def = ty::lookup_trait_def(tcx, did);
-                let predicates = ty::predicates(tcx, ty::mk_self_type(tcx), &trait_def.bounds);
+                let predicates = ty::lookup_super_predicates(tcx, did);
                 self.add_constraints_from_predicates(&trait_def.generics,
-                                                     &predicates,
+                                                     predicates.predicates.as_slice(),
                                                      self.covariant);
 
                 let trait_items = ty::trait_items(tcx, did);
index 2bb4424822a4749c5b58b3537fee5d09cb860823..db41bf9fee329d9e36e65cf9f183bc1ec7a5a524 100644 (file)
@@ -165,14 +165,12 @@ pub fn build_external_trait(cx: &DocContext, tcx: &ty::ctxt,
             _ => unreachable!()
         }
     });
-    let trait_def = ty::lookup_trait_def(tcx, did);
     let predicates = ty::lookup_predicates(tcx, did);
-    let bounds = trait_def.bounds.clean(cx);
     clean::Trait {
         unsafety: def.unsafety,
         generics: (&def.generics, &predicates, subst::TypeSpace).clean(cx),
         items: items.collect(),
-        bounds: bounds,
+        bounds: vec![], // supertraits can be found in the list of predicates
     }
 }
 
index 36d39fa58ba7e5ec7e23a8bcc5cc2c595e59f341..c39451b15ada5c8334e9d93a50604008598caaca 100644 (file)
@@ -49,7 +49,7 @@
 
 use std::rc::Rc;
 use std::u32;
-use std::old_path::Path as FsPath; // Conflicts with Path struct
+use std::path::PathBuf;
 
 use core::DocContext;
 use doctree;
@@ -118,7 +118,7 @@ fn clean(&self, cx: &DocContext) -> Vec<U> {
 #[derive(Clone, RustcEncodable, RustcDecodable, Debug)]
 pub struct Crate {
     pub name: String,
-    pub src: FsPath,
+    pub src: PathBuf,
     pub module: Option<Item>,
     pub externs: Vec<(ast::CrateNum, ExternalCrate)>,
     pub primitives: Vec<PrimitiveType>,
@@ -191,7 +191,7 @@ fn clean(&self, cx: &DocContext) -> Crate {
 
         let src = match cx.input {
             Input::File(ref path) => path.clone(),
-            Input::Str(_) => FsPath::new("") // FIXME: this is wrong
+            Input::Str(_) => PathBuf::new("") // FIXME: this is wrong
         };
 
         Crate {
index 942aec7d22f2c0bff99a4faaab2fce803e7cb477..6cfe7a33dd4f366b285c4991f29f755dabec38d5 100644 (file)
@@ -8,7 +8,12 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-use std::{old_io, str};
+use std::fs::File;
+use std::io::prelude::*;
+use std::io;
+use std::old_io;
+use std::path::{PathBuf, Path};
+use std::str;
 
 #[derive(Clone)]
 pub struct ExternalHtml{
@@ -33,16 +38,17 @@ pub fn load(in_header: &[String], before_content: &[String], after_content: &[St
     }
 }
 
-pub fn load_string(input: &Path) -> old_io::IoResult<Option<String>> {
-    let mut f = try!(old_io::File::open(input));
-    let d = try!(f.read_to_end());
+pub fn load_string(input: &Path) -> io::Result<Option<String>> {
+    let mut f = try!(File::open(input));
+    let mut d = Vec::new();
+    try!(f.read_to_end(&mut d));
     Ok(str::from_utf8(&d).map(|s| s.to_string()).ok())
 }
 
 macro_rules! load_or_return {
     ($input: expr, $cant_read: expr, $not_utf8: expr) => {
         {
-            let input = Path::new($input);
+            let input = PathBuf::new($input);
             match ::externalfiles::load_string(&input) {
                 Err(e) => {
                     let _ = writeln!(&mut old_io::stderr(),
index 6b2676eca3d026ef4061ca442ab265236c7f7402..51c58861b4b252b66ea31d3b4d9a78de7a3e45ae 100644 (file)
@@ -20,7 +20,9 @@
 
 #[cfg(unix)]
 mod imp {
-    use std::ffi::CString;
+    use std::ffi::{AsOsStr, CString};
+    use std::os::unix::prelude::*;
+    use std::path::Path;
     use libc;
     use std::os as stdos;
 
@@ -114,7 +116,7 @@ pub struct Lock {
 
     impl Lock {
         pub fn new(p: &Path) -> Lock {
-            let buf = CString::new(p.as_vec()).unwrap();
+            let buf = CString::new(p.as_os_str().as_bytes()).unwrap();
             let fd = unsafe {
                 libc::open(buf.as_ptr(), libc::O_RDWR | libc::O_CREAT,
                            libc::S_IRWXU)
@@ -163,11 +165,14 @@ fn drop(&mut self) {
 #[cfg(windows)]
 mod imp {
     use libc;
+    use std::ffi::AsOsStr;
     use std::mem;
+    use std::os::windows::prelude::*;
     use std::os;
+    use std::path::Path;
     use std::ptr;
 
-    static LOCKFILE_EXCLUSIVE_LOCK: libc::DWORD = 0x00000002;
+    const LOCKFILE_EXCLUSIVE_LOCK: libc::DWORD = 0x00000002;
 
     #[allow(non_snake_case)]
     extern "system" {
@@ -190,7 +195,7 @@ pub struct Lock {
 
     impl Lock {
         pub fn new(p: &Path) -> Lock {
-            let mut p_16: Vec<u16> = p.as_str().unwrap().utf16_units().collect();
+            let mut p_16: Vec<_> = p.as_os_str().encode_wide().collect();
             p_16.push(0);
             let handle = unsafe {
                 libc::CreateFileW(p_16.as_ptr(),
index c537e370723d7ca2526e0fc2cbbac25c9f7eeb19..3acd17dedd59d986503814984c474860e70d2f78 100644 (file)
@@ -9,7 +9,8 @@
 // except according to those terms.
 
 use std::fmt;
-use std::old_io;
+use std::io::prelude::*;
+use std::io;
 
 use externalfiles::ExternalHtml;
 
@@ -31,8 +32,8 @@ pub struct Page<'a> {
 }
 
 pub fn render<T: fmt::Display, S: fmt::Display>(
-    dst: &mut old_io::Writer, layout: &Layout, page: &Page, sidebar: &S, t: &T)
-    -> old_io::IoResult<()>
+    dst: &mut io::Write, layout: &Layout, page: &Page, sidebar: &S, t: &T)
+    -> io::Result<()>
 {
     write!(dst,
 r##"<!DOCTYPE html>
@@ -159,7 +160,7 @@ pub fn render<T: fmt::Display, S: fmt::Display>(
     )
 }
 
-pub fn redirect(dst: &mut old_io::Writer, url: &str) -> old_io::IoResult<()> {
+pub fn redirect(dst: &mut io::Write, url: &str) -> io::Result<()> {
     // <script> triggers a redirect before refresh, so this is fine.
     write!(dst,
 r##"<!DOCTYPE html>
index 735487611dc50d522a13a2ae0ebf4b67e0fc50e6..46c7a701954859dfdf6691b62bb76fc351fd42f0 100644 (file)
 use std::collections::{HashMap, HashSet};
 use std::default::Default;
 use std::fmt;
-use std::old_io::fs::PathExtensions;
-use std::old_io::{fs, File, BufferedWriter, BufferedReader};
-use std::old_io;
+use std::fs::{self, File};
+use std::io::prelude::*;
+use std::io::{self, BufWriter, BufReader};
 use std::iter::repeat;
+use std::path::{PathBuf, Path};
 use std::str;
 use std::sync::Arc;
 
 use html::layout;
 use html::markdown::Markdown;
 use html::markdown;
-use html::escape::Escape;
 use stability_summary;
 
 /// A pair of name and its optional document.
-#[derive(Clone, Eq, Ord, PartialEq, PartialOrd)]
-pub struct NameDoc(String, Option<String>);
+pub type NameDoc = (String, Option<String>);
 
 /// Major driving force in all rustdoc rendering. This contains information
 /// about where in the tree-like hierarchy rendering is occurring and controls
@@ -89,19 +88,13 @@ pub struct Context {
     pub root_path: String,
     /// The path to the crate root source minus the file name.
     /// Used for simplifying paths to the highlighted source code files.
-    pub src_root: Path,
+    pub src_root: PathBuf,
     /// The current destination folder of where HTML artifacts should be placed.
     /// This changes as the context descends into the module hierarchy.
-    pub dst: Path,
+    pub dst: PathBuf,
     /// This describes the layout of each page, and is not modified after
     /// creation of the context (contains info like the favicon and added html).
     pub layout: layout::Layout,
-    /// This map is a list of what should be displayed on the sidebar of the
-    /// current page. The key is the section header (traits, modules,
-    /// functions), and the value is the list of containers belonging to this
-    /// header. This map will change depending on the surrounding context of the
-    /// page.
-    pub sidebar: HashMap<String, Vec<NameDoc>>,
     /// This flag indicates whether [src] links should be generated or not. If
     /// the source files are present in the html rendering, then this will be
     /// `true`.
@@ -220,7 +213,7 @@ struct SourceCollector<'a> {
     /// Processed source-file paths
     seen: HashSet<String>,
     /// Root destination to place all HTML output into
-    dst: Path,
+    dst: PathBuf,
 }
 
 /// Wrapper struct to render the source code of a file. This will do things like
@@ -257,15 +250,18 @@ struct IndexItem {
 /// Generates the documentation for `crate` into the directory `dst`
 pub fn run(mut krate: clean::Crate,
            external_html: &ExternalHtml,
-           dst: Path,
-           passes: HashSet<String>) -> old_io::IoResult<()> {
+           dst: PathBuf,
+           passes: HashSet<String>) -> io::Result<()> {
+    let src_root = match krate.src.parent() {
+        Some(p) => p.to_path_buf(),
+        None => PathBuf::new(""),
+    };
     let mut cx = Context {
         dst: dst,
-        src_root: krate.src.dir_path(),
+        src_root: src_root,
         passes: passes,
         current: Vec::new(),
         root_path: String::new(),
-        sidebar: HashMap::new(),
         layout: layout::Layout {
             logo: "".to_string(),
             favicon: "".to_string(),
@@ -392,7 +388,7 @@ pub fn run(mut krate: clean::Crate,
     cx.krate(krate, summary)
 }
 
-fn build_index(krate: &clean::Crate, cache: &mut Cache) -> old_io::IoResult<String> {
+fn build_index(krate: &clean::Crate, cache: &mut Cache) -> io::Result<String> {
     // Build the search index from the collected metadata
     let mut nodeid_to_pathid = HashMap::new();
     let mut pathid_to_nodeid = Vec::new();
@@ -437,7 +433,7 @@ fn build_index(krate: &clean::Crate, cache: &mut Cache) -> old_io::IoResult<Stri
     }
 
     // Collect the index into a string
-    let mut w = Vec::new();
+    let mut w = io::Cursor::new(Vec::new());
     try!(write!(&mut w, r#"searchIndex['{}'] = {{"items":["#, krate.name));
 
     let mut lastpath = "".to_string();
@@ -480,13 +476,13 @@ fn build_index(krate: &clean::Crate, cache: &mut Cache) -> old_io::IoResult<Stri
 
     try!(write!(&mut w, "]}};"));
 
-    Ok(String::from_utf8(w).unwrap())
+    Ok(String::from_utf8(w.into_inner()).unwrap())
 }
 
 fn write_shared(cx: &Context,
                 krate: &clean::Crate,
                 cache: &Cache,
-                search_index: String) -> old_io::IoResult<()> {
+                search_index: String) -> io::Result<()> {
     // Write out the shared files. Note that these are shared among all rustdoc
     // docs placed in the output directory, so this needs to be a synchronized
     // operation with respect to all other rustdocs running around.
@@ -518,10 +514,10 @@ fn write_shared(cx: &Context,
                include_bytes!("static/SourceCodePro-Semibold.woff")));
 
     fn collect(path: &Path, krate: &str,
-               key: &str) -> old_io::IoResult<Vec<String>> {
+               key: &str) -> io::Result<Vec<String>> {
         let mut ret = Vec::new();
         if path.exists() {
-            for line in BufferedReader::new(File::open(path)).lines() {
+            for line in BufReader::new(try!(File::open(path))).lines() {
                 let line = try!(line);
                 if !line.starts_with(key) {
                     continue
@@ -567,14 +563,14 @@ fn collect(path: &Path, krate: &str,
             mydst.push(part);
             try!(mkdir(&mydst));
         }
-        mydst.push(format!("{}.{}.js",
-                           remote_item_type.to_static_str(),
-                           remote_path[remote_path.len() - 1]));
+        mydst.push(&format!("{}.{}.js",
+                            remote_item_type.to_static_str(),
+                            remote_path[remote_path.len() - 1]));
         let all_implementors = try!(collect(&mydst, &krate.name,
                                             "implementors"));
 
-        try!(mkdir(&mydst.dir_path()));
-        let mut f = BufferedWriter::new(try!(File::create(&mydst)));
+        try!(mkdir(mydst.parent().unwrap()));
+        let mut f = BufWriter::new(try!(File::create(&mydst)));
         try!(writeln!(&mut f, "(function() {{var implementors = {{}};"));
 
         for implementor in &all_implementors {
@@ -606,7 +602,7 @@ fn collect(path: &Path, krate: &str,
 }
 
 fn render_sources(cx: &mut Context,
-                  krate: clean::Crate) -> old_io::IoResult<clean::Crate> {
+                  krate: clean::Crate) -> io::Result<clean::Crate> {
     info!("emitting source files");
     let dst = cx.dst.join("src");
     try!(mkdir(&dst));
@@ -624,15 +620,15 @@ fn render_sources(cx: &mut Context,
 
 /// Writes the entire contents of a string to a destination, not attempting to
 /// catch any errors.
-fn write(dst: Path, contents: &[u8]) -> old_io::IoResult<()> {
-    File::create(&dst).write_all(contents)
+fn write(dst: PathBuf, contents: &[u8]) -> io::Result<()> {
+    try!(File::create(&dst)).write_all(contents)
 }
 
 /// Makes a directory on the filesystem, failing the task if an error occurs and
 /// skipping if the directory already exists.
-fn mkdir(path: &Path) -> old_io::IoResult<()> {
+fn mkdir(path: &Path) -> io::Result<()> {
     if !path.exists() {
-        fs::mkdir(path, old_io::USER_RWX)
+        fs::create_dir(path)
     } else {
         Ok(())
     }
@@ -648,21 +644,17 @@ fn shortty(item: &clean::Item) -> ItemType {
 /// static HTML tree.
 // FIXME (#9639): The closure should deal with &[u8] instead of &str
 // FIXME (#9639): This is too conservative, rejecting non-UTF-8 paths
-fn clean_srcpath<F>(src_root: &Path, src: &[u8], mut f: F) where
+fn clean_srcpath<F>(src_root: &Path, p: &Path, mut f: F) where
     F: FnMut(&str),
 {
-    let p = Path::new(src);
-
     // make it relative, if possible
-    let p = p.path_relative_from(src_root).unwrap_or(p);
+    let p = p.relative_from(src_root).unwrap_or(p);
 
-    if p.as_vec() != b"." {
-        for c in p.str_components().map(|x|x.unwrap()) {
-            if ".." == c {
-                f("up");
-            } else {
-                f(c)
-            }
+    for c in p.iter().map(|x| x.to_str().unwrap()) {
+        if ".." == c {
+            f("up");
+        } else {
+            f(c)
         }
     }
 }
@@ -733,13 +725,14 @@ fn fold_item(&mut self, item: clean::Item) -> Option<clean::Item> {
 
 impl<'a> SourceCollector<'a> {
     /// Renders the given filename into its corresponding HTML source file.
-    fn emit_source(&mut self, filename: &str) -> old_io::IoResult<()> {
-        let p = Path::new(filename);
+    fn emit_source(&mut self, filename: &str) -> io::Result<()> {
+        let p = PathBuf::new(filename);
 
         // If we couldn't open this file, then just returns because it
         // probably means that it's some standard library macro thing and we
         // can't have the source to it anyway.
-        let contents = match File::open(&p).read_to_end() {
+        let mut contents = Vec::new();
+        match File::open(&p).and_then(|mut f| f.read_to_end(&mut contents)) {
             Ok(r) => r,
             // macros from other libraries get special filenames which we can
             // safely ignore
@@ -759,18 +752,20 @@ fn emit_source(&mut self, filename: &str) -> old_io::IoResult<()> {
         // Create the intermediate directories
         let mut cur = self.dst.clone();
         let mut root_path = String::from_str("../../");
-        clean_srcpath(&self.cx.src_root, p.dirname(), |component| {
+        clean_srcpath(&self.cx.src_root, &p, |component| {
             cur.push(component);
             mkdir(&cur).unwrap();
             root_path.push_str("../");
         });
 
-        let mut fname = p.filename().expect("source has no filename").to_vec();
-        fname.extend(".html".bytes());
-        cur.push(fname);
-        let mut w = BufferedWriter::new(try!(File::create(&cur)));
+        let mut fname = p.file_name().expect("source has no filename")
+                         .to_os_string();
+        fname.push(".html");
+        cur.push(&fname);
+        let mut w = BufWriter::new(try!(File::create(&cur)));
 
-        let title = format!("{} -- source", cur.filename_display());
+        let title = format!("{} -- source", cur.file_name().unwrap()
+                                               .to_string_lossy());
         let desc = format!("Source to the Rust file `{}`.", filename);
         let page = layout::Page {
             title: &title,
@@ -779,7 +774,7 @@ fn emit_source(&mut self, filename: &str) -> old_io::IoResult<()> {
             description: &desc,
             keywords: get_basic_keywords(),
         };
-        try!(layout::render(&mut w as &mut Writer, &self.cx.layout,
+        try!(layout::render(&mut w, &self.cx.layout,
                             &page, &(""), &Source(contents)));
         try!(w.flush());
         return Ok(());
@@ -1081,7 +1076,7 @@ fn recurse<T, F>(&mut self, s: String, f: F) -> T where
     /// This currently isn't parallelized, but it'd be pretty easy to add
     /// parallelization to this function.
     fn krate(mut self, mut krate: clean::Crate,
-             stability: stability_summary::ModuleSummary) -> old_io::IoResult<()> {
+             stability: stability_summary::ModuleSummary) -> io::Result<()> {
         let mut item = match krate.module.take() {
             Some(i) => i,
             None => return Ok(())
@@ -1091,7 +1086,7 @@ fn krate(mut self, mut krate: clean::Crate,
         // render stability dashboard
         try!(self.recurse(stability.name.clone(), |this| {
             let json_dst = &this.dst.join("stability.json");
-            let mut json_out = BufferedWriter::new(try!(File::create(json_dst)));
+            let mut json_out = BufWriter::new(try!(File::create(json_dst)));
             try!(write!(&mut json_out, "{}", json::as_json(&stability)));
 
             let mut title = stability.name.clone();
@@ -1106,7 +1101,7 @@ fn krate(mut self, mut krate: clean::Crate,
                 keywords: get_basic_keywords(),
             };
             let html_dst = &this.dst.join("stability.html");
-            let mut html_out = BufferedWriter::new(try!(File::create(html_dst)));
+            let mut html_out = BufWriter::new(try!(File::create(html_dst)));
             layout::render(&mut html_out, &this.layout, &page,
                            &Sidebar{ cx: this, item: &item },
                            &stability)
@@ -1131,12 +1126,12 @@ fn krate(mut self, mut krate: clean::Crate,
     /// all sub-items which need to be rendered.
     ///
     /// The rendering driver uses this closure to queue up more work.
-    fn item<F>(&mut self, item: clean::Item, mut f: F) -> old_io::IoResult<()> where
+    fn item<F>(&mut self, item: clean::Item, mut f: F) -> io::Result<()> where
         F: FnMut(&mut Context, clean::Item),
     {
-        fn render(w: old_io::File, cx: &Context, it: &clean::Item,
-                  pushname: bool) -> old_io::IoResult<()> {
-            info!("Rendering an item to {}", w.path().display());
+        fn render(w: File, cx: &Context, it: &clean::Item,
+                  pushname: bool) -> io::Result<()> {
+            info!("Rendering an item to {}", w.path().unwrap().display());
             // A little unfortunate that this is done like this, but it sure
             // does make formatting *a lot* nicer.
             CURRENT_LOCATION_KEY.with(|slot| {
@@ -1177,7 +1172,7 @@ fn render(w: old_io::File, cx: &Context, it: &clean::Item,
             // We have a huge number of calls to write, so try to alleviate some
             // of the pain by using a buffered writer instead of invoking the
             // write syscall all the time.
-            let mut writer = BufferedWriter::new(w);
+            let mut writer = BufWriter::new(w);
             if !cx.render_redirect_pages {
                 try!(layout::render(&mut writer, &cx.layout, &page,
                                     &Sidebar{ cx: cx, item: it },
@@ -1227,7 +1222,16 @@ fn render(w: old_io::File, cx: &Context, it: &clean::Item,
                         clean::ModuleItem(m) => m,
                         _ => unreachable!()
                     };
-                    this.sidebar = this.build_sidebar(&m);
+
+                    // render sidebar-items.js used throughout this module
+                    {
+                        let items = this.build_sidebar_items(&m);
+                        let js_dst = this.dst.join("sidebar-items.js");
+                        let mut js_out = BufWriter::new(try!(File::create(&js_dst)));
+                        try!(write!(&mut js_out, "initSidebarItems({});",
+                                    json::as_json(&items)));
+                    }
+
                     for item in m.items {
                         f(this,item);
                     }
@@ -1238,7 +1242,7 @@ fn render(w: old_io::File, cx: &Context, it: &clean::Item,
             // Things which don't have names (like impls) don't get special
             // pages dedicated to them.
             _ if item.name.is_some() => {
-                let dst = self.dst.join(item_path(&item));
+                let dst = self.dst.join(&item_path(&item));
                 let dst = try!(File::create(&dst));
                 render(dst, self, &item, true)
             }
@@ -1247,15 +1251,11 @@ fn render(w: old_io::File, cx: &Context, it: &clean::Item,
         }
     }
 
-    fn build_sidebar(&self, m: &clean::Module) -> HashMap<String, Vec<NameDoc>> {
+    fn build_sidebar_items(&self, m: &clean::Module) -> HashMap<String, Vec<NameDoc>> {
         let mut map = HashMap::new();
         for item in &m.items {
             if self.ignore_private_item(item) { continue }
 
-            // avoid putting foreign items to the sidebar.
-            if let &clean::ForeignFunctionItem(..) = &item.inner { continue }
-            if let &clean::ForeignStaticItem(..) = &item.inner { continue }
-
             let short = shortty(item).to_static_str();
             let myname = match item.name {
                 None => continue,
@@ -1264,7 +1264,7 @@ fn build_sidebar(&self, m: &clean::Module) -> HashMap<String, Vec<NameDoc>> {
             let short = short.to_string();
             let v = map.entry(short).get().unwrap_or_else(
                 |vacant_entry| vacant_entry.insert(Vec::with_capacity(1)));
-            v.push(NameDoc(myname, Some(shorter_line(item.doc_value()))));
+            v.push((myname, Some(plain_summary_line(item.doc_value()))));
         }
 
         for (_, items) in &mut map {
@@ -1307,7 +1307,7 @@ fn href(&self, cx: &Context) -> Option<String> {
         // has anchors for the line numbers that we're linking to.
         if ast_util::is_local(self.item.def_id) {
             let mut path = Vec::new();
-            clean_srcpath(&cx.src_root, self.item.source.filename.as_bytes(),
+            clean_srcpath(&cx.src_root, Path::new(&self.item.source.filename),
                           |component| {
                 path.push(component.to_string());
             });
@@ -1478,8 +1478,9 @@ fn shorter<'a>(s: Option<&'a str>) -> &'a str {
 }
 
 #[inline]
-fn shorter_line(s: Option<&str>) -> String {
-    shorter(s).replace("\n", " ")
+fn plain_summary_line(s: Option<&str>) -> String {
+    let line = shorter(s).replace("\n", " ");
+    markdown::plain_summary_line(&line[..])
 }
 
 fn document(w: &mut fmt::Formatter, item: &clean::Item) -> fmt::Result {
@@ -2211,9 +2212,18 @@ impl<'a> fmt::Display for Sidebar<'a> {
     fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
         let cx = self.cx;
         let it = self.item;
+        let parentlen = cx.current.len() - if it.is_mod() {1} else {0};
+
+        // the sidebar is designed to display sibling functions, modules and
+        // other miscellaneous informations. since there are lots of sibling
+        // items (and that causes quadratic growth in large modules),
+        // we refactor common parts into a shared JavaScript file per module.
+        // still, we don't move everything into JS because we want to preserve
+        // as much HTML as possible in order to allow non-JS-enabled browsers
+        // to navigate the documentation (though slightly inefficiently).
+
         try!(write!(fmt, "<p class='location'>"));
-        let len = cx.current.len() - if it.is_mod() {1} else {0};
-        for (i, name) in cx.current.iter().take(len).enumerate() {
+        for (i, name) in cx.current.iter().take(parentlen).enumerate() {
             if i > 0 {
                 try!(write!(fmt, "::<wbr>"));
             }
@@ -2223,40 +2233,25 @@ fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
         }
         try!(write!(fmt, "</p>"));
 
-        fn block(w: &mut fmt::Formatter, short: &str, longty: &str,
-                 cur: &clean::Item, cx: &Context) -> fmt::Result {
-            let items = match cx.sidebar.get(short) {
-                Some(items) => items,
-                None => return Ok(())
-            };
-            try!(write!(w, "<div class='block {}'><h2>{}</h2>", short, longty));
-            for &NameDoc(ref name, ref doc) in items {
-                let curty = shortty(cur).to_static_str();
-                let class = if cur.name.as_ref().unwrap() == name &&
-                               short == curty { "current" } else { "" };
-                try!(write!(w, "<a class='{ty} {class}' href='{href}{path}' \
-                                title='{title}'>{name}</a>",
-                       ty = short,
-                       class = class,
-                       href = if curty == "mod" {"../"} else {""},
-                       path = if short == "mod" {
-                           format!("{}/index.html", name)
-                       } else {
-                           format!("{}.{}.html", short, name)
-                       },
-                       title = Escape(doc.as_ref().unwrap()),
-                       name = name));
-            }
-            try!(write!(w, "</div>"));
-            Ok(())
+        // sidebar refers to the enclosing module, not this module
+        let relpath = if shortty(it) == ItemType::Module { "../" } else { "" };
+        try!(write!(fmt,
+                    "<script>window.sidebarCurrent = {{\
+                        name: '{name}', \
+                        ty: '{ty}', \
+                        relpath: '{path}'\
+                     }};</script>",
+                    name = it.name.as_ref().map(|x| &x[..]).unwrap_or(""),
+                    ty = shortty(it).to_static_str(),
+                    path = relpath));
+        if parentlen == 0 {
+            // there is no sidebar-items.js beyond the crate root path
+            // FIXME maybe dynamic crate loading can be merged here
+        } else {
+            try!(write!(fmt, "<script defer src=\"{path}sidebar-items.js\"></script>",
+                        path = relpath));
         }
 
-        try!(block(fmt, "mod", "Modules", it, cx));
-        try!(block(fmt, "struct", "Structs", it, cx));
-        try!(block(fmt, "enum", "Enums", it, cx));
-        try!(block(fmt, "trait", "Traits", it, cx));
-        try!(block(fmt, "fn", "Functions", it, cx));
-        try!(block(fmt, "macro", "Macros", it, cx));
         Ok(())
     }
 }
index 21b7de9ff7c821ab6f68c9439b5c9371a4369d8e..1f075566ad5a280aca775e27fd5398e076b7bf11 100644 (file)
@@ -83,7 +83,7 @@ h2 {
 h3 {
     font-size: 1.3em;
 }
-h1, h2, h3:not(.impl):not(.method):not(.type), h4:not(.method):not(.type) {
+h1, h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod) {
     color: black;
     font-weight: 500;
     margin: 20px 0 15px 0;
@@ -93,7 +93,7 @@ h1.fqn {
     border-bottom: 1px dashed #D5D5D5;
     margin-top: 0;
 }
-h2, h3:not(.impl):not(.method):not(.type), h4:not(.method):not(.type) {
+h2, h3:not(.impl):not(.method):not(.type):not(.tymethod), h4:not(.method):not(.type):not(.tymethod) {
     border-bottom: 1px solid #DDDDDD;
 }
 h3.impl, h3.method, h4.method, h3.type, h4.type {
index aac3985f0cc9cd967115c98c7381b696f1e43eb6..a9b233dd128d49994112dd364743f8d66acd36aa 100644 (file)
     "use strict";
     var resizeTimeout, interval;
 
+    // This mapping table should match the discriminants of
+    // `rustdoc::html::item_type::ItemType` type in Rust.
+    var itemTypes = ["mod",
+                     "externcrate",
+                     "import",
+                     "struct",
+                     "enum",
+                     "fn",
+                     "type",
+                     "static",
+                     "trait",
+                     "impl",
+                     "tymethod",
+                     "method",
+                     "structfield",
+                     "variant",
+                     "macro",
+                     "primitive",
+                     "associatedtype",
+                     "constant"];
+
     $('.js-only').removeClass('js-only');
 
     function getQueryStringParams() {
             showResults(results);
         }
 
-        // This mapping table should match the discriminants of
-        // `rustdoc::html::item_type::ItemType` type in Rust.
-        var itemTypes = ["mod",
-                         "externcrate",
-                         "import",
-                         "struct",
-                         "enum",
-                         "fn",
-                         "type",
-                         "static",
-                         "trait",
-                         "impl",
-                         "tymethod",
-                         "method",
-                         "structfield",
-                         "variant",
-                         "macro",
-                         "primitive",
-                         "associatedtype",
-                         "constant"];
-
         function itemTypeFromName(typename) {
             for (var i = 0; i < itemTypes.length; ++i) {
                 if (itemTypes[i] === typename) return i;
 
     window.initSearch = initSearch;
 
+    // delayed sidebar rendering.
+    function initSidebarItems(items) {
+        var sidebar = $('.sidebar');
+        var current = window.sidebarCurrent;
+
+        function block(shortty, longty) {
+            var filtered = items[shortty];
+            if (!filtered) return;
+
+            var div = $('<div>').attr('class', 'block ' + shortty);
+            div.append($('<h2>').text(longty));
+
+            for (var i = 0; i < filtered.length; ++i) {
+                var item = filtered[i];
+                var name = item[0];
+                var desc = item[1]; // can be null
+
+                var klass = shortty;
+                if (name === current.name && shortty == current.ty) {
+                    klass += ' current';
+                }
+                var path;
+                if (shortty === 'mod') {
+                    path = name + '/index.html';
+                } else {
+                    path = shortty + '.' + name + '.html';
+                }
+                div.append($('<a>', {'href': current.relpath + path,
+                                     'title': desc,
+                                     'class': klass}).text(name));
+            }
+            sidebar.append(div);
+        }
+
+        block("mod", "Modules");
+        block("struct", "Structs");
+        block("enum", "Enums");
+        block("trait", "Traits");
+        block("fn", "Functions");
+        block("macro", "Macros");
+    }
+
+    window.initSidebarItems = initSidebarItems;
+
     window.register_implementors = function(imp) {
         var list = $('#implementors-list');
         var libs = Object.getOwnPropertyNames(imp);
index 687f764f02077a10cc0df749585984d9e08030b7..8fb979875cd760245c2f2668bfdc94e4ad605043 100644 (file)
@@ -15,7 +15,7 @@
     if (window.playgroundUrl) {
         $('pre.rust').hover(function() {
             var a = $('<a>').text('⇱').attr('class', 'test-arrow');
-            var code = $(this).siblings(".rusttest").text();
+            var code = $(this).prev(".rusttest").text();
             a.attr('href', window.playgroundUrl + '?code=' +
                            encodeURIComponent(code));
             a.attr('target', '_blank');
index e58239a82c603b2487570641ec122241fa96dc7c..c203dc0e7199ed51a6cb2954f7fb5354ee49504b 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "rustdoc"]
 #![unstable(feature = "rustdoc")]
 #![staged_api]
 #![feature(test)]
 #![feature(unicode)]
 #![feature(str_words)]
+#![feature(io)]
+#![feature(path)]
+#![feature(file_path)]
+#![feature(path_ext)]
 
 extern crate arena;
 extern crate getopts;
@@ -43,6 +49,7 @@
 extern crate rustc_driver;
 extern crate rustc_resolve;
 extern crate rustc_lint;
+extern crate rustc_back;
 extern crate serialize;
 extern crate syntax;
 extern crate "test" as testing;
 use std::cell::RefCell;
 use std::collections::HashMap;
 use std::env;
-use std::old_io::File;
-use std::old_io;
+use std::fs::File;
+use std::io::{self, Read, Write};
+use std::path::PathBuf;
 use std::rc::Rc;
 use std::sync::mpsc::channel;
+
 use externalfiles::ExternalHtml;
 use serialize::Decodable;
 use serialize::json::{self, Json};
@@ -94,7 +103,7 @@ pub mod html {
              fn(clean::Crate) -> plugins::PluginResult,         // fn
              &'static str);                                     // description
 
-static PASSES: &'static [Pass] = &[
+const PASSES: &'static [Pass] = &[
     ("strip-hidden", passes::strip_hidden,
      "strips all doc(hidden) items from the output"),
     ("unindent-comments", passes::unindent_comments,
@@ -105,7 +114,7 @@ pub mod html {
      "strips all private items from a crate which cannot be seen externally"),
 ];
 
-static DEFAULT_PASSES: &'static [&'static str] = &[
+const DEFAULT_PASSES: &'static [&'static str] = &[
     "strip-hidden",
     "strip-private",
     "collapse-docs",
@@ -242,7 +251,7 @@ pub fn main_args(args: &[String]) -> int {
     let should_test = matches.opt_present("test");
     let markdown_input = input.ends_with(".md") || input.ends_with(".markdown");
 
-    let output = matches.opt_str("o").map(|s| Path::new(s));
+    let output = matches.opt_str("o").map(|s| PathBuf::new(&s));
     let cfgs = matches.opt_strs("cfg");
 
     let external_html = match ExternalHtml::load(
@@ -261,7 +270,8 @@ pub fn main_args(args: &[String]) -> int {
         (true, false) => {
             return test::run(input, cfgs, libs, externs, test_args, crate_name)
         }
-        (false, true) => return markdown::render(input, output.unwrap_or(Path::new("doc")),
+        (false, true) => return markdown::render(input,
+                                                 output.unwrap_or(PathBuf::new("doc")),
                                                  &matches, &external_html,
                                                  !matches.opt_present("markdown-no-toc")),
         (false, false) => {}
@@ -278,7 +288,8 @@ pub fn main_args(args: &[String]) -> int {
     info!("going to format");
     match matches.opt_str("w").as_ref().map(|s| &**s) {
         Some("html") | None => {
-            match html::render::run(krate, &external_html, output.unwrap_or(Path::new("doc")),
+            match html::render::run(krate, &external_html,
+                                    output.unwrap_or(PathBuf::new("doc")),
                                     passes.into_iter().collect()) {
                 Ok(()) => {}
                 Err(e) => panic!("failed to generate documentation: {}", e),
@@ -286,7 +297,7 @@ pub fn main_args(args: &[String]) -> int {
         }
         Some("json") => {
             match json_output(krate, json_plugins,
-                              output.unwrap_or(Path::new("doc.json"))) {
+                              output.unwrap_or(PathBuf::new("doc.json"))) {
                 Ok(()) => {}
                 Err(e) => panic!("failed to write json: {}", e),
             }
@@ -364,15 +375,15 @@ fn rust_input(cratefile: &str, externs: core::Externs, matches: &getopts::Matche
     let cfgs = matches.opt_strs("cfg");
     let triple = matches.opt_str("target");
 
-    let cr = Path::new(cratefile);
+    let cr = PathBuf::new(cratefile);
     info!("starting to run rustc");
 
     let (tx, rx) = channel();
     std::thread::spawn(move || {
         use rustc::session::config::Input;
 
-        let cr = cr;
-        tx.send(core::run_core(paths, cfgs, externs, Input::File(cr), triple)).unwrap();
+        tx.send(core::run_core(paths, cfgs, externs, Input::File(cr),
+                               triple)).unwrap();
     }).join().map_err(|_| "rustc failed").unwrap();
     let (mut krate, analysis) = rx.recv().unwrap();
     info!("finished with rustc");
@@ -451,13 +462,12 @@ fn rust_input(cratefile: &str, externs: core::Externs, matches: &getopts::Matche
 /// This input format purely deserializes the json output file. No passes are
 /// run over the deserialized output.
 fn json_input(input: &str) -> Result<Output, String> {
-    let mut input = match File::open(&Path::new(input)) {
-        Ok(f) => f,
-        Err(e) => {
-            return Err(format!("couldn't open {}: {}", input, e))
-        }
+    let mut bytes = Vec::new();
+    match File::open(input).and_then(|mut f| f.read_to_end(&mut bytes)) {
+        Ok(()) => {}
+        Err(e) => return Err(format!("couldn't open {}: {}", input, e)),
     };
-    match json::from_reader(&mut input) {
+    match json::from_reader(&mut &bytes[..]) {
         Err(s) => Err(format!("{:?}", s)),
         Ok(Json::Object(obj)) => {
             let mut obj = obj;
@@ -495,7 +505,7 @@ fn json_input(input: &str) -> Result<Output, String> {
 /// Outputs the crate/plugin json as a giant json blob at the specified
 /// destination.
 fn json_output(krate: clean::Crate, res: Vec<plugins::PluginJson> ,
-               dst: Path) -> old_io::IoResult<()> {
+               dst: PathBuf) -> io::Result<()> {
     // {
     //   "schema": version,
     //   "crate": { parsed crate ... },
index d64d9becc0c7c459f2ac2ebcb9e6132bc834bcb7..7d635c8b2327481f609130157e366566004403a5 100644 (file)
@@ -8,7 +8,10 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+use std::fs::File;
+use std::io::Write;
 use std::old_io;
+use std::path::{PathBuf, Path};
 
 use core;
 use getopts;
@@ -40,10 +43,10 @@ fn extract_leading_metadata<'a>(s: &'a str) -> (Vec<&'a str>, &'a str) {
 
 /// Render `input` (e.g. "foo.md") into an HTML file in `output`
 /// (e.g. output = "bar" => "bar/foo.html").
-pub fn render(input: &str, mut output: Path, matches: &getopts::Matches,
+pub fn render(input: &str, mut output: PathBuf, matches: &getopts::Matches,
               external_html: &ExternalHtml, include_toc: bool) -> int {
     let input_p = Path::new(input);
-    output.push(input_p.filestem().unwrap());
+    output.push(input_p.file_stem().unwrap());
     output.set_extension("html");
 
     let mut css = String::new();
@@ -59,7 +62,7 @@ pub fn render(input: &str, mut output: Path, matches: &getopts::Matches,
     }
     let playground = playground.unwrap_or("".to_string());
 
-    let mut out = match old_io::File::create(&output) {
+    let mut out = match File::create(&output) {
         Err(e) => {
             let _ = writeln!(&mut old_io::stderr(),
                              "error opening `{}` for writing: {}",
index 43e8f44244e788c258b5f3a0d0b6873d2cd317ef..e7312d6548e9f5798a811923818389ecad43b141 100644 (file)
@@ -9,21 +9,25 @@
 // except according to those terms.
 
 use std::cell::RefCell;
-use std::sync::mpsc::channel;
+use std::collections::{HashSet, HashMap};
 use std::dynamic_lib::DynamicLibrary;
-use std::old_io::{Command, TempDir};
+use std::env;
+use std::ffi::OsString;
 use std::old_io;
-use std::os;
+use std::io;
+use std::path::PathBuf;
+use std::process::Command;
 use std::str;
+use std::sync::mpsc::channel;
 use std::thread;
 use std::thunk::Thunk;
 
-use std::collections::{HashSet, HashMap};
 use testing;
 use rustc_lint;
 use rustc::session::{self, config};
 use rustc::session::config::get_unstable_features_setting;
 use rustc::session::search_paths::{SearchPaths, PathKind};
+use rustc_back::tempdir::TempDir;
 use rustc_driver::{driver, Compilation};
 use syntax::codemap::CodeMap;
 use syntax::diagnostic;
@@ -43,11 +47,12 @@ pub fn run(input: &str,
            mut test_args: Vec<String>,
            crate_name: Option<String>)
            -> int {
-    let input_path = Path::new(input);
+    let input_path = PathBuf::new(input);
     let input = config::Input::File(input_path.clone());
 
     let sessopts = config::Options {
-        maybe_sysroot: Some(os::self_exe_name().unwrap().dir_path().dir_path()),
+        maybe_sysroot: Some(env::current_exe().unwrap().parent().unwrap()
+                                              .parent().unwrap().to_path_buf()),
         search_paths: libs.clone(),
         crate_types: vec!(config::CrateTypeDylib),
         externs: externs.clone(),
@@ -106,16 +111,18 @@ pub fn run(input: &str,
     0
 }
 
+#[allow(deprecated)]
 fn runtest(test: &str, cratename: &str, libs: SearchPaths,
            externs: core::Externs,
-           should_fail: bool, no_run: bool, as_test_harness: bool) {
+           should_panic: bool, no_run: bool, as_test_harness: bool) {
     // the test harness wants its own `main` & top level functions, so
     // never wrap the test in `fn main() { ... }`
     let test = maketest(test, Some(cratename), true, as_test_harness);
     let input = config::Input::Str(test.to_string());
 
     let sessopts = config::Options {
-        maybe_sysroot: Some(os::self_exe_name().unwrap().dir_path().dir_path()),
+        maybe_sysroot: Some(env::current_exe().unwrap().parent().unwrap()
+                                              .parent().unwrap().to_path_buf()),
         search_paths: libs,
         crate_types: vec!(config::CrateTypeExecutable),
         output_types: vec!(config::OutputTypeExe),
@@ -170,7 +177,7 @@ fn runtest(test: &str, cratename: &str, libs: SearchPaths,
     rustc_lint::register_builtins(&mut sess.lint_store.borrow_mut(), Some(&sess));
 
     let outdir = TempDir::new("rustdoctest").ok().expect("rustdoc needs a tempdir");
-    let out = Some(outdir.path().clone());
+    let out = Some(outdir.path().to_path_buf());
     let cfg = config::build_configuration(&sess);
     let libdir = sess.target_filesearch(PathKind::All).get_lib_path();
     let mut control = driver::CompileController::basic();
@@ -187,25 +194,27 @@ fn runtest(test: &str, cratename: &str, libs: SearchPaths,
     // environment to ensure that the target loads the right libraries at
     // runtime. It would be a sad day if the *host* libraries were loaded as a
     // mistake.
-    let mut cmd = Command::new(outdir.path().join("rust-out"));
+    let mut cmd = Command::new(&outdir.path().join("rust-out"));
+    let var = DynamicLibrary::envvar();
     let newpath = {
-        let mut path = DynamicLibrary::search_path();
+        let path = env::var_os(var).unwrap_or(OsString::new());
+        let mut path = env::split_paths(&path).collect::<Vec<_>>();
         path.insert(0, libdir.clone());
-        DynamicLibrary::create_path(&path)
+        env::join_paths(path.iter()).unwrap()
     };
-    cmd.env(DynamicLibrary::envvar(), newpath);
+    cmd.env(var, &newpath);
 
     match cmd.output() {
         Err(e) => panic!("couldn't run the test: {}{}", e,
-                        if e.kind == old_io::PermissionDenied {
+                        if e.kind() == io::ErrorKind::PermissionDenied {
                             " - maybe your tempdir is mounted with noexec?"
                         } else { "" }),
         Ok(out) => {
-            if should_fail && out.status.success() {
+            if should_panic && out.status.success() {
                 panic!("test executable succeeded when it should have failed");
-            } else if !should_fail && !out.status.success() {
+            } else if !should_panic && !out.status.success() {
                 panic!("test executable failed:\n{:?}",
-                      str::from_utf8(&out.error));
+                      str::from_utf8(&out.stdout));
             }
         }
     }
@@ -270,7 +279,7 @@ pub fn new(cratename: String, libs: SearchPaths, externs: core::Externs,
     }
 
     pub fn add_test(&mut self, test: String,
-                    should_fail: bool, no_run: bool, should_ignore: bool, as_test_harness: bool) {
+                    should_panic: bool, no_run: bool, should_ignore: bool, as_test_harness: bool) {
         let name = if self.use_headers {
             let s = self.current_header.as_ref().map(|s| &**s).unwrap_or("");
             format!("{}_{}", s, self.cnt)
@@ -286,14 +295,14 @@ pub fn add_test(&mut self, test: String,
             desc: testing::TestDesc {
                 name: testing::DynTestName(name),
                 ignore: should_ignore,
-                should_fail: testing::ShouldFail::No, // compiler failures are test failures
+                should_panic: testing::ShouldPanic::No, // compiler failures are test failures
             },
             testfn: testing::DynTestFn(Thunk::new(move|| {
                 runtest(&test,
                         &cratename,
                         libs,
                         externs,
-                        should_fail,
+                        should_panic,
                         no_run,
                         as_test_harness);
             }))
index a3cc2d6b935d9fab31d9bea4d38968ea822132e1..6f3d90d45b08721a10583ecd14d8e89d5f32fd74 100644 (file)
@@ -24,7 +24,7 @@ pub trait ToHex {
     fn to_hex(&self) -> String;
 }
 
-static CHARS: &'static[u8] = b"0123456789abcdef";
+const CHARS: &'static [u8] = b"0123456789abcdef";
 
 impl ToHex for [u8] {
     /// Turn a vector of `u8` bytes into a hexadecimal string.
@@ -117,7 +117,7 @@ fn from_hex(&self) -> Result<Vec<u8>, FromHexError> {
         // This may be an overestimate if there is any whitespace
         let mut b = Vec::with_capacity(self.len() / 2);
         let mut modulus = 0;
-        let mut buf = 0u8;
+        let mut buf = 0;
 
         for (idx, byte) in self.bytes().enumerate() {
             buf <<= 4;
index 14930f91c9152f02335e731e2ab3bdbdcbd01b39..6fc56522c6af1dbaa7198a214416b4388535449d 100644 (file)
 //!     let json_str: String = json_obj.to_string();
 //!
 //!     // Deserialize like before
-//!     let decoded: TestStruct = json::decode(json_str.as_slice()).unwrap();
+//!     let decoded: TestStruct = json::decode(json_str)).unwrap();
 //! }
 //! ```
 
@@ -1569,8 +1569,8 @@ fn parse_u64(&mut self) -> Result<u64, ParserError> {
                 while !self.eof() {
                     match self.ch_or_null() {
                         c @ '0' ... '9' => {
-                            accum *= 10;
-                            accum += (c as u64) - ('0' as u64);
+                            accum = accum.wrapping_mul(10);
+                            accum = accum.wrapping_add((c as u64) - ('0' as u64));
 
                             // Detect overflow by comparing to the last value.
                             if accum <= last_accum { return self.error(InvalidNumber); }
@@ -1653,7 +1653,7 @@ fn parse_exponent(&mut self, mut res: f64) -> Result<f64, ParserError> {
 
     fn decode_hex_escape(&mut self) -> Result<u16, ParserError> {
         let mut i = 0;
-        let mut n = 0u16;
+        let mut n = 0;
         while i < 4 && !self.eof() {
             self.bump();
             n = match self.ch_or_null() {
index d476fd72abc3b03ea2f8cc8b729f8182fa78fad6..ad7908c6dd57c820bf327d81cd7c06f8d7307921 100644 (file)
@@ -14,6 +14,8 @@
 Core encoding and decoding interfaces.
 */
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "serialize"]
 #![unstable(feature = "rustc_private",
             reason = "deprecated in favor of rustc-serialize on crates.io")]
@@ -35,6 +37,7 @@
 #![feature(staged_api)]
 #![feature(std_misc)]
 #![feature(unicode)]
+#![feature(path)]
 #![cfg_attr(test, feature(test))]
 
 // test harness access
index 70f0ba4bb23af013d1429e4d5fcdb2e882a85bac..f287229e0830db19fc9a96a2e499fde9e6c3a9d8 100644 (file)
@@ -15,6 +15,7 @@
 */
 
 use std::old_path;
+use std::path;
 use std::rc::Rc;
 use std::cell::{Cell, RefCell};
 use std::sync::Arc;
@@ -564,6 +565,19 @@ fn decode<D: Decoder>(d: &mut D) -> Result<old_path::windows::Path, D::Error> {
     }
 }
 
+impl Encodable for path::PathBuf {
+    fn encode<S: Encoder>(&self, e: &mut S) -> Result<(), S::Error> {
+        self.to_str().unwrap().encode(e)
+    }
+}
+
+impl Decodable for path::PathBuf {
+    fn decode<D: Decoder>(d: &mut D) -> Result<path::PathBuf, D::Error> {
+        let bytes: String = try!(Decodable::decode(d));
+        Ok(path::PathBuf::new(&bytes))
+    }
+}
+
 impl<T: Encodable + Copy> Encodable for Cell<T> {
     fn encode<S: Encoder>(&self, s: &mut S) -> Result<(), S::Error> {
         self.get().encode(s)
index 94457a5d71441b784dc52e9969f6d5e77703ea60..8b275d1bc4ab772b867569cf6bb77ea6d178547a 100644 (file)
@@ -186,7 +186,7 @@ fn into_ascii_lowercase(mut self) -> Vec<u8> {
 impl AsciiExt for u8 {
     type Owned = u8;
     #[inline]
-    fn is_ascii(&self) -> bool { *self & 128 == 0u8 }
+    fn is_ascii(&self) -> bool { *self & 128 == 0 }
     #[inline]
     fn to_ascii_uppercase(&self) -> u8 { ASCII_UPPERCASE_MAP[*self as usize] }
     #[inline]
@@ -398,7 +398,7 @@ fn test_to_ascii_uppercase() {
         assert_eq!("url()URL()uRl()ürl".to_ascii_uppercase(), "URL()URL()URL()üRL");
         assert_eq!("hıKß".to_ascii_uppercase(), "HıKß");
 
-        for i in 0u32..501 {
+        for i in 0..501 {
             let upper = if 'a' as u32 <= i && i <= 'z' as u32 { i + 'A' as u32 - 'a' as u32 }
                         else { i };
             assert_eq!((from_u32(i).unwrap()).to_string().to_ascii_uppercase(),
@@ -412,7 +412,7 @@ fn test_to_ascii_lowercase() {
         // Dotted capital I, Kelvin sign, Sharp S.
         assert_eq!("HİKß".to_ascii_lowercase(), "hİKß");
 
-        for i in 0u32..501 {
+        for i in 0..501 {
             let lower = if 'A' as u32 <= i && i <= 'Z' as u32 { i + 'a' as u32 - 'A' as u32 }
                         else { i };
             assert_eq!((from_u32(i).unwrap()).to_string().to_ascii_lowercase(),
@@ -426,7 +426,7 @@ fn test_into_ascii_uppercase() {
                    "URL()URL()URL()üRL".to_string());
         assert_eq!(("hıKß".to_string()).into_ascii_uppercase(), "HıKß");
 
-        for i in 0u32..501 {
+        for i in 0..501 {
             let upper = if 'a' as u32 <= i && i <= 'z' as u32 { i + 'A' as u32 - 'a' as u32 }
                         else { i };
             assert_eq!((from_u32(i).unwrap()).to_string().into_ascii_uppercase(),
@@ -441,7 +441,7 @@ fn test_into_ascii_lowercase() {
         // Dotted capital I, Kelvin sign, Sharp S.
         assert_eq!(("HİKß".to_string()).into_ascii_lowercase(), "hİKß");
 
-        for i in 0u32..501 {
+        for i in 0..501 {
             let lower = if 'A' as u32 <= i && i <= 'Z' as u32 { i + 'a' as u32 - 'A' as u32 }
                         else { i };
             assert_eq!((from_u32(i).unwrap()).to_string().into_ascii_lowercase(),
@@ -459,7 +459,7 @@ fn test_eq_ignore_ascii_case() {
         assert!(!"K".eq_ignore_ascii_case("k"));
         assert!(!"ß".eq_ignore_ascii_case("s"));
 
-        for i in 0u32..501 {
+        for i in 0..501 {
             let lower = if 'A' as u32 <= i && i <= 'Z' as u32 { i + 'a' as u32 - 'A' as u32 }
                         else { i };
             assert!((from_u32(i).unwrap()).to_string().eq_ignore_ascii_case(
index faddbba50590f9ce1a87499ef7db2a299e21b038..9502302aa53ab8de04827a7af22e91b23bc8d93e 100644 (file)
@@ -314,6 +314,13 @@ fn search_hashed<K, V, M, F>(table: M,
     M: Deref<Target=RawTable<K, V>>,
     F: FnMut(&K) -> bool,
 {
+    // This is the only function where capacity can be zero. To avoid
+    // undefined behaviour when Bucket::new gets the raw bucket in this
+    // case, immediately return the appropriate search result.
+    if table.capacity() == 0 {
+        return TableRef(table);
+    }
+
     let size = table.size();
     let mut probe = Bucket::new(table, hash);
     let ib = probe.index();
@@ -2190,7 +2197,7 @@ fn test_index() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_index_nonexistent() {
         let mut map = HashMap::new();
 
index 4c03d8915eb8a04ca0909e022739eb6c38ade22a..69fd0a57d5f38c3eb4176b8d15db486cab819c8d 100644 (file)
@@ -20,6 +20,7 @@
 use mem::{min_align_of, size_of};
 use mem;
 use num::{Int, UnsignedInt};
+use num::wrapping::{OverflowingOps, WrappingOps};
 use ops::{Deref, DerefMut, Drop};
 use option::Option;
 use option::Option::{Some, None};
@@ -27,7 +28,7 @@
 use rt::heap::{allocate, deallocate, EMPTY};
 use collections::hash_state::HashState;
 
-const EMPTY_BUCKET: u64 = 0u64;
+const EMPTY_BUCKET: u64 = 0;
 
 /// The raw hashtable, providing safe-ish access to the unzipped and highly
 /// optimized arrays of hashes, keys, and values.
@@ -148,7 +149,7 @@ pub fn make_hash<T: ?Sized, S>(hash_state: &S, t: &T) -> SafeHash
 {
     let mut state = hash_state.hasher();
     t.hash(&mut state);
-    // We need to avoid 0u64 in order to prevent collisions with
+    // We need to avoid 0 in order to prevent collisions with
     // EMPTY_HASH. We can maintain our precious uniform distribution
     // of initial indexes by unconditionally setting the MSB,
     // effectively reducing 64-bits hashes to 63 bits.
@@ -224,6 +225,9 @@ pub fn new(table: M, hash: SafeHash) -> Bucket<K, V, M> {
     }
 
     pub fn at_index(table: M, ib_index: usize) -> Bucket<K, V, M> {
+        // if capacity is 0, then the RawBucket will be populated with bogus pointers.
+        // This is an uncommon case though, so avoid it in release builds.
+        debug_assert!(table.capacity() > 0, "Table should have capacity at this point");
         let ib_index = ib_index & (table.capacity() - 1);
         Bucket {
             raw: unsafe {
@@ -371,7 +375,7 @@ pub fn distance(&self) -> usize {
         // Calculates the distance one has to travel when going from
         // `hash mod capacity` onwards to `idx mod capacity`, wrapping around
         // if the destination is not reached before the end of the table.
-        (self.idx - self.hash().inspect() as usize) & (self.table.capacity() - 1)
+        (self.idx.wrapping_sub(self.hash().inspect() as usize)) & (self.table.capacity() - 1)
     }
 
     #[inline]
@@ -524,13 +528,13 @@ fn test_rounding() {
 fn calculate_offsets(hashes_size: usize,
                      keys_size: usize, keys_align: usize,
                      vals_align: usize)
-                     -> (usize, usize) {
+                     -> (usize, usize, bool) {
     let keys_offset = round_up_to_next(hashes_size, keys_align);
-    let end_of_keys = keys_offset + keys_size;
+    let (end_of_keys, oflo) = keys_offset.overflowing_add(keys_size);
 
     let vals_offset = round_up_to_next(end_of_keys, vals_align);
 
-    (keys_offset, vals_offset)
+    (keys_offset, vals_offset, oflo)
 }
 
 // Returns a tuple of (minimum required malloc alignment, hash_offset,
@@ -538,26 +542,26 @@ fn calculate_offsets(hashes_size: usize,
 fn calculate_allocation(hash_size: usize, hash_align: usize,
                         keys_size: usize, keys_align: usize,
                         vals_size: usize, vals_align: usize)
-                        -> (usize, usize, usize) {
+                        -> (usize, usize, usize, bool) {
     let hash_offset = 0;
-    let (_, vals_offset) = calculate_offsets(hash_size,
-                                             keys_size, keys_align,
-                                                        vals_align);
-    let end_of_vals = vals_offset + vals_size;
+    let (_, vals_offset, oflo) = calculate_offsets(hash_size,
+                                                   keys_size, keys_align,
+                                                              vals_align);
+    let (end_of_vals, oflo2) = vals_offset.overflowing_add(vals_size);
 
     let min_align = cmp::max(hash_align, cmp::max(keys_align, vals_align));
 
-    (min_align, hash_offset, end_of_vals)
+    (min_align, hash_offset, end_of_vals, oflo || oflo2)
 }
 
 #[test]
 fn test_offset_calculation() {
-    assert_eq!(calculate_allocation(128, 8, 15, 1, 4,  4), (8, 0, 148));
-    assert_eq!(calculate_allocation(3,   1, 2,  1, 1,  1), (1, 0, 6));
-    assert_eq!(calculate_allocation(6,   2, 12, 4, 24, 8), (8, 0, 48));
-    assert_eq!(calculate_offsets(128, 15, 1, 4), (128, 144));
-    assert_eq!(calculate_offsets(3,   2,  1, 1), (3,   5));
-    assert_eq!(calculate_offsets(6,   12, 4, 8), (8,   24));
+    assert_eq!(calculate_allocation(128, 8, 15, 1, 4,  4), (8, 0, 148, false));
+    assert_eq!(calculate_allocation(3,   1, 2,  1, 1,  1), (1, 0, 6, false));
+    assert_eq!(calculate_allocation(6,   2, 12, 4, 24, 8), (8, 0, 48, false));
+    assert_eq!(calculate_offsets(128, 15, 1, 4), (128, 144, false));
+    assert_eq!(calculate_offsets(3,   2,  1, 1), (3,   5, false));
+    assert_eq!(calculate_offsets(6,   12, 4, 8), (8,   24, false));
 }
 
 impl<K, V> RawTable<K, V> {
@@ -587,12 +591,14 @@ unsafe fn new_uninitialized(capacity: usize) -> RawTable<K, V> {
         // This is great in theory, but in practice getting the alignment
         // right is a little subtle. Therefore, calculating offsets has been
         // factored out into a different function.
-        let (malloc_alignment, hash_offset, size) =
+        let (malloc_alignment, hash_offset, size, oflo) =
             calculate_allocation(
                 hashes_size, min_align_of::<u64>(),
                 keys_size,   min_align_of::< K >(),
                 vals_size,   min_align_of::< V >());
 
+        assert!(!oflo, "capacity overflow");
+
         // One check for overflow that covers calculation and rounding of size.
         let size_of_bucket = size_of::<u64>().checked_add(size_of::<K>()).unwrap()
                                              .checked_add(size_of::<V>()).unwrap();
@@ -618,10 +624,11 @@ fn first_bucket_raw(&self) -> RawBucket<K, V> {
         let keys_size = self.capacity * size_of::<K>();
 
         let buffer = *self.hashes as *mut u8;
-        let (keys_offset, vals_offset) = calculate_offsets(hashes_size,
-                                                           keys_size, min_align_of::<K>(),
-                                                           min_align_of::<V>());
-
+        let (keys_offset, vals_offset, oflo) =
+            calculate_offsets(hashes_size,
+                              keys_size, min_align_of::<K>(),
+                              min_align_of::<V>());
+        debug_assert!(!oflo, "capacity overflow");
         unsafe {
             RawBucket {
                 hash: *self.hashes,
@@ -995,9 +1002,12 @@ fn drop(&mut self) {
         let hashes_size = self.capacity * size_of::<u64>();
         let keys_size = self.capacity * size_of::<K>();
         let vals_size = self.capacity * size_of::<V>();
-        let (align, _, size) = calculate_allocation(hashes_size, min_align_of::<u64>(),
-                                                    keys_size, min_align_of::<K>(),
-                                                    vals_size, min_align_of::<V>());
+        let (align, _, size, oflo) =
+            calculate_allocation(hashes_size, min_align_of::<u64>(),
+                                 keys_size, min_align_of::<K>(),
+                                 vals_size, min_align_of::<V>());
+
+        debug_assert!(!oflo, "should be impossible");
 
         unsafe {
             deallocate(*self.hashes as *mut u8, size, align);
index 100d3e6ed4aa9c5c6afb095c293b3e1c6ee8fe7e..caada8ae50f74aa30a4f0c7373674ddbb5ad191b 100644 (file)
@@ -78,7 +78,7 @@
 //! * You want a bit vector.
 //!
 //! ### Use a `BitSet` when:
-//! * You want a `VecSet`.
+//! * You want a `BitVec`, but want `Set` properties
 //!
 //! ### Use a `BinaryHeap` when:
 //! * You want to store a bunch of elements, but only ever want to process the "biggest"
@@ -89,7 +89,8 @@
 //!
 //! Choosing the right collection for the job requires an understanding of what each collection
 //! is good at. Here we briefly summarize the performance of different collections for certain
-//! important operations. For further details, see each type's documentation.
+//! important operations. For further details, see each type's documentation, and note that the
+//! names of actual methods may differ from the tables below on certain collections.
 //!
 //! Throughout the documentation, we will follow a few conventions. For all operations,
 //! the collection's size is denoted by n. If another collection is involved in the operation, it
 //! a variant of the `Entry` enum.
 //!
 //! If a `Vacant(entry)` is yielded, then the key *was not* found. In this case the
-//! only valid operation is to `set` the value of the entry. When this is done,
+//! only valid operation is to `insert` a value into the entry. When this is done,
 //! the vacant entry is consumed and converted into a mutable reference to the
 //! the value that was inserted. This allows for further manipulation of the value
 //! beyond the lifetime of the search itself. This is useful if complex logic needs to
 //! be performed on the value regardless of whether the value was just inserted.
 //!
 //! If an `Occupied(entry)` is yielded, then the key *was* found. In this case, the user
-//! has several options: they can `get`, `set`, or `take` the value of the occupied
+//! has several options: they can `get`, `insert`, or `remove` the value of the occupied
 //! entry. Additionally, they can convert the occupied entry into a mutable reference
-//! to its value, providing symmetry to the vacant `set` case.
+//! to its value, providing symmetry to the vacant `insert` case.
 //!
 //! ### Examples
 //!
 //! use std::collections::btree_map::{BTreeMap, Entry};
 //!
 //! // A client of the bar. They have an id and a blood alcohol level.
-//! struct Person { id: u32, blood_alcohol: f32 };
+//! struct Person { id: u32, blood_alcohol: f32 }
 //!
 //! // All the orders made to the bar, by client id.
 //! let orders = vec![1,2,1,2,3,4,1,2,2,3,4,1,1,1];
index 1968ca4b9e7052cbad18612fd4ab8f21e13848df..b2ef04a5d632c2e82a3de7f32d2d787ba9e404d3 100644 (file)
@@ -616,6 +616,9 @@ mod os {
 mod os {
     pub const FAMILY: &'static str = "unix";
     pub const OS: &'static str = "ios";
+    pub const DLL_PREFIX: &'static str = "lib";
+    pub const DLL_SUFFIX: &'static str = ".dylib";
+    pub const DLL_EXTENSION: &'static str = "dylib";
     pub const EXE_SUFFIX: &'static str = "";
     pub const EXE_EXTENSION: &'static str = "";
 }
@@ -777,8 +780,8 @@ fn test_var_big() {
             i += 1;
         }
         let n = make_rand_name();
-        set_var(&n, s.as_slice());
-        eq(var_os(&n), Some(s.as_slice()));
+        set_var(&n, &s);
+        eq(var_os(&n), Some(&s));
     }
 
     #[test]
@@ -796,7 +799,7 @@ fn test_env_set_get_huge() {
         let n = make_rand_name();
         let s = repeat("x").take(10000).collect::<String>();
         set_var(&n, &s);
-        eq(var_os(&n), Some(s.as_slice()));
+        eq(var_os(&n), Some(&s));
         remove_var(&n);
         eq(var_os(&n), None);
     }
index 69bcc82f6827570f61226dc0e241a0b4de023d5c..ec9f90723be96525237346913150d0a389f39b0b 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![unstable(feature = "std_misc")]
+
 use cmp::{PartialEq, Eq, PartialOrd, Ord, Ordering};
 use error::{Error, FromError};
 use fmt;
@@ -59,6 +61,7 @@
 /// # }
 /// ```
 #[derive(Clone, PartialEq, PartialOrd, Eq, Ord, Hash)]
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct CString {
     inner: Vec<u8>,
 }
@@ -110,13 +113,19 @@ pub struct CString {
 /// }
 /// ```
 #[derive(Hash)]
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct CStr {
+    // FIXME: this should not be represented with a DST slice but rather with
+    //        just a raw `libc::c_char` along with some form of marker to make
+    //        this an unsized type. Essentially `sizeof(&CStr)` should be the
+    //        same as `sizeof(&c_char)` but `CStr` should be an unsized type.
     inner: [libc::c_char]
 }
 
 /// An error returned from `CString::new` to indicate that a nul byte was found
 /// in the vector provided.
 #[derive(Clone, PartialEq, Debug)]
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct NulError(usize, Vec<u8>);
 
 /// A conversion trait used by the constructor of `CString` for types that can
@@ -153,6 +162,7 @@ impl CString {
     /// This function will return an error if the bytes yielded contain an
     /// internal 0 byte. The error returned will contain the bytes as well as
     /// the position of the nul byte.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn new<T: IntoBytes>(t: T) -> Result<CString, NulError> {
         let bytes = t.into_bytes();
         match bytes.iter().position(|x| *x == 0) {
@@ -216,6 +226,7 @@ pub fn from_vec(v: Vec<u8>) -> CString {
     ///
     /// This method is equivalent to `from_vec` except that no runtime assertion
     /// is made that `v` contains no 0 bytes.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub unsafe fn from_vec_unchecked(mut v: Vec<u8>) -> CString {
         v.push(0);
         CString { inner: v }
@@ -225,17 +236,20 @@ pub unsafe fn from_vec_unchecked(mut v: Vec<u8>) -> CString {
     ///
     /// The returned slice does **not** contain the trailing nul separator and
     /// it is guaranteed to not have any interior nul bytes.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn as_bytes(&self) -> &[u8] {
         &self.inner[..self.inner.len() - 1]
     }
 
     /// Equivalent to the `as_bytes` function except that the returned slice
     /// includes the trailing nul byte.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn as_bytes_with_nul(&self) -> &[u8] {
         &self.inner
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Deref for CString {
     type Target = CStr;
 
@@ -254,23 +268,28 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
 impl NulError {
     /// Returns the position of the nul byte in the slice that was provided to
     /// `CString::from_vec`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn nul_position(&self) -> usize { self.0 }
 
     /// Consumes this error, returning the underlying vector of bytes which
     /// generated the error in the first place.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn into_vec(self) -> Vec<u8> { self.1 }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Error for NulError {
     fn description(&self) -> &str { "nul byte found in data" }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl fmt::Display for NulError {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
         write!(f, "nul byte found in provided data at position: {}", self.0)
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl FromError<NulError> for io::Error {
     fn from_error(_: NulError) -> io::Error {
         io::Error::new(io::ErrorKind::InvalidInput,
@@ -278,6 +297,7 @@ fn from_error(_: NulError) -> io::Error {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl FromError<NulError> for old_io::IoError {
     fn from_error(_: NulError) -> old_io::IoError {
         old_io::IoError {
@@ -325,6 +345,7 @@ impl CStr {
     /// }
     /// # }
     /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub unsafe fn from_ptr<'a>(ptr: *const libc::c_char) -> &'a CStr {
         let len = libc::strlen(ptr);
         mem::transmute(slice::from_raw_parts(ptr, len as usize + 1))
@@ -335,6 +356,7 @@ pub unsafe fn from_ptr<'a>(ptr: *const libc::c_char) -> &'a CStr {
     /// The returned pointer will be valid for as long as `self` is and points
     /// to a contiguous region of memory terminated with a 0 byte to represent
     /// the end of the string.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn as_ptr(&self) -> *const libc::c_char {
         self.inner.as_ptr()
     }
@@ -351,6 +373,7 @@ pub fn as_ptr(&self) -> *const libc::c_char {
     /// > **Note**: This method is currently implemented as a 0-cost cast, but
     /// > it is planned to alter its definition in the future to perform the
     /// > length calculation whenever this method is called.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn to_bytes(&self) -> &[u8] {
         let bytes = self.to_bytes_with_nul();
         &bytes[..bytes.len() - 1]
@@ -364,22 +387,27 @@ pub fn to_bytes(&self) -> &[u8] {
     /// > **Note**: This method is currently implemented as a 0-cost cast, but
     /// > it is planned to alter its definition in the future to perform the
     /// > length calculation whenever this method is called.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn to_bytes_with_nul(&self) -> &[u8] {
         unsafe { mem::transmute::<&[libc::c_char], &[u8]>(&self.inner) }
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialEq for CStr {
     fn eq(&self, other: &CStr) -> bool {
         self.to_bytes().eq(other.to_bytes())
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Eq for CStr {}
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialOrd for CStr {
     fn partial_cmp(&self, other: &CStr) -> Option<Ordering> {
         self.to_bytes().partial_cmp(&other.to_bytes())
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Ord for CStr {
     fn cmp(&self, other: &CStr) -> Ordering {
         self.to_bytes().cmp(&other.to_bytes())
@@ -422,15 +450,14 @@ mod tests {
     use prelude::v1::*;
     use super::*;
     use libc;
-    use mem;
 
     #[test]
     fn c_to_rust() {
         let data = b"123\0";
         let ptr = data.as_ptr() as *const libc::c_char;
         unsafe {
-            assert_eq!(c_str_to_bytes(&ptr), b"123");
-            assert_eq!(c_str_to_bytes_with_nul(&ptr), b"123\0");
+            assert_eq!(CStr::from_ptr(ptr).to_bytes(), b"123");
+            assert_eq!(CStr::from_ptr(ptr).to_bytes_with_nul(), b"123\0");
         }
     }
 
index 1bff6afb776079b0e5102ad2b0e92541d089263c..f17dc6542491bad149819704d118debd755ac9a7 100644 (file)
 
 //! Utilities related to FFI bindings.
 
-#![unstable(feature = "std_misc",
-            reason = "module just underwent fairly large reorganization and the dust \
-                      still needs to settle")]
+#![stable(feature = "rust1", since = "1.0.0")]
 
-pub use self::c_str::{CString, CStr, NulError, IntoBytes};
+#[stable(feature = "rust1", since = "1.0.0")]
+pub use self::c_str::{CString, CStr};
+pub use self::c_str::{NulError, IntoBytes};
 #[allow(deprecated)]
 pub use self::c_str::c_str_to_bytes;
 #[allow(deprecated)]
 pub use self::c_str::c_str_to_bytes_with_nul;
 
+#[stable(feature = "rust1", since = "1.0.0")]
 pub use self::os_str::OsString;
+#[stable(feature = "rust1", since = "1.0.0")]
 pub use self::os_str::OsStr;
 
 mod c_str;
@@ -28,6 +30,7 @@
 
 // FIXME (#21670): these should be defined in the os_str module
 /// Freely convertible to an `&OsStr` slice.
+#[unstable(feature = "std_misc")]
 pub trait AsOsStr {
     /// Convert to an `&OsStr` slice.
     fn as_os_str(&self) -> &OsStr;
index fe0df1728efc0bd34559941d394346acc3d0a63d..77df831bbfe3771e21e57fb92ca2f5a191674b0d 100644 (file)
 
 use core::prelude::*;
 
-use borrow::{Borrow, ToOwned};
+use borrow::{Borrow, Cow, ToOwned};
 use fmt::{self, Debug};
 use mem;
-use string::{String, CowString};
+use string::String;
 use ops;
 use cmp;
 use hash::{Hash, Hasher};
 
 /// Owned, mutable OS strings.
 #[derive(Clone)]
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct OsString {
     inner: Buf
 }
 
 /// Slices into OS strings.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct OsStr {
     inner: Slice
 }
 
 impl OsString {
     /// Constructs an `OsString` at no cost by consuming a `String`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn from_string(s: String) -> OsString {
         OsString { inner: Buf::from_string(s) }
     }
@@ -67,11 +70,13 @@ pub fn from_string(s: String) -> OsString {
     /// Constructs an `OsString` by copying from a `&str` slice.
     ///
     /// Equivalent to: `OsString::from_string(String::from_str(s))`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn from_str(s: &str) -> OsString {
         OsString { inner: Buf::from_str(s) }
     }
 
     /// Constructs a new empty `OsString`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn new() -> OsString {
         OsString { inner: Buf::from_string(String::new()) }
     }
@@ -79,16 +84,26 @@ pub fn new() -> OsString {
     /// Convert the `OsString` into a `String` if it contains valid Unicode data.
     ///
     /// On failure, ownership of the original `OsString` is returned.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn into_string(self) -> Result<String, OsString> {
         self.inner.into_string().map_err(|buf| OsString { inner: buf} )
     }
 
     /// Extend the string with the given `&OsStr` slice.
+    #[deprecated(since = "1.0.0", reason = "renamed to `push`")]
+    #[unstable(feature = "os")]
     pub fn push_os_str(&mut self, s: &OsStr) {
         self.inner.push_slice(&s.inner)
     }
+
+    /// Extend the string with the given `&OsStr` slice.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    pub fn push<T: AsOsStr + ?Sized>(&mut self, s: &T) {
+        self.inner.push_slice(&s.as_os_str().inner)
+    }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl ops::Index<ops::RangeFull> for OsString {
     type Output = OsStr;
 
@@ -98,6 +113,7 @@ fn index(&self, _index: &ops::RangeFull) -> &OsStr {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl ops::Deref for OsString {
     type Target = OsStr;
 
@@ -107,32 +123,38 @@ fn deref(&self) -> &OsStr {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Debug for OsString {
     fn fmt(&self, formatter: &mut fmt::Formatter) -> Result<(), fmt::Error> {
         fmt::Debug::fmt(&**self, formatter)
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialEq for OsString {
     fn eq(&self, other: &OsString) -> bool {
         &**self == &**other
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialEq<str> for OsString {
     fn eq(&self, other: &str) -> bool {
         &**self == other
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialEq<OsString> for str {
     fn eq(&self, other: &OsString) -> bool {
         &**other == self
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Eq for OsString {}
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialOrd for OsString {
     #[inline]
     fn partial_cmp(&self, other: &OsString) -> Option<cmp::Ordering> {
@@ -148,6 +170,7 @@ fn gt(&self, other: &OsString) -> bool { &**self > &**other }
     fn ge(&self, other: &OsString) -> bool { &**self >= &**other }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialOrd<str> for OsString {
     #[inline]
     fn partial_cmp(&self, other: &str) -> Option<cmp::Ordering> {
@@ -155,6 +178,7 @@ fn partial_cmp(&self, other: &str) -> Option<cmp::Ordering> {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Ord for OsString {
     #[inline]
     fn cmp(&self, other: &OsString) -> cmp::Ordering {
@@ -172,6 +196,7 @@ fn hash<H: Hasher>(&self, state: &mut H) {
 
 impl OsStr {
     /// Coerce directly from a `&str` slice to a `&OsStr` slice.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn from_str(s: &str) -> &OsStr {
         unsafe { mem::transmute(Slice::from_str(s)) }
     }
@@ -179,18 +204,21 @@ pub fn from_str(s: &str) -> &OsStr {
     /// Yield a `&str` slice if the `OsStr` is valid unicode.
     ///
     /// This conversion may entail doing a check for UTF-8 validity.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn to_str(&self) -> Option<&str> {
         self.inner.to_str()
     }
 
-    /// Convert an `OsStr` to a `CowString`.
+    /// Convert an `OsStr` to a `Cow<str>`.
     ///
     /// Any non-Unicode sequences are replaced with U+FFFD REPLACEMENT CHARACTER.
-    pub fn to_string_lossy(&self) -> CowString {
+    #[stable(feature = "rust1", since = "1.0.0")]
+    pub fn to_string_lossy(&self) -> Cow<str> {
         self.inner.to_string_lossy()
     }
 
     /// Copy the slice into an owned `OsString`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn to_os_string(&self) -> OsString {
         OsString { inner: self.inner.to_owned() }
     }
@@ -204,26 +232,31 @@ fn bytes(&self) -> &[u8] {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialEq for OsStr {
     fn eq(&self, other: &OsStr) -> bool {
         self.bytes().eq(other.bytes())
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialEq<str> for OsStr {
     fn eq(&self, other: &str) -> bool {
         *self == *OsStr::from_str(other)
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialEq<OsStr> for str {
     fn eq(&self, other: &OsStr) -> bool {
         *other == *OsStr::from_str(self)
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Eq for OsStr {}
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialOrd for OsStr {
     #[inline]
     fn partial_cmp(&self, other: &OsStr) -> Option<cmp::Ordering> {
@@ -239,6 +272,7 @@ fn gt(&self, other: &OsStr) -> bool { self.bytes().gt(other.bytes()) }
     fn ge(&self, other: &OsStr) -> bool { self.bytes().ge(other.bytes()) }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl PartialOrd<str> for OsStr {
     #[inline]
     fn partial_cmp(&self, other: &str) -> Option<cmp::Ordering> {
@@ -249,6 +283,7 @@ fn partial_cmp(&self, other: &str) -> Option<cmp::Ordering> {
 // FIXME (#19470): cannot provide PartialOrd<OsStr> for str until we
 // have more flexible coherence rules.
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Ord for OsStr {
     #[inline]
     fn cmp(&self, other: &OsStr) -> cmp::Ordering { self.bytes().cmp(other.bytes()) }
@@ -262,21 +297,25 @@ fn hash<H: Hasher>(&self, state: &mut H) {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Debug for OsStr {
     fn fmt(&self, formatter: &mut fmt::Formatter) -> Result<(), fmt::Error> {
         self.inner.fmt(formatter)
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Borrow<OsStr> for OsString {
     fn borrow(&self) -> &OsStr { &self[..] }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl ToOwned for OsStr {
     type Owned = OsString;
     fn to_owned(&self) -> OsString { self.to_os_string() }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a, T: AsOsStr + ?Sized> AsOsStr for &'a T {
     fn as_os_str(&self) -> &OsStr {
         (*self).as_os_str()
@@ -307,15 +346,12 @@ fn as_os_str(&self) -> &OsStr {
     }
 }
 
-#[cfg(unix)]
 impl AsOsStr for Path {
+    #[cfg(unix)]
     fn as_os_str(&self) -> &OsStr {
         unsafe { mem::transmute(self.as_vec()) }
     }
-}
-
-#[cfg(windows)]
-impl AsOsStr for Path {
+    #[cfg(windows)]
     fn as_os_str(&self) -> &OsStr {
         // currently .as_str() is actually infallible on windows
         OsStr::from_str(self.as_str().unwrap())
index 64ec025a5c423bc087426f835ef43aef8e93eb5e..9f9163eb9e69f1fdb5aa1379afe362d9dbdaac9c 100644 (file)
@@ -15,7 +15,7 @@
 //! operations. Extra platform-specific functionality can be found in the
 //! extension traits of `std::os::$platform`.
 
-#![unstable(feature = "fs")]
+#![stable(feature = "rust1", since = "1.0.0")]
 
 use core::prelude::*;
 
@@ -25,6 +25,7 @@
 use sys_common::{AsInnerMut, FromInner, AsInner};
 use vec::Vec;
 
+#[allow(deprecated)]
 pub use self::tempdir::TempDir;
 
 mod tempdir;
@@ -52,6 +53,7 @@
 /// # Ok(())
 /// # }
 /// ```
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct File {
     inner: fs_imp::File,
     path: PathBuf,
@@ -62,6 +64,7 @@ pub struct File {
 /// This structure is returned from the `metadata` function or method and
 /// represents known metadata about a file such as its permissions, size,
 /// modification times, etc.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Metadata(fs_imp::FileAttr);
 
 /// Iterator over the entries in a directory.
@@ -70,6 +73,7 @@ pub struct File {
 /// will yield instances of `io::Result<DirEntry>`. Through a `DirEntry`
 /// information like the entry's path and possibly other metadata can be
 /// learned.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct ReadDir(fs_imp::ReadDir);
 
 /// Entries returned by the `ReadDir` iterator.
@@ -77,9 +81,14 @@ pub struct File {
 /// An instance of `DirEntry` represents an entry inside of a directory on the
 /// filesystem. Each entry can be inspected via methods to learn about the full
 /// path or possibly other metadata through per-platform extension traits.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct DirEntry(fs_imp::DirEntry);
 
 /// An iterator that recursively walks over the contents of a directory.
+#[unstable(feature = "fs_walk",
+           reason = "the precise semantics and defaults for a recursive walk \
+                     may change and this may end up accounting for files such \
+                     as symlinks differently")]
 pub struct WalkDir {
     cur: Option<ReadDir>,
     stack: Vec<io::Result<ReadDir>>,
@@ -92,6 +101,7 @@ pub struct WalkDir {
 /// `File::create` methods are aliases for commonly used options using this
 /// builder.
 #[derive(Clone)]
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct OpenOptions(fs_imp::OpenOptions);
 
 /// Representation of the various permissions on a file.
@@ -101,6 +111,7 @@ pub struct WalkDir {
 /// functionality, such as mode bits, is available through the
 /// `os::unix::PermissionsExt` trait.
 #[derive(Clone, PartialEq, Eq, Debug)]
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Permissions(fs_imp::FilePermissions);
 
 impl File {
@@ -112,6 +123,7 @@ impl File {
     ///
     /// This function will return an error if `path` does not already exist.
     /// Other errors may also be returned according to `OpenOptions::open`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn open<P: AsPath + ?Sized>(path: &P) -> io::Result<File> {
         OpenOptions::new().read(true).open(path)
     }
@@ -122,11 +134,15 @@ pub fn open<P: AsPath + ?Sized>(path: &P) -> io::Result<File> {
     /// and will truncate it if it does.
     ///
     /// See the `OpenOptions::open` function for more details.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn create<P: AsPath + ?Sized>(path: &P) -> io::Result<File> {
         OpenOptions::new().write(true).create(true).truncate(true).open(path)
     }
 
     /// Returns the original path that was used to open this file.
+    #[unstable(feature = "file_path",
+               reason = "this abstraction is imposed by this library instead \
+                         of the underlying OS and may be removed")]
     pub fn path(&self) -> Option<&Path> {
         Some(&self.path)
     }
@@ -135,6 +151,7 @@ pub fn path(&self) -> Option<&Path> {
     ///
     /// This function will attempt to ensure that all in-core data reaches the
     /// filesystem before returning.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn sync_all(&self) -> io::Result<()> {
         self.inner.fsync()
     }
@@ -148,6 +165,7 @@ pub fn sync_all(&self) -> io::Result<()> {
     ///
     /// Note that some platforms may simply implement this in terms of
     /// `sync_all`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn sync_data(&self) -> io::Result<()> {
         self.inner.datasync()
     }
@@ -159,11 +177,13 @@ pub fn sync_data(&self) -> io::Result<()> {
     /// be shrunk. If it is greater than the current file's size, then the file
     /// will be extended to `size` and have all of the intermediate data filled
     /// in with 0s.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn set_len(&self, size: u64) -> io::Result<()> {
         self.inner.truncate(size)
     }
 
-    /// Queries information about the underlying file.
+    /// Queries metadata about the underlying file.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn metadata(&self) -> io::Result<Metadata> {
         self.inner.file_attr().map(Metadata)
     }
@@ -172,33 +192,39 @@ pub fn metadata(&self) -> io::Result<Metadata> {
 impl AsInner<fs_imp::File> for File {
     fn as_inner(&self) -> &fs_imp::File { &self.inner }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Read for File {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         self.inner.read(buf)
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Write for File {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.inner.write(buf)
     }
     fn flush(&mut self) -> io::Result<()> { self.inner.flush() }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Seek for File {
     fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> {
         self.inner.seek(pos)
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Read for &'a File {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         self.inner.read(buf)
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Write for &'a File {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.inner.write(buf)
     }
     fn flush(&mut self) -> io::Result<()> { self.inner.flush() }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Seek for &'a File {
     fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> {
         self.inner.seek(pos)
@@ -209,6 +235,7 @@ impl OpenOptions {
     /// Creates a blank net set of options ready for configuration.
     ///
     /// All options are initially set to `false`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn new() -> OpenOptions {
         OpenOptions(fs_imp::OpenOptions::new())
     }
@@ -217,6 +244,7 @@ pub fn new() -> OpenOptions {
     ///
     /// This option, when true, will indicate that the file should be
     /// `read`-able if opened.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn read(&mut self, read: bool) -> &mut OpenOptions {
         self.0.read(read); self
     }
@@ -225,6 +253,7 @@ pub fn read(&mut self, read: bool) -> &mut OpenOptions {
     ///
     /// This option, when true, will indicate that the file should be
     /// `write`-able if opened.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn write(&mut self, write: bool) -> &mut OpenOptions {
         self.0.write(write); self
     }
@@ -233,6 +262,7 @@ pub fn write(&mut self, write: bool) -> &mut OpenOptions {
     ///
     /// This option, when true, means that writes will append to a file instead
     /// of overwriting previous contents.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn append(&mut self, append: bool) -> &mut OpenOptions {
         self.0.append(append); self
     }
@@ -241,6 +271,7 @@ pub fn append(&mut self, append: bool) -> &mut OpenOptions {
     ///
     /// If a file is successfully opened with this option set it will truncate
     /// the file to 0 length if it already exists.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn truncate(&mut self, truncate: bool) -> &mut OpenOptions {
         self.0.truncate(truncate); self
     }
@@ -249,6 +280,7 @@ pub fn truncate(&mut self, truncate: bool) -> &mut OpenOptions {
     ///
     /// This option indicates whether a new file will be created if the file
     /// does not yet already exist.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn create(&mut self, create: bool) -> &mut OpenOptions {
         self.0.create(create); self
     }
@@ -264,37 +296,33 @@ pub fn create(&mut self, create: bool) -> &mut OpenOptions {
     /// * Attempting to open a file with access that the user lacks
     ///   permissions for
     /// * Filesystem-level errors (full disk, etc)
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn open<P: AsPath + ?Sized>(&self, path: &P) -> io::Result<File> {
         let path = path.as_path();
         let inner = try!(fs_imp::File::open(path, &self.0));
-
-        // On *BSD systems, we can open a directory as a file and read from
-        // it: fd=open("/tmp", O_RDONLY); read(fd, buf, N); due to an old
-        // tradition before the introduction of opendir(3).  We explicitly
-        // reject it because there are few use cases.
-        if cfg!(not(any(target_os = "linux", target_os = "android"))) &&
-           try!(inner.file_attr()).is_dir() {
-            Err(Error::new(ErrorKind::InvalidInput, "is a directory", None))
-        } else {
-            Ok(File { path: path.to_path_buf(), inner: inner })
-        }
+        Ok(File { path: path.to_path_buf(), inner: inner })
     }
 }
+
 impl AsInnerMut<fs_imp::OpenOptions> for OpenOptions {
     fn as_inner_mut(&mut self) -> &mut fs_imp::OpenOptions { &mut self.0 }
 }
 
 impl Metadata {
     /// Returns whether this metadata is for a directory.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn is_dir(&self) -> bool { self.0.is_dir() }
 
     /// Returns whether this metadata is for a regular file.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn is_file(&self) -> bool { self.0.is_file() }
 
     /// Returns the size of the file, in bytes, this metadata is for.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn len(&self) -> u64 { self.0.size() }
 
     /// Returns the permissions of the file this metadata is for.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn permissions(&self) -> Permissions {
         Permissions(self.0.perm())
     }
@@ -302,22 +330,32 @@ pub fn permissions(&self) -> Permissions {
     /// Returns the most recent access time for a file.
     ///
     /// The return value is in milliseconds since the epoch.
+    #[unstable(feature = "fs_time",
+               reason = "the return type of u64 is not quite appropriate for \
+                         this method and may change if the standard library \
+                         gains a type to represent a moment in time")]
     pub fn accessed(&self) -> u64 { self.0.accessed() }
 
     /// Returns the most recent modification time for a file.
     ///
     /// The return value is in milliseconds since the epoch.
+    #[unstable(feature = "fs_time",
+               reason = "the return type of u64 is not quite appropriate for \
+                         this method and may change if the standard library \
+                         gains a type to represent a moment in time")]
     pub fn modified(&self) -> u64 { self.0.modified() }
 }
 
 impl Permissions {
     /// Returns whether these permissions describe a readonly file.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn readonly(&self) -> bool { self.0.readonly() }
 
     /// Modify the readonly flag for this set of permissions.
     ///
     /// This operation does **not** modify the filesystem. To modify the
     /// filesystem use the `fs::set_permissions` function.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn set_readonly(&mut self, readonly: bool) {
         self.0.set_readonly(readonly)
     }
@@ -333,6 +371,7 @@ impl AsInner<fs_imp::FilePermissions> for Permissions {
     fn as_inner(&self) -> &fs_imp::FilePermissions { &self.0 }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Iterator for ReadDir {
     type Item = io::Result<DirEntry>;
 
@@ -341,11 +380,13 @@ fn next(&mut self) -> Option<io::Result<DirEntry>> {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl DirEntry {
     /// Returns the full path to the file that this entry represents.
     ///
     /// The full path is created by joining the original path to `read_dir` or
     /// `walk_dir` with the filename of this entry.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn path(&self) -> PathBuf { self.0.path() }
 }
 
@@ -368,31 +409,9 @@ pub fn path(&self) -> PathBuf { self.0.path() }
 /// This function will return an error if `path` points to a directory, if the
 /// user lacks permissions to remove the file, or if some other filesystem-level
 /// error occurs.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn remove_file<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
-    let path = path.as_path();
-    let e = match fs_imp::unlink(path) {
-        Ok(()) => return Ok(()),
-        Err(e) => e,
-    };
-    if !cfg!(windows) { return Err(e) }
-
-    // On unix, a readonly file can be successfully removed. On windows,
-    // however, it cannot. To keep the two platforms in line with
-    // respect to their behavior, catch this case on windows, attempt to
-    // change it to read-write, and then remove the file.
-    if e.kind() != ErrorKind::PermissionDenied { return Err(e) }
-
-    let attr = match metadata(path) { Ok(a) => a, Err(..) => return Err(e) };
-    let mut perms = attr.permissions();
-    if !perms.readonly() { return Err(e) }
-    perms.set_readonly(false);
-
-    if set_permissions(path, perms).is_err() { return Err(e) }
-    if fs_imp::unlink(path).is_ok() { return Ok(()) }
-
-    // Oops, try to put things back the way we found it
-    let _ = set_permissions(path, attr.permissions());
-    Err(e)
+    fs_imp::unlink(path.as_path())
 }
 
 /// Given a path, query the file system to get information about a file,
@@ -418,6 +437,7 @@ pub fn remove_file<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
 /// This function will return an error if the user lacks the requisite
 /// permissions to perform a `metadata` call on the given `path` or if there
 /// is no entry in the filesystem at the provided path.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn metadata<P: AsPath + ?Sized>(path: &P) -> io::Result<Metadata> {
     fs_imp::stat(path.as_path()).map(Metadata)
 }
@@ -438,6 +458,7 @@ pub fn metadata<P: AsPath + ?Sized>(path: &P) -> io::Result<Metadata> {
 /// the process lacks permissions to view the contents, if `from` and `to`
 /// reside on separate filesystems, or if some other intermittent I/O error
 /// occurs.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn rename<P: AsPath + ?Sized, Q: AsPath + ?Sized>(from: &P, to: &Q)
                                                       -> io::Result<()> {
     fs_imp::rename(from.as_path(), to.as_path())
@@ -468,6 +489,7 @@ pub fn rename<P: AsPath + ?Sized, Q: AsPath + ?Sized>(from: &P, to: &Q)
 /// * The `from` file does not exist
 /// * The current process does not have the permission rights to access
 ///   `from` or write `to`
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn copy<P: AsPath + ?Sized, Q: AsPath + ?Sized>(from: &P, to: &Q)
                                                     -> io::Result<u64> {
     let from = from.as_path();
@@ -490,6 +512,7 @@ pub fn copy<P: AsPath + ?Sized, Q: AsPath + ?Sized>(from: &P, to: &Q)
 ///
 /// The `dst` path will be a link pointing to the `src` path. Note that systems
 /// often require these two paths to both be located on the same filesystem.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn hard_link<P: AsPath + ?Sized, Q: AsPath + ?Sized>(src: &P, dst: &Q)
                                                          -> io::Result<()> {
     fs_imp::link(src.as_path(), dst.as_path())
@@ -498,6 +521,7 @@ pub fn hard_link<P: AsPath + ?Sized, Q: AsPath + ?Sized>(src: &P, dst: &Q)
 /// Creates a new soft link on the filesystem.
 ///
 /// The `dst` path will be a soft link pointing to the `src` path.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn soft_link<P: AsPath + ?Sized, Q: AsPath + ?Sized>(src: &P, dst: &Q)
                                                          -> io::Result<()> {
     fs_imp::symlink(src.as_path(), dst.as_path())
@@ -510,6 +534,7 @@ pub fn soft_link<P: AsPath + ?Sized, Q: AsPath + ?Sized>(src: &P, dst: &Q)
 /// This function will return an error on failure. Failure conditions include
 /// reading a file that does not exist or reading a file that is not a soft
 /// link.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn read_link<P: AsPath + ?Sized>(path: &P) -> io::Result<PathBuf> {
     fs_imp::readlink(path.as_path())
 }
@@ -528,6 +553,7 @@ pub fn read_link<P: AsPath + ?Sized>(path: &P) -> io::Result<PathBuf> {
 ///
 /// This function will return an error if the user lacks permissions to make a
 /// new directory at the provided `path`, or if the directory already exists.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn create_dir<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
     fs_imp::mkdir(path.as_path())
 }
@@ -541,6 +567,7 @@ pub fn create_dir<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
 /// does not already exist and it could not be created otherwise. The specific
 /// error conditions for when a directory is being created (after it is
 /// determined to not exist) are outlined by `fs::create_dir`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn create_dir_all<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
     let path = path.as_path();
     if path.is_dir() { return Ok(()) }
@@ -572,6 +599,7 @@ pub fn create_dir_all<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
 ///
 /// This function will return an error if the user lacks permissions to remove
 /// the directory at the provided `path`, or if the directory isn't empty.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn remove_dir<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
     fs_imp::rmdir(path.as_path())
 }
@@ -585,6 +613,7 @@ pub fn remove_dir<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
 /// # Errors
 ///
 /// See `file::remove_file` and `fs::remove_dir`
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn remove_dir_all<P: AsPath + ?Sized>(path: &P) -> io::Result<()> {
     let path = path.as_path();
     for child in try!(read_dir(path)) {
@@ -637,6 +666,7 @@ fn lstat(path: &Path) -> io::Result<fs_imp::FileAttr> { fs_imp::stat(path) }
 /// This function will return an error if the provided `path` doesn't exist, if
 /// the process lacks permissions to view the contents or if the `path` points
 /// at a non-directory file
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn read_dir<P: AsPath + ?Sized>(path: &P) -> io::Result<ReadDir> {
     fs_imp::readdir(path.as_path()).map(ReadDir)
 }
@@ -649,11 +679,16 @@ pub fn read_dir<P: AsPath + ?Sized>(path: &P) -> io::Result<ReadDir> {
 ///
 /// The iterator will yield instances of `io::Result<DirEntry>`. New errors may
 /// be encountered after an iterator is initially constructed.
+#[unstable(feature = "fs_walk",
+           reason = "the precise semantics and defaults for a recursive walk \
+                     may change and this may end up accounting for files such \
+                     as symlinks differently")]
 pub fn walk_dir<P: AsPath + ?Sized>(path: &P) -> io::Result<WalkDir> {
     let start = try!(read_dir(path));
     Ok(WalkDir { cur: Some(start), stack: Vec::new() })
 }
 
+#[unstable(feature = "fs_walk")]
 impl Iterator for WalkDir {
     type Item = io::Result<DirEntry>;
 
@@ -683,6 +718,9 @@ fn next(&mut self) -> Option<io::Result<DirEntry>> {
 }
 
 /// Utility methods for paths.
+#[unstable(feature = "path_ext",
+           reason = "the precise set of methods exposed on this trait may \
+                     change and some methods may be removed")]
 pub trait PathExt {
     /// Get information on the file, directory, etc at this path.
     ///
@@ -727,6 +765,10 @@ fn is_dir(&self) -> bool {
 /// The file at the path specified will have its last access time set to
 /// `atime` and its modification time set to `mtime`. The times specified should
 /// be in milliseconds.
+#[unstable(feature = "fs_time",
+           reason = "the argument type of u64 is not quite appropriate for \
+                     this function and may change if the standard library \
+                     gains a type to represent a moment in time")]
 pub fn set_file_times<P: AsPath + ?Sized>(path: &P, accessed: u64,
                                           modified: u64) -> io::Result<()> {
     fs_imp::utimes(path.as_path(), accessed, modified)
@@ -752,6 +794,10 @@ pub fn set_file_times<P: AsPath + ?Sized>(path: &P, accessed: u64,
 /// This function will return an error if the provided `path` doesn't exist, if
 /// the process lacks permissions to change the attributes of the file, or if
 /// some other I/O error is encountered.
+#[unstable(feature = "fs",
+           reason = "a more granual ability to set specific permissions may \
+                     be exposed on the Permissions structure itself and this \
+                     method may not always exist")]
 pub fn set_permissions<P: AsPath + ?Sized>(path: &P, perm: Permissions)
                                            -> io::Result<()> {
     fs_imp::set_perm(path.as_path(), perm.0)
@@ -782,7 +828,7 @@ macro_rules! check { ($e:expr) => (
     macro_rules! error { ($e:expr, $s:expr) => (
         match $e {
             Ok(_) => panic!("Unexpected success. Should've been: {:?}", $s),
-            Err(ref err) => assert!(err.to_string().contains($s.as_slice()),
+            Err(ref err) => assert!(err.to_string().contains($s),
                                     format!("`{}` did not contain `{}`", err, $s))
         }
     ) }
@@ -834,7 +880,7 @@ fn file_test_io_smoke_test() {
                 -1|0 => panic!("shouldn't happen"),
                 n => str::from_utf8(&read_buf[..n]).unwrap().to_string()
             };
-            assert_eq!(read_str.as_slice(), message);
+            assert_eq!(read_str, message);
         }
         check!(fs::remove_file(filename));
     }
@@ -1053,7 +1099,7 @@ fn file_test_directoryinfo_readdir() {
             check!(w.write(msg));
         }
         let files = check!(fs::read_dir(dir));
-        let mut mem = [0u8; 4];
+        let mut mem = [0; 4];
         for f in files {
             let f = f.unwrap().path();
             {
@@ -1061,7 +1107,7 @@ fn file_test_directoryinfo_readdir() {
                 check!(check!(File::open(&f)).read(&mut mem));
                 let read_str = str::from_utf8(&mem).unwrap();
                 let expected = format!("{}{}", prefix, n.to_str().unwrap());
-                assert_eq!(expected.as_slice(), read_str);
+                assert_eq!(expected, read_str);
             }
             check!(fs::remove_file(&f));
         }
@@ -1083,7 +1129,7 @@ fn file_test_walk_dir() {
         check!(File::create(&dir2.join("14")));
 
         let files = check!(fs::walk_dir(dir));
-        let mut cur = [0u8; 2];
+        let mut cur = [0; 2];
         for f in files {
             let f = f.unwrap().path();
             let stem = f.file_stem().unwrap().to_str().unwrap();
@@ -1267,6 +1313,8 @@ fn copy_file_preserves_perm_bits() {
         check!(fs::set_permissions(&input, p));
         check!(fs::copy(&input, &out));
         assert!(check!(out.metadata()).permissions().readonly());
+        check!(fs::set_permissions(&input, attr.permissions()));
+        check!(fs::set_permissions(&out, attr.permissions()));
     }
 
     #[cfg(not(windows))] // FIXME(#10264) operation not permitted?
@@ -1350,10 +1398,13 @@ fn chmod_works() {
         let attr = check!(fs::metadata(&file));
         assert!(attr.permissions().readonly());
 
-        match fs::set_permissions(&tmpdir.join("foo"), p) {
-            Ok(..) => panic!("wanted a panic"),
+        match fs::set_permissions(&tmpdir.join("foo"), p.clone()) {
+            Ok(..) => panic!("wanted an error"),
             Err(..) => {}
         }
+
+        p.set_readonly(false);
+        check!(fs::set_permissions(&file, p));
     }
 
     #[test]
@@ -1506,6 +1557,7 @@ fn binary_file() {
     }
 
     #[test]
+    #[cfg(not(windows))]
     fn unlink_readonly() {
         let tmpdir = tmpdir();
         let path = tmpdir.join("file");
index 79bdb35dd48cd3b6ebc1e3f9b5d5d6004be241c0..c1da77a6668f51b513ab79d7428a87aa1bcebd3d 100644 (file)
@@ -9,6 +9,9 @@
 // except according to those terms.
 
 #![unstable(feature = "tempdir", reason = "needs an RFC before stabilization")]
+#![deprecated(since = "1.0.0",
+              reason = "use the `tempdir` crate from crates.io instead")]
+#![allow(deprecated)]
 
 use prelude::v1::*;
 
index 1135609959015d2fbee5d2565a0dd18affd69b7f..3603f1275048d9fda1fe4210f1ad32f0ba7b9db7 100644 (file)
@@ -616,14 +616,14 @@ fn test_short_reads() {
 
     #[test]
     fn read_char_buffered() {
-        let buf = [195u8, 159u8];
+        let buf = [195, 159];
         let reader = BufReader::with_capacity(1, &buf[..]);
         assert_eq!(reader.chars().next(), Some(Ok('ß')));
     }
 
     #[test]
     fn test_chars() {
-        let buf = [195u8, 159u8, b'a'];
+        let buf = [195, 159, b'a'];
         let reader = BufReader::with_capacity(1, &buf[..]);
         let mut it = reader.chars();
         assert_eq!(it.next(), Some(Ok('ß')));
index b1779587528c26b20ca9635cca37e48bbdc851ba..2445f5a7a40403e8c7f15190953b70e48926e77d 100644 (file)
@@ -8,8 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(missing_copy_implementations)]
-
 use prelude::v1::*;
 use io::prelude::*;
 
@@ -32,6 +30,7 @@
 /// Implementations of the I/O traits for `Cursor<T>` are not currently generic
 /// over `T` itself. Instead, specific implementations are provided for various
 /// in-memory buffer types like `Vec<u8>` and `&[u8]`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Cursor<T> {
     inner: T,
     pos: u64,
@@ -39,26 +38,32 @@ pub struct Cursor<T> {
 
 impl<T> Cursor<T> {
     /// Create a new cursor wrapping the provided underlying I/O object.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn new(inner: T) -> Cursor<T> {
         Cursor { pos: 0, inner: inner }
     }
 
     /// Consume this cursor, returning the underlying value.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn into_inner(self) -> T { self.inner }
 
     /// Get a reference to the underlying value in this cursor.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn get_ref(&self) -> &T { &self.inner }
 
     /// Get a mutable reference to the underlying value in this cursor.
     ///
     /// Care should be taken to avoid modifying the internal I/O state of the
     /// underlying value as it may corrupt this cursor's position.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn get_mut(&mut self) -> &mut T { &mut self.inner }
 
     /// Returns the current value of this cursor
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn position(&self) -> u64 { self.pos }
 
     /// Sets the value of this cursor
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn set_position(&mut self, pos: u64) { self.pos = pos; }
 }
 
@@ -83,8 +88,11 @@ fn seek(&mut self, style: SeekFrom) -> io::Result<u64> {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> io::Seek for Cursor<&'a [u8]> { seek!(); }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> io::Seek for Cursor<&'a mut [u8]> { seek!(); }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl io::Seek for Cursor<Vec<u8>> { seek!(); }
 
 macro_rules! read {
@@ -97,8 +105,11 @@ fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Read for Cursor<&'a [u8]> { read!(); }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Read for Cursor<&'a mut [u8]> { read!(); }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Read for Cursor<Vec<u8>> { read!(); }
 
 macro_rules! buffer {
@@ -111,10 +122,14 @@ fn fill_buf(&mut self) -> io::Result<&[u8]> {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> BufRead for Cursor<&'a [u8]> { buffer!(); }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> BufRead for Cursor<&'a mut [u8]> { buffer!(); }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> BufRead for Cursor<Vec<u8>> { buffer!(); }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Write for Cursor<&'a mut [u8]> {
     fn write(&mut self, data: &[u8]) -> io::Result<usize> {
         let pos = cmp::min(self.pos, self.inner.len() as u64);
@@ -125,6 +140,7 @@ fn write(&mut self, data: &[u8]) -> io::Result<usize> {
     fn flush(&mut self) -> io::Result<()> { Ok(()) }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Write for Cursor<Vec<u8>> {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         // Make sure the internal buffer is as least as big as where we
@@ -237,7 +253,7 @@ fn test_buf_writer_error() {
 
     #[test]
     fn test_mem_reader() {
-        let mut reader = Cursor::new(vec!(0u8, 1, 2, 3, 4, 5, 6, 7));
+        let mut reader = Cursor::new(vec!(0, 1, 2, 3, 4, 5, 6, 7));
         let mut buf = [];
         assert_eq!(reader.read(&mut buf), Ok(0));
         assert_eq!(reader.position(), 0);
@@ -259,7 +275,7 @@ fn test_mem_reader() {
 
     #[test]
     fn read_to_end() {
-        let mut reader = Cursor::new(vec!(0u8, 1, 2, 3, 4, 5, 6, 7));
+        let mut reader = Cursor::new(vec!(0, 1, 2, 3, 4, 5, 6, 7));
         let mut v = Vec::new();
         reader.read_to_end(&mut v).ok().unwrap();
         assert_eq!(v, [0, 1, 2, 3, 4, 5, 6, 7]);
@@ -267,7 +283,7 @@ fn read_to_end() {
 
     #[test]
     fn test_slice_reader() {
-        let in_buf = vec![0u8, 1, 2, 3, 4, 5, 6, 7];
+        let in_buf = vec![0, 1, 2, 3, 4, 5, 6, 7];
         let mut reader = &mut in_buf.as_slice();
         let mut buf = [];
         assert_eq!(reader.read(&mut buf), Ok(0));
@@ -289,7 +305,7 @@ fn test_slice_reader() {
 
     #[test]
     fn test_buf_reader() {
-        let in_buf = vec![0u8, 1, 2, 3, 4, 5, 6, 7];
+        let in_buf = vec![0, 1, 2, 3, 4, 5, 6, 7];
         let mut reader = Cursor::new(in_buf.as_slice());
         let mut buf = [];
         assert_eq!(reader.read(&mut buf), Ok(0));
@@ -335,7 +351,7 @@ fn seek_past_end() {
         assert_eq!(r.seek(SeekFrom::Start(10)), Ok(10));
         assert_eq!(r.read(&mut [0]), Ok(0));
 
-        let mut r = Cursor::new(vec!(10u8));
+        let mut r = Cursor::new(vec!(10));
         assert_eq!(r.seek(SeekFrom::Start(10)), Ok(10));
         assert_eq!(r.read(&mut [0]), Ok(0));
 
@@ -347,11 +363,11 @@ fn seek_past_end() {
 
     #[test]
     fn seek_before_0() {
-        let buf = [0xff_u8];
+        let buf = [0xff];
         let mut r = Cursor::new(&buf[..]);
         assert!(r.seek(SeekFrom::End(-2)).is_err());
 
-        let mut r = Cursor::new(vec!(10u8));
+        let mut r = Cursor::new(vec!(10));
         assert!(r.seek(SeekFrom::End(-2)).is_err());
 
         let mut buf = [0];
index 82b69ddebff68630fcf70bf1da0d61c342ed754b..c968415d3efdc5670cdee690fb3cea0c6bf60032 100644 (file)
 // =============================================================================
 // Forwarding implementations
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a, R: Read + ?Sized> Read for &'a mut R {
-    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> { (**self).read(buf) }
-
-    fn read_to_end(&mut self, buf: &mut Vec<u8>) -> io::Result<()> { (**self).read_to_end(buf) }
-
+    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
+        (**self).read(buf)
+    }
+    fn read_to_end(&mut self, buf: &mut Vec<u8>) -> io::Result<()> {
+        (**self).read_to_end(buf)
+    }
     fn read_to_string(&mut self, buf: &mut String) -> io::Result<()> {
         (**self).read_to_string(buf)
     }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a, W: Write + ?Sized> Write for &'a mut W {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> { (**self).write(buf) }
-
-    fn write_all(&mut self, buf: &[u8]) -> io::Result<()> { (**self).write_all(buf) }
-
-    fn write_fmt(&mut self, fmt: fmt::Arguments) -> io::Result<()> { (**self).write_fmt(fmt) }
-
     fn flush(&mut self) -> io::Result<()> { (**self).flush() }
+    fn write_all(&mut self, buf: &[u8]) -> io::Result<()> {
+        (**self).write_all(buf)
+    }
+    fn write_fmt(&mut self, fmt: fmt::Arguments) -> io::Result<()> {
+        (**self).write_fmt(fmt)
+    }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a, S: Seek + ?Sized> Seek for &'a mut S {
     fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> { (**self).seek(pos) }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a, B: BufRead + ?Sized> BufRead for &'a mut B {
     fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() }
-
     fn consume(&mut self, amt: usize) { (**self).consume(amt) }
-
     fn read_until(&mut self, byte: u8, buf: &mut Vec<u8>) -> io::Result<()> {
         (**self).read_until(byte, buf)
     }
-
-    fn read_line(&mut self, buf: &mut String) -> io::Result<()> { (**self).read_line(buf) }
+    fn read_line(&mut self, buf: &mut String) -> io::Result<()> {
+        (**self).read_line(buf)
+    }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<R: Read + ?Sized> Read for Box<R> {
-    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> { (**self).read(buf) }
+    fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
+        (**self).read(buf)
+    }
+    fn read_to_end(&mut self, buf: &mut Vec<u8>) -> io::Result<()> {
+        (**self).read_to_end(buf)
+    }
+    fn read_to_string(&mut self, buf: &mut String) -> io::Result<()> {
+        (**self).read_to_string(buf)
+    }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<W: Write + ?Sized> Write for Box<W> {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> { (**self).write(buf) }
     fn flush(&mut self) -> io::Result<()> { (**self).flush() }
+    fn write_all(&mut self, buf: &[u8]) -> io::Result<()> {
+        (**self).write_all(buf)
+    }
+    fn write_fmt(&mut self, fmt: fmt::Arguments) -> io::Result<()> {
+        (**self).write_fmt(fmt)
+    }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<S: Seek + ?Sized> Seek for Box<S> {
     fn seek(&mut self, pos: SeekFrom) -> io::Result<u64> { (**self).seek(pos) }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<B: BufRead + ?Sized> BufRead for Box<B> {
     fn fill_buf(&mut self) -> io::Result<&[u8]> { (**self).fill_buf() }
     fn consume(&mut self, amt: usize) { (**self).consume(amt) }
+    fn read_until(&mut self, byte: u8, buf: &mut Vec<u8>) -> io::Result<()> {
+        (**self).read_until(byte, buf)
+    }
+    fn read_line(&mut self, buf: &mut String) -> io::Result<()> {
+        (**self).read_line(buf)
+    }
 }
 
 // =============================================================================
 // In-memory buffer implementations
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Read for &'a [u8] {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         let amt = cmp::min(buf.len(), self.len());
@@ -83,11 +114,13 @@ fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> BufRead for &'a [u8] {
     fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(*self) }
     fn consume(&mut self, amt: usize) { *self = &self[amt..]; }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<'a> Write for &'a mut [u8] {
     fn write(&mut self, data: &[u8]) -> io::Result<usize> {
         let amt = cmp::min(data.len(), self.len());
@@ -108,6 +141,7 @@ fn write_all(&mut self, data: &[u8]) -> io::Result<()> {
     fn flush(&mut self) -> io::Result<()> { Ok(()) }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Write for Vec<u8> {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.push_all(buf);
@@ -115,7 +149,7 @@ fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
     }
 
     fn write_all(&mut self, buf: &[u8]) -> io::Result<()> {
-        try!(self.write(buf));
+        self.push_all(buf);
         Ok(())
     }
 
index 5510c0203e6cff3c3af5e7c487cf2ad2112ba909..9137068076b46818d30eb55a5d5cf77d5a0845a9 100644 (file)
@@ -237,11 +237,13 @@ fn read_to_string(&mut self, buf: &mut String) -> Result<()> {
 
 /// Extension methods for all instances of `Read`, typically imported through
 /// `std::io::prelude::*`.
+#[unstable(feature = "io", reason = "may merge into the Read trait")]
 pub trait ReadExt: Read + Sized {
     /// Create a "by reference" adaptor for this instance of `Read`.
     ///
     /// The returned adaptor also implements `Read` and will simply borrow this
     /// current reader.
+    #[stable(feature = "rust1", since = "1.0.0")]
     fn by_ref(&mut self) -> &mut Self { self }
 
     /// Transform this `Read` instance to an `Iterator` over its bytes.
@@ -250,6 +252,7 @@ fn by_ref(&mut self) -> &mut Self { self }
     /// R::Err>`.  The yielded item is `Ok` if a byte was successfully read and
     /// `Err` otherwise for I/O errors. EOF is mapped to returning `None` from
     /// this iterator.
+    #[stable(feature = "rust1", since = "1.0.0")]
     fn bytes(self) -> Bytes<Self> {
         Bytes { inner: self }
     }
@@ -264,6 +267,9 @@ fn bytes(self) -> Bytes<Self> {
     ///
     /// Currently this adaptor will discard intermediate data read, and should
     /// be avoided if this is not desired.
+    #[unstable(feature = "io", reason = "the semantics of a partial read/write \
+                                         of where errors happen is currently \
+                                         unclear and may change")]
     fn chars(self) -> Chars<Self> {
         Chars { inner: self }
     }
@@ -273,6 +279,7 @@ fn chars(self) -> Chars<Self> {
     /// The returned `Read` instance will first read all bytes from this object
     /// until EOF is encountered. Afterwards the output is equivalent to the
     /// output of `next`.
+    #[stable(feature = "rust1", since = "1.0.0")]
     fn chain<R: Read>(self, next: R) -> Chain<Self, R> {
         Chain { first: self, second: next, done_first: false }
     }
@@ -283,6 +290,7 @@ fn chain<R: Read>(self, next: R) -> Chain<Self, R> {
     /// `limit` bytes, after which it will always return EOF (`Ok(0)`). Any
     /// read errors will not count towards the number of bytes read and future
     /// calls to `read` may succeed.
+    #[stable(feature = "rust1", since = "1.0.0")]
     fn take(self, limit: u64) -> Take<Self> {
         Take { inner: self, limit: limit }
     }
@@ -293,6 +301,9 @@ fn take(self, limit: u64) -> Take<Self> {
     /// Whenever the returned `Read` instance is read it will write the read
     /// data to `out`. The current semantics of this implementation imply that
     /// a `write` error will not report how much data was initially read.
+    #[unstable(feature = "io", reason = "the semantics of a partial read/write \
+                                         of where errors happen is currently \
+                                         unclear and may change")]
     fn tee<W: Write>(self, out: W) -> Tee<Self, W> {
         Tee { reader: self, writer: out }
     }
@@ -415,11 +426,13 @@ fn write_str(&mut self, s: &str) -> fmt::Result {
 
 /// Extension methods for all instances of `Write`, typically imported through
 /// `std::io::prelude::*`.
+#[unstable(feature = "io", reason = "may merge into the Read trait")]
 pub trait WriteExt: Write + Sized {
     /// Create a "by reference" adaptor for this instance of `Write`.
     ///
     /// The returned adaptor also implements `Write` and will simply borrow this
     /// current writer.
+    #[stable(feature = "rust1", since = "1.0.0")]
     fn by_ref(&mut self) -> &mut Self { self }
 
     /// Creates a new writer which will write all data to both this writer and
@@ -430,11 +443,15 @@ fn by_ref(&mut self) -> &mut Self { self }
     /// implementation do not precisely track where errors happen. For example
     /// an error on the second call to `write` will not report that the first
     /// call to `write` succeeded.
+    #[unstable(feature = "io", reason = "the semantics of a partial read/write \
+                                         of where errors happen is currently \
+                                         unclear and may change")]
     fn broadcast<W: Write>(self, other: W) -> Broadcast<Self, W> {
         Broadcast { first: self, second: other }
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<T: Write> WriteExt for T {}
 
 /// An object implementing `Seek` internally has some form of cursor which can
@@ -592,6 +609,8 @@ pub trait BufReadExt: BufRead + Sized {
     ///
     /// This function will yield errors whenever `read_until` would have also
     /// yielded an error.
+    #[unstable(feature = "io", reason = "may be renamed to not conflict with \
+                                         SliceExt::split")]
     fn split(self, byte: u8) -> Split<Self> {
         Split { buf: self, delim: byte }
     }
@@ -604,11 +623,13 @@ fn split(self, byte: u8) -> Split<Self> {
     ///
     /// This function will yield errors whenever `read_string` would have also
     /// yielded an error.
+    #[stable(feature = "rust1", since = "1.0.0")]
     fn lines(self) -> Lines<Self> {
         Lines { buf: self }
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<T: BufRead> BufReadExt for T {}
 
 /// A `Write` adaptor which will write data to multiple locations.
@@ -635,12 +656,14 @@ fn flush(&mut self) -> Result<()> {
 /// Adaptor to chain together two instances of `Read`.
 ///
 /// For more information, see `ReadExt::chain`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Chain<T, U> {
     first: T,
     second: U,
     done_first: bool,
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<T: Read, U: Read> Read for Chain<T, U> {
     fn read(&mut self, buf: &mut [u8]) -> Result<usize> {
         if !self.done_first {
@@ -656,11 +679,13 @@ fn read(&mut self, buf: &mut [u8]) -> Result<usize> {
 /// Reader adaptor which limits the bytes read from an underlying reader.
 ///
 /// For more information, see `ReadExt::take`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Take<T> {
     inner: T,
     limit: u64,
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<T> Take<T> {
     /// Returns the number of bytes that can be read before this instance will
     /// return EOF.
@@ -669,9 +694,11 @@ impl<T> Take<T> {
     ///
     /// This instance may reach EOF after reading fewer bytes than indicated by
     /// this method if the underlying `Read` instance reaches EOF.
+    #[stable(feature = "rust1", since = "1.0.0")]
     pub fn limit(&self) -> u64 { self.limit }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<T: Read> Read for Take<T> {
     fn read(&mut self, buf: &mut [u8]) -> Result<usize> {
         // Don't call into inner reader at all at EOF because it may still block
@@ -686,6 +713,7 @@ fn read(&mut self, buf: &mut [u8]) -> Result<usize> {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<T: BufRead> BufRead for Take<T> {
     fn fill_buf(&mut self) -> Result<&[u8]> {
         let buf = try!(self.inner.fill_buf());
@@ -721,10 +749,12 @@ fn read(&mut self, buf: &mut [u8]) -> Result<usize> {
 /// A bridge from implementations of `Read` to an `Iterator` of `u8`.
 ///
 /// See `ReadExt::bytes` for more information.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Bytes<R> {
     inner: R,
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<R: Read> Iterator for Bytes<R> {
     type Item = Result<u8>;
 
@@ -845,10 +875,12 @@ fn next(&mut self) -> Option<Result<Vec<u8>>> {
 /// byte.
 ///
 /// See `BufReadExt::lines` for more information.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Lines<B> {
     buf: B,
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl<B: BufRead> Iterator for Lines<B> {
     type Item = Result<String>;
 
@@ -975,7 +1007,7 @@ fn take_eof() {
         struct R;
 
         impl Read for R {
-            fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
+            fn read(&mut self, _: &mut [u8]) -> io::Result<usize> {
                 Err(io::Error::new(io::ErrorKind::Other, "", None))
             }
         }
index 61ad9905771a406b328d8de4161f2157a038b4b4..4027f741654b66bbbf57c9644f06e66bb7866b30 100644 (file)
@@ -157,9 +157,6 @@ fn read_to_string(&mut self, buf: &mut String) -> io::Result<()> {
 
 impl<'a> Read for StdinLock<'a> {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
-        // Flush stdout so that weird issues like a print!'d prompt not being
-        // shown until after the user hits enter.
-        drop(stdout().flush());
         self.inner.read(buf)
     }
 }
index 3d342137c62ddd3d3a340811384d1dc2e166efd8..20426025257c3761a8bba56c4281f5093ac49ccb 100644 (file)
@@ -12,7 +12,7 @@
 
 use prelude::v1::*;
 
-use io::{self, Read, Write, ErrorKind};
+use io::{self, Read, Write, ErrorKind, BufRead};
 
 /// Copies the entire contents of a reader into a writer.
 ///
@@ -27,6 +27,7 @@
 /// This function will return an error immediately if any call to `read` or
 /// `write` returns an error. All instances of `ErrorKind::Interrupted` are
 /// handled by this function and the underlying operation is retried.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn copy<R: Read, W: Write>(r: &mut R, w: &mut W) -> io::Result<u64> {
     let mut buf = [0; super::DEFAULT_BUF_SIZE];
     let mut written = 0;
@@ -43,26 +44,37 @@ pub fn copy<R: Read, W: Write>(r: &mut R, w: &mut W) -> io::Result<u64> {
 }
 
 /// A reader which is always at EOF.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Empty { _priv: () }
 
 /// Creates an instance of an empty reader.
 ///
 /// All reads from the returned reader will return `Ok(0)`.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn empty() -> Empty { Empty { _priv: () } }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Read for Empty {
     fn read(&mut self, _buf: &mut [u8]) -> io::Result<usize> { Ok(0) }
 }
+#[stable(feature = "rust1", since = "1.0.0")]
+impl BufRead for Empty {
+    fn fill_buf(&mut self) -> io::Result<&[u8]> { Ok(&[]) }
+    fn consume(&mut self, _n: usize) {}
+}
 
 /// A reader which infinitely yields one byte.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Repeat { byte: u8 }
 
 /// Creates an instance of a reader that infinitely repeats one byte.
 ///
 /// All reads from this reader will succeed by filling the specified buffer with
 /// the given byte.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn repeat(byte: u8) -> Repeat { Repeat { byte: byte } }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Read for Repeat {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         for slot in buf.iter_mut() {
@@ -73,14 +85,17 @@ fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
 }
 
 /// A writer which will move data into the void.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub struct Sink { _priv: () }
 
 /// Creates an instance of a writer which will successfully consume all data.
 ///
 /// All calls to `write` on the returned instance will return `Ok(buf.len())`
 /// and the contents of the buffer will not be inspected.
+#[stable(feature = "rust1", since = "1.0.0")]
 pub fn sink() -> Sink { Sink { _priv: () } }
 
+#[stable(feature = "rust1", since = "1.0.0")]
 impl Write for Sink {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> { Ok(buf.len()) }
     fn flush(&mut self) -> io::Result<()> { Ok(()) }
index 7957bc35b76b5c3e90507df79c6b624e9b2c6326..ce14967090e0fb40c8208fc65b9212722873c189 100644 (file)
@@ -94,7 +94,8 @@
 //! to all code by default. [`macros`](macros/index.html) contains
 //! all the standard macros, such as `assert!`, `panic!`, `println!`,
 //! and `format!`, also available to all Rust code.
-
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "std"]
 #![stable(feature = "rust1", since = "1.0.0")]
 #![staged_api]
 #![feature(unsafe_no_drop_flag)]
 #![feature(macro_reexport)]
 #![feature(hash)]
+#![feature(int_uint)]
 #![feature(unique)]
-#![cfg_attr(test, feature(test, rustc_private, env))]
+#![feature(allow_internal_unstable)]
+#![cfg_attr(test, feature(test, rustc_private))]
 
 // Don't link to std. We are std.
 #![feature(no_std)]
index f16f501c46a19006ff789b01839a71f054684528..101aae3eb248b161a70f9744ca1137129194a874 100644 (file)
@@ -293,7 +293,7 @@ macro_rules! try_opt {
         }
 
         // split the string by ':' and convert the second part to u16
-        let mut parts_iter = self.rsplitn(2, ':');
+        let mut parts_iter = self.rsplitn(1, ':');
         let port_str = try_opt!(parts_iter.next(), "invalid socket address");
         let host = try_opt!(parts_iter.next(), "invalid socket address");
         let port: u16 = try_opt!(port_str.parse().ok(), "invalid port value");
@@ -562,7 +562,7 @@ fn to_socket_addr_socketaddr() {
     #[test]
     fn to_socket_addr_ipaddr_u16() {
         let a = IpAddr::new_v4(77, 88, 21, 11);
-        let p = 12345u16;
+        let p = 12345;
         let e = SocketAddr::new(a, p);
         assert_eq!(Ok(vec![e]), tsa((a, p)));
     }
@@ -570,13 +570,13 @@ fn to_socket_addr_ipaddr_u16() {
     #[test]
     fn to_socket_addr_str_u16() {
         let a = SocketAddr::new(IpAddr::new_v4(77, 88, 21, 11), 24352);
-        assert_eq!(Ok(vec![a]), tsa(("77.88.21.11", 24352u16)));
+        assert_eq!(Ok(vec![a]), tsa(("77.88.21.11", 24352)));
 
         let a = SocketAddr::new(IpAddr::new_v6(0x2a02, 0x6b8, 0, 1, 0, 0, 0, 1), 53);
         assert_eq!(Ok(vec![a]), tsa(("2a02:6b8:0:1::1", 53)));
 
         let a = SocketAddr::new(IpAddr::new_v4(127, 0, 0, 1), 23924);
-        assert!(tsa(("localhost", 23924u16)).unwrap().contains(&a));
+        assert!(tsa(("localhost", 23924)).unwrap().contains(&a));
     }
 
     #[test]
@@ -590,4 +590,10 @@ fn to_socket_addr_str() {
         let a = SocketAddr::new(IpAddr::new_v4(127, 0, 0, 1), 23924);
         assert!(tsa("localhost:23924").unwrap().contains(&a));
     }
+
+    #[test]
+    #[cfg(not(windows))]
+    fn to_socket_addr_str_bad() {
+        assert!(tsa("1200::AB00:1234::2552:7777:1313:34300").is_err());
+    }
 }
index e82dc88cddd7b7036989232092f2e781f43a4617..aa54a432d625ba803a2dfec2a3e8110ef25182e7 100644 (file)
@@ -136,7 +136,7 @@ fn parse_digit(c: char, radix: u8) -> Option<u8> {
     }
 
     fn read_number_impl(&mut self, radix: u8, max_digits: u32, upto: u32) -> Option<u32> {
-        let mut r = 0u32;
+        let mut r = 0;
         let mut digit_count = 0;
         loop {
             match self.read_digit(radix) {
@@ -164,7 +164,7 @@ fn read_number(&mut self, radix: u8, max_digits: u32, upto: u32) -> Option<u32>
     }
 
     fn read_ipv4_addr_impl(&mut self) -> Option<Ipv4Addr> {
-        let mut bs = [0u8; 4];
+        let mut bs = [0; 4];
         let mut i = 0;
         while i < 4 {
             if i != 0 && self.read_given_char('.').is_none() {
@@ -189,7 +189,7 @@ fn read_ipv4_addr(&mut self) -> Option<Ipv4Addr> {
     fn read_ipv6_addr_impl(&mut self) -> Option<Ipv6Addr> {
         fn ipv6_addr_from_head_tail(head: &[u16], tail: &[u16]) -> Ipv6Addr {
             assert!(head.len() + tail.len() <= 8);
-            let mut gs = [0u16; 8];
+            let mut gs = [0; 8];
             gs.clone_from_slice(head);
             gs[(8 - tail.len()) .. 8].clone_from_slice(tail);
             Ipv6Addr::new(gs[0], gs[1], gs[2], gs[3], gs[4], gs[5], gs[6], gs[7])
@@ -231,7 +231,7 @@ fn ipv6_addr_from_head_tail(head: &[u16], tail: &[u16]) -> Ipv6Addr {
             (i, false)
         }
 
-        let mut head = [0u16; 8];
+        let mut head = [0; 8];
         let (head_size, head_ipv4) = read_groups(self, &mut head, 8);
 
         if head_size == 8 {
@@ -250,7 +250,7 @@ fn ipv6_addr_from_head_tail(head: &[u16], tail: &[u16]) -> Ipv6Addr {
             return None;
         }
 
-        let mut tail = [0u16; 8];
+        let mut tail = [0; 8];
         let (tail_size, _) = read_groups(self, &mut tail, 8 - head_size);
         Some(ipv6_addr_from_head_tail(&head[..head_size], &tail[..tail_size]))
     }
index f99cd2b1d1be9eeb59887f081817a4787236af95..fd723ea13e9629e8f94c9c0bb6933430d201a5e6 100644 (file)
@@ -233,13 +233,13 @@ macro_rules! t {
         }
     }
 
-    // FIXME #11530 this fails on android because tests are run as root
-    #[cfg_attr(any(windows, target_os = "android"), ignore)]
     #[test]
     fn bind_error() {
-        match TcpListener::bind("0.0.0.0:1") {
+        match TcpListener::bind("1.1.1.1:9999") {
             Ok(..) => panic!(),
-            Err(e) => assert_eq!(e.kind(), ErrorKind::PermissionDenied),
+            Err(e) =>
+                // EADDRNOTAVAIL is mapped to ConnectionRefused
+                assert_eq!(e.kind(), ErrorKind::ConnectionRefused),
         }
     }
 
@@ -425,7 +425,7 @@ fn connect(i: usize, addr: SocketAddr) {
 
     #[test]
     fn multiple_connect_interleaved_lazy_schedule_ip4() {
-        static MAX: usize = 10;
+        const MAX: usize = 10;
         each_ip(&mut |addr| {
             let acceptor = t!(TcpListener::bind(&addr));
 
index 7d15a16309e5b3f481a52440fa1df25b44d614da..969dd35ba228878ea1f90aebd5eb10f397bc9960 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
@@ -468,6 +468,11 @@ mod tests {
     use num::*;
     use num::FpCategory as Fp;
 
+    #[test]
+    fn test_num_f32() {
+        test_num(10f32, 2f32);
+    }
+
     #[test]
     fn test_min_nan() {
         assert_eq!(NAN.min(2.0), 2.0);
@@ -481,8 +486,163 @@ fn test_max_nan() {
     }
 
     #[test]
-    fn test_num_f32() {
-        test_num(10f32, 2f32);
+    fn test_nan() {
+        let nan: f32 = Float::nan();
+        assert!(nan.is_nan());
+        assert!(!nan.is_infinite());
+        assert!(!nan.is_finite());
+        assert!(!nan.is_normal());
+        assert!(!nan.is_positive());
+        assert!(!nan.is_negative());
+        assert_eq!(Fp::Nan, nan.classify());
+    }
+
+    #[test]
+    fn test_infinity() {
+        let inf: f32 = Float::infinity();
+        assert!(inf.is_infinite());
+        assert!(!inf.is_finite());
+        assert!(inf.is_positive());
+        assert!(!inf.is_negative());
+        assert!(!inf.is_nan());
+        assert!(!inf.is_normal());
+        assert_eq!(Fp::Infinite, inf.classify());
+    }
+
+    #[test]
+    fn test_neg_infinity() {
+        let neg_inf: f32 = Float::neg_infinity();
+        assert!(neg_inf.is_infinite());
+        assert!(!neg_inf.is_finite());
+        assert!(!neg_inf.is_positive());
+        assert!(neg_inf.is_negative());
+        assert!(!neg_inf.is_nan());
+        assert!(!neg_inf.is_normal());
+        assert_eq!(Fp::Infinite, neg_inf.classify());
+    }
+
+    #[test]
+    fn test_zero() {
+        let zero: f32 = Float::zero();
+        assert_eq!(0.0, zero);
+        assert!(!zero.is_infinite());
+        assert!(zero.is_finite());
+        assert!(zero.is_positive());
+        assert!(!zero.is_negative());
+        assert!(!zero.is_nan());
+        assert!(!zero.is_normal());
+        assert_eq!(Fp::Zero, zero.classify());
+    }
+
+    #[test]
+    fn test_neg_zero() {
+        let neg_zero: f32 = Float::neg_zero();
+        assert_eq!(0.0, neg_zero);
+        assert!(!neg_zero.is_infinite());
+        assert!(neg_zero.is_finite());
+        assert!(!neg_zero.is_positive());
+        assert!(neg_zero.is_negative());
+        assert!(!neg_zero.is_nan());
+        assert!(!neg_zero.is_normal());
+        assert_eq!(Fp::Zero, neg_zero.classify());
+    }
+
+    #[test]
+    fn test_one() {
+        let one: f32 = Float::one();
+        assert_eq!(1.0, one);
+        assert!(!one.is_infinite());
+        assert!(one.is_finite());
+        assert!(one.is_positive());
+        assert!(!one.is_negative());
+        assert!(!one.is_nan());
+        assert!(one.is_normal());
+        assert_eq!(Fp::Normal, one.classify());
+    }
+
+    #[test]
+    fn test_is_nan() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert!(nan.is_nan());
+        assert!(!0.0f32.is_nan());
+        assert!(!5.3f32.is_nan());
+        assert!(!(-10.732f32).is_nan());
+        assert!(!inf.is_nan());
+        assert!(!neg_inf.is_nan());
+    }
+
+    #[test]
+    fn test_is_infinite() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert!(!nan.is_infinite());
+        assert!(inf.is_infinite());
+        assert!(neg_inf.is_infinite());
+        assert!(!0.0f32.is_infinite());
+        assert!(!42.8f32.is_infinite());
+        assert!(!(-109.2f32).is_infinite());
+    }
+
+    #[test]
+    fn test_is_finite() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert!(!nan.is_finite());
+        assert!(!inf.is_finite());
+        assert!(!neg_inf.is_finite());
+        assert!(0.0f32.is_finite());
+        assert!(42.8f32.is_finite());
+        assert!((-109.2f32).is_finite());
+    }
+
+    #[test]
+    fn test_is_normal() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        let zero: f32 = Float::zero();
+        let neg_zero: f32 = Float::neg_zero();
+        assert!(!nan.is_normal());
+        assert!(!inf.is_normal());
+        assert!(!neg_inf.is_normal());
+        assert!(!zero.is_normal());
+        assert!(!neg_zero.is_normal());
+        assert!(1f32.is_normal());
+        assert!(1e-37f32.is_normal());
+        assert!(!1e-38f32.is_normal());
+    }
+
+    #[test]
+    fn test_classify() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        let zero: f32 = Float::zero();
+        let neg_zero: f32 = Float::neg_zero();
+        assert_eq!(nan.classify(), Fp::Nan);
+        assert_eq!(inf.classify(), Fp::Infinite);
+        assert_eq!(neg_inf.classify(), Fp::Infinite);
+        assert_eq!(zero.classify(), Fp::Zero);
+        assert_eq!(neg_zero.classify(), Fp::Zero);
+        assert_eq!(1f32.classify(), Fp::Normal);
+        assert_eq!(1e-37f32.classify(), Fp::Normal);
+        assert_eq!(1e-38f32.classify(), Fp::Subnormal);
+    }
+
+    #[test]
+    fn test_integer_decode() {
+        assert_eq!(3.14159265359f32.integer_decode(), (13176795, -22, 1));
+        assert_eq!((-8573.5918555f32).integer_decode(), (8779358, -10, -1));
+        assert_eq!(2f32.powf(100.0).integer_decode(), (8388608, 77, 1));
+        assert_eq!(0f32.integer_decode(), (0, -150, 1));
+        assert_eq!((-0f32).integer_decode(), (0, -150, -1));
+        assert_eq!(INFINITY.integer_decode(), (8388608, 105, 1));
+        assert_eq!(NEG_INFINITY.integer_decode(), (8388608, 105, -1));
+        assert_eq!(NAN.integer_decode(), (12582912, 105, 1));
     }
 
     #[test]
@@ -555,6 +715,140 @@ fn test_fract() {
         assert_approx_eq!((-1.7f32).fract(), -0.7f32);
     }
 
+    #[test]
+    fn test_abs() {
+        assert_eq!(INFINITY.abs(), INFINITY);
+        assert_eq!(1f32.abs(), 1f32);
+        assert_eq!(0f32.abs(), 0f32);
+        assert_eq!((-0f32).abs(), 0f32);
+        assert_eq!((-1f32).abs(), 1f32);
+        assert_eq!(NEG_INFINITY.abs(), INFINITY);
+        assert_eq!((1f32/NEG_INFINITY).abs(), 0f32);
+        assert!(NAN.abs().is_nan());
+    }
+
+    #[test]
+    fn test_signum() {
+        assert_eq!(INFINITY.signum(), 1f32);
+        assert_eq!(1f32.signum(), 1f32);
+        assert_eq!(0f32.signum(), 1f32);
+        assert_eq!((-0f32).signum(), -1f32);
+        assert_eq!((-1f32).signum(), -1f32);
+        assert_eq!(NEG_INFINITY.signum(), -1f32);
+        assert_eq!((1f32/NEG_INFINITY).signum(), -1f32);
+        assert!(NAN.signum().is_nan());
+    }
+
+    #[test]
+    fn test_is_positive() {
+        assert!(INFINITY.is_positive());
+        assert!(1f32.is_positive());
+        assert!(0f32.is_positive());
+        assert!(!(-0f32).is_positive());
+        assert!(!(-1f32).is_positive());
+        assert!(!NEG_INFINITY.is_positive());
+        assert!(!(1f32/NEG_INFINITY).is_positive());
+        assert!(!NAN.is_positive());
+    }
+
+    #[test]
+    fn test_is_negative() {
+        assert!(!INFINITY.is_negative());
+        assert!(!1f32.is_negative());
+        assert!(!0f32.is_negative());
+        assert!((-0f32).is_negative());
+        assert!((-1f32).is_negative());
+        assert!(NEG_INFINITY.is_negative());
+        assert!((1f32/NEG_INFINITY).is_negative());
+        assert!(!NAN.is_negative());
+    }
+
+    #[test]
+    fn test_mul_add() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_approx_eq!(12.3f32.mul_add(4.5, 6.7), 62.05);
+        assert_approx_eq!((-12.3f32).mul_add(-4.5, -6.7), 48.65);
+        assert_approx_eq!(0.0f32.mul_add(8.9, 1.2), 1.2);
+        assert_approx_eq!(3.4f32.mul_add(-0.0, 5.6), 5.6);
+        assert!(nan.mul_add(7.8, 9.0).is_nan());
+        assert_eq!(inf.mul_add(7.8, 9.0), inf);
+        assert_eq!(neg_inf.mul_add(7.8, 9.0), neg_inf);
+        assert_eq!(8.9f32.mul_add(inf, 3.2), inf);
+        assert_eq!((-3.2f32).mul_add(2.4, neg_inf), neg_inf);
+    }
+
+    #[test]
+    fn test_recip() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_eq!(1.0f32.recip(), 1.0);
+        assert_eq!(2.0f32.recip(), 0.5);
+        assert_eq!((-0.4f32).recip(), -2.5);
+        assert_eq!(0.0f32.recip(), inf);
+        assert!(nan.recip().is_nan());
+        assert_eq!(inf.recip(), 0.0);
+        assert_eq!(neg_inf.recip(), 0.0);
+    }
+
+    #[test]
+    fn test_powi() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_eq!(1.0f32.powi(1), 1.0);
+        assert_approx_eq!((-3.1f32).powi(2), 9.61);
+        assert_approx_eq!(5.9f32.powi(-2), 0.028727);
+        assert_eq!(8.3f32.powi(0), 1.0);
+        assert!(nan.powi(2).is_nan());
+        assert_eq!(inf.powi(3), inf);
+        assert_eq!(neg_inf.powi(2), inf);
+    }
+
+    #[test]
+    fn test_powf() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_eq!(1.0f32.powf(1.0), 1.0);
+        assert_approx_eq!(3.4f32.powf(4.5), 246.408218);
+        assert_approx_eq!(2.7f32.powf(-3.2), 0.041652);
+        assert_approx_eq!((-3.1f32).powf(2.0), 9.61);
+        assert_approx_eq!(5.9f32.powf(-2.0), 0.028727);
+        assert_eq!(8.3f32.powf(0.0), 1.0);
+        assert!(nan.powf(2.0).is_nan());
+        assert_eq!(inf.powf(2.0), inf);
+        assert_eq!(neg_inf.powf(3.0), neg_inf);
+    }
+
+    #[test]
+    fn test_sqrt_domain() {
+        assert!(NAN.sqrt().is_nan());
+        assert!(NEG_INFINITY.sqrt().is_nan());
+        assert!((-1.0f32).sqrt().is_nan());
+        assert_eq!((-0.0f32).sqrt(), -0.0);
+        assert_eq!(0.0f32.sqrt(), 0.0);
+        assert_eq!(1.0f32.sqrt(), 1.0);
+        assert_eq!(INFINITY.sqrt(), INFINITY);
+    }
+
+    #[test]
+    fn test_rsqrt() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert!(nan.rsqrt().is_nan());
+        assert_eq!(inf.rsqrt(), 0.0);
+        assert!(neg_inf.rsqrt().is_nan());
+        assert!((-1.0f32).rsqrt().is_nan());
+        assert_eq!((-0.0f32).rsqrt(), neg_inf);
+        assert_eq!(0.0f32.rsqrt(), inf);
+        assert_eq!(1.0f32.rsqrt(), 1.0);
+        assert_eq!(4.0f32.rsqrt(), 0.5);
+    }
+
     #[test]
     fn test_exp() {
         assert_eq!(1.0, 0.0f32.exp());
@@ -582,6 +876,172 @@ fn test_exp2() {
         assert!(nan.exp2().is_nan());
     }
 
+    #[test]
+    fn test_ln() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_approx_eq!(1.0f32.exp().ln(), 1.0);
+        assert!(nan.ln().is_nan());
+        assert_eq!(inf.ln(), inf);
+        assert!(neg_inf.ln().is_nan());
+        assert!((-2.3f32).ln().is_nan());
+        assert_eq!((-0.0f32).ln(), neg_inf);
+        assert_eq!(0.0f32.ln(), neg_inf);
+        assert_approx_eq!(4.0f32.ln(), 1.386294);
+    }
+
+    #[test]
+    fn test_log() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_eq!(10.0f32.log(10.0), 1.0);
+        assert_approx_eq!(2.3f32.log(3.5), 0.664858);
+        assert_eq!(1.0f32.exp().log(1.0.exp()), 1.0);
+        assert!(1.0f32.log(1.0).is_nan());
+        assert!(1.0f32.log(-13.9).is_nan());
+        assert!(nan.log(2.3).is_nan());
+        assert_eq!(inf.log(10.0), inf);
+        assert!(neg_inf.log(8.8).is_nan());
+        assert!((-2.3f32).log(0.1).is_nan());
+        assert_eq!((-0.0f32).log(2.0), neg_inf);
+        assert_eq!(0.0f32.log(7.0), neg_inf);
+    }
+
+    #[test]
+    fn test_log2() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_approx_eq!(10.0f32.log2(), 3.321928);
+        assert_approx_eq!(2.3f32.log2(), 1.201634);
+        assert_approx_eq!(1.0f32.exp().log2(), 1.442695);
+        assert!(nan.log2().is_nan());
+        assert_eq!(inf.log2(), inf);
+        assert!(neg_inf.log2().is_nan());
+        assert!((-2.3f32).log2().is_nan());
+        assert_eq!((-0.0f32).log2(), neg_inf);
+        assert_eq!(0.0f32.log2(), neg_inf);
+    }
+
+    #[test]
+    fn test_log10() {
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_eq!(10.0f32.log10(), 1.0);
+        assert_approx_eq!(2.3f32.log10(), 0.361728);
+        assert_approx_eq!(1.0f32.exp().log10(), 0.434294);
+        assert_eq!(1.0f32.log10(), 0.0);
+        assert!(nan.log10().is_nan());
+        assert_eq!(inf.log10(), inf);
+        assert!(neg_inf.log10().is_nan());
+        assert!((-2.3f32).log10().is_nan());
+        assert_eq!((-0.0f32).log10(), neg_inf);
+        assert_eq!(0.0f32.log10(), neg_inf);
+    }
+
+    #[test]
+    fn test_to_degrees() {
+        let pi: f32 = consts::PI;
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_eq!(0.0f32.to_degrees(), 0.0);
+        assert_approx_eq!((-5.8f32).to_degrees(), -332.315521);
+        assert_eq!(pi.to_degrees(), 180.0);
+        assert!(nan.to_degrees().is_nan());
+        assert_eq!(inf.to_degrees(), inf);
+        assert_eq!(neg_inf.to_degrees(), neg_inf);
+    }
+
+    #[test]
+    fn test_to_radians() {
+        let pi: f32 = consts::PI;
+        let nan: f32 = Float::nan();
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        assert_eq!(0.0f32.to_radians(), 0.0);
+        assert_approx_eq!(154.6f32.to_radians(), 2.698279);
+        assert_approx_eq!((-332.31f32).to_radians(), -5.799903);
+        assert_eq!(180.0f32.to_radians(), pi);
+        assert!(nan.to_radians().is_nan());
+        assert_eq!(inf.to_radians(), inf);
+        assert_eq!(neg_inf.to_radians(), neg_inf);
+    }
+
+    #[test]
+    fn test_ldexp() {
+        // We have to use from_str until base-2 exponents
+        // are supported in floating-point literals
+        let f1: f32 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
+        let f2: f32 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
+        let f3: f32 = FromStrRadix::from_str_radix("1.Cp-12", 16).unwrap();
+        assert_eq!(Float::ldexp(1f32, -123), f1);
+        assert_eq!(Float::ldexp(1f32, -111), f2);
+        assert_eq!(Float::ldexp(1.75f32, -12), f3);
+
+        assert_eq!(Float::ldexp(0f32, -123), 0f32);
+        assert_eq!(Float::ldexp(-0f32, -123), -0f32);
+
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        let nan: f32 = Float::nan();
+        assert_eq!(Float::ldexp(inf, -123), inf);
+        assert_eq!(Float::ldexp(neg_inf, -123), neg_inf);
+        assert!(Float::ldexp(nan, -123).is_nan());
+    }
+
+    #[test]
+    fn test_frexp() {
+        // We have to use from_str until base-2 exponents
+        // are supported in floating-point literals
+        let f1: f32 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
+        let f2: f32 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
+        let f3: f32 = FromStrRadix::from_str_radix("1.Cp-123", 16).unwrap();
+        let (x1, exp1) = f1.frexp();
+        let (x2, exp2) = f2.frexp();
+        let (x3, exp3) = f3.frexp();
+        assert_eq!((x1, exp1), (0.5f32, -122));
+        assert_eq!((x2, exp2), (0.5f32, -110));
+        assert_eq!((x3, exp3), (0.875f32, -122));
+        assert_eq!(Float::ldexp(x1, exp1), f1);
+        assert_eq!(Float::ldexp(x2, exp2), f2);
+        assert_eq!(Float::ldexp(x3, exp3), f3);
+
+        assert_eq!(0f32.frexp(), (0f32, 0));
+        assert_eq!((-0f32).frexp(), (-0f32, 0));
+    }
+
+    #[test] #[cfg_attr(windows, ignore)] // FIXME #8755
+    fn test_frexp_nowin() {
+        let inf: f32 = Float::infinity();
+        let neg_inf: f32 = Float::neg_infinity();
+        let nan: f32 = Float::nan();
+        assert_eq!(match inf.frexp() { (x, _) => x }, inf);
+        assert_eq!(match neg_inf.frexp() { (x, _) => x }, neg_inf);
+        assert!(match nan.frexp() { (x, _) => x.is_nan() })
+    }
+
+    #[test]
+    fn test_abs_sub() {
+        assert_eq!((-1f32).abs_sub(1f32), 0f32);
+        assert_eq!(1f32.abs_sub(1f32), 0f32);
+        assert_eq!(1f32.abs_sub(0f32), 1f32);
+        assert_eq!(1f32.abs_sub(-1f32), 2f32);
+        assert_eq!(NEG_INFINITY.abs_sub(0f32), 0f32);
+        assert_eq!(INFINITY.abs_sub(1f32), INFINITY);
+        assert_eq!(0f32.abs_sub(NEG_INFINITY), INFINITY);
+        assert_eq!(0f32.abs_sub(INFINITY), 0f32);
+    }
+
+    #[test]
+    fn test_abs_sub_nowin() {
+        assert!(NAN.abs_sub(-1f32).is_nan());
+        assert!(1f32.abs_sub(NAN).is_nan());
+    }
+
     #[test]
     fn test_asinh() {
         assert_eq!(0.0f32.asinh(), 0.0f32);
@@ -674,174 +1134,4 @@ fn test_real_consts() {
         assert_approx_eq!(ln_2, 2f32.ln());
         assert_approx_eq!(ln_10, 10f32.ln());
     }
-
-    #[test]
-    pub fn test_abs() {
-        assert_eq!(INFINITY.abs(), INFINITY);
-        assert_eq!(1f32.abs(), 1f32);
-        assert_eq!(0f32.abs(), 0f32);
-        assert_eq!((-0f32).abs(), 0f32);
-        assert_eq!((-1f32).abs(), 1f32);
-        assert_eq!(NEG_INFINITY.abs(), INFINITY);
-        assert_eq!((1f32/NEG_INFINITY).abs(), 0f32);
-        assert!(NAN.abs().is_nan());
-    }
-
-    #[test]
-    fn test_abs_sub() {
-        assert_eq!((-1f32).abs_sub(1f32), 0f32);
-        assert_eq!(1f32.abs_sub(1f32), 0f32);
-        assert_eq!(1f32.abs_sub(0f32), 1f32);
-        assert_eq!(1f32.abs_sub(-1f32), 2f32);
-        assert_eq!(NEG_INFINITY.abs_sub(0f32), 0f32);
-        assert_eq!(INFINITY.abs_sub(1f32), INFINITY);
-        assert_eq!(0f32.abs_sub(NEG_INFINITY), INFINITY);
-        assert_eq!(0f32.abs_sub(INFINITY), 0f32);
-    }
-
-    #[test]
-    fn test_abs_sub_nowin() {
-        assert!(NAN.abs_sub(-1f32).is_nan());
-        assert!(1f32.abs_sub(NAN).is_nan());
-    }
-
-    #[test]
-    fn test_signum() {
-        assert_eq!(INFINITY.signum(), 1f32);
-        assert_eq!(1f32.signum(), 1f32);
-        assert_eq!(0f32.signum(), 1f32);
-        assert_eq!((-0f32).signum(), -1f32);
-        assert_eq!((-1f32).signum(), -1f32);
-        assert_eq!(NEG_INFINITY.signum(), -1f32);
-        assert_eq!((1f32/NEG_INFINITY).signum(), -1f32);
-        assert!(NAN.signum().is_nan());
-    }
-
-    #[test]
-    fn test_is_positive() {
-        assert!(INFINITY.is_positive());
-        assert!(1f32.is_positive());
-        assert!(0f32.is_positive());
-        assert!(!(-0f32).is_positive());
-        assert!(!(-1f32).is_positive());
-        assert!(!NEG_INFINITY.is_positive());
-        assert!(!(1f32/NEG_INFINITY).is_positive());
-        assert!(!NAN.is_positive());
-    }
-
-    #[test]
-    fn test_is_negative() {
-        assert!(!INFINITY.is_negative());
-        assert!(!1f32.is_negative());
-        assert!(!0f32.is_negative());
-        assert!((-0f32).is_negative());
-        assert!((-1f32).is_negative());
-        assert!(NEG_INFINITY.is_negative());
-        assert!((1f32/NEG_INFINITY).is_negative());
-        assert!(!NAN.is_negative());
-    }
-
-    #[test]
-    fn test_is_normal() {
-        let nan: f32 = Float::nan();
-        let inf: f32 = Float::infinity();
-        let neg_inf: f32 = Float::neg_infinity();
-        let zero: f32 = Float::zero();
-        let neg_zero: f32 = Float::neg_zero();
-        assert!(!nan.is_normal());
-        assert!(!inf.is_normal());
-        assert!(!neg_inf.is_normal());
-        assert!(!zero.is_normal());
-        assert!(!neg_zero.is_normal());
-        assert!(1f32.is_normal());
-        assert!(1e-37f32.is_normal());
-        assert!(!1e-38f32.is_normal());
-    }
-
-    #[test]
-    fn test_classify() {
-        let nan: f32 = Float::nan();
-        let inf: f32 = Float::infinity();
-        let neg_inf: f32 = Float::neg_infinity();
-        let zero: f32 = Float::zero();
-        let neg_zero: f32 = Float::neg_zero();
-        assert_eq!(nan.classify(), Fp::Nan);
-        assert_eq!(inf.classify(), Fp::Infinite);
-        assert_eq!(neg_inf.classify(), Fp::Infinite);
-        assert_eq!(zero.classify(), Fp::Zero);
-        assert_eq!(neg_zero.classify(), Fp::Zero);
-        assert_eq!(1f32.classify(), Fp::Normal);
-        assert_eq!(1e-37f32.classify(), Fp::Normal);
-        assert_eq!(1e-38f32.classify(), Fp::Subnormal);
-    }
-
-    #[test]
-    fn test_ldexp() {
-        // We have to use from_str until base-2 exponents
-        // are supported in floating-point literals
-        let f1: f32 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
-        let f2: f32 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
-        assert_eq!(Float::ldexp(1f32, -123), f1);
-        assert_eq!(Float::ldexp(1f32, -111), f2);
-
-        assert_eq!(Float::ldexp(0f32, -123), 0f32);
-        assert_eq!(Float::ldexp(-0f32, -123), -0f32);
-
-        let inf: f32 = Float::infinity();
-        let neg_inf: f32 = Float::neg_infinity();
-        let nan: f32 = Float::nan();
-        assert_eq!(Float::ldexp(inf, -123), inf);
-        assert_eq!(Float::ldexp(neg_inf, -123), neg_inf);
-        assert!(Float::ldexp(nan, -123).is_nan());
-    }
-
-    #[test]
-    fn test_frexp() {
-        // We have to use from_str until base-2 exponents
-        // are supported in floating-point literals
-        let f1: f32 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
-        let f2: f32 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
-        let (x1, exp1) = f1.frexp();
-        let (x2, exp2) = f2.frexp();
-        assert_eq!((x1, exp1), (0.5f32, -122));
-        assert_eq!((x2, exp2), (0.5f32, -110));
-        assert_eq!(Float::ldexp(x1, exp1), f1);
-        assert_eq!(Float::ldexp(x2, exp2), f2);
-
-        assert_eq!(0f32.frexp(), (0f32, 0));
-        assert_eq!((-0f32).frexp(), (-0f32, 0));
-    }
-
-    #[test] #[cfg_attr(windows, ignore)] // FIXME #8755
-    fn test_frexp_nowin() {
-        let inf: f32 = Float::infinity();
-        let neg_inf: f32 = Float::neg_infinity();
-        let nan: f32 = Float::nan();
-        assert_eq!(match inf.frexp() { (x, _) => x }, inf);
-        assert_eq!(match neg_inf.frexp() { (x, _) => x }, neg_inf);
-        assert!(match nan.frexp() { (x, _) => x.is_nan() })
-    }
-
-    #[test]
-    fn test_integer_decode() {
-        assert_eq!(3.14159265359f32.integer_decode(), (13176795u64, -22i16, 1i8));
-        assert_eq!((-8573.5918555f32).integer_decode(), (8779358u64, -10i16, -1i8));
-        assert_eq!(2f32.powf(100.0).integer_decode(), (8388608u64, 77i16, 1i8));
-        assert_eq!(0f32.integer_decode(), (0u64, -150i16, 1i8));
-        assert_eq!((-0f32).integer_decode(), (0u64, -150i16, -1i8));
-        assert_eq!(INFINITY.integer_decode(), (8388608u64, 105i16, 1i8));
-        assert_eq!(NEG_INFINITY.integer_decode(), (8388608u64, 105i16, -1i8));
-        assert_eq!(NAN.integer_decode(), (12582912u64, 105i16, 1i8));
-    }
-
-    #[test]
-    fn test_sqrt_domain() {
-        assert!(NAN.sqrt().is_nan());
-        assert!(NEG_INFINITY.sqrt().is_nan());
-        assert!((-1.0f32).sqrt().is_nan());
-        assert_eq!((-0.0f32).sqrt(), -0.0);
-        assert_eq!(0.0f32.sqrt(), 0.0);
-        assert_eq!(1.0f32.sqrt(), 1.0);
-        assert_eq!(INFINITY.sqrt(), INFINITY);
-    }
 }
index 0ce56371c77e544733a9dfc3a72a4ca2809b1e79..95065b59678c951052eef175475ebab3ff75c39f 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
@@ -477,6 +477,11 @@ mod tests {
     use num::*;
     use num::FpCategory as Fp;
 
+    #[test]
+    fn test_num_f64() {
+        test_num(10f64, 2f64);
+    }
+
     #[test]
     fn test_min_nan() {
         assert_eq!(NAN.min(2.0), 2.0);
@@ -490,8 +495,162 @@ fn test_max_nan() {
     }
 
     #[test]
-    fn test_num_f64() {
-        test_num(10f64, 2f64);
+    fn test_nan() {
+        let nan: f64 = Float::nan();
+        assert!(nan.is_nan());
+        assert!(!nan.is_infinite());
+        assert!(!nan.is_finite());
+        assert!(!nan.is_normal());
+        assert!(!nan.is_positive());
+        assert!(!nan.is_negative());
+        assert_eq!(Fp::Nan, nan.classify());
+    }
+
+    #[test]
+    fn test_infinity() {
+        let inf: f64 = Float::infinity();
+        assert!(inf.is_infinite());
+        assert!(!inf.is_finite());
+        assert!(inf.is_positive());
+        assert!(!inf.is_negative());
+        assert!(!inf.is_nan());
+        assert!(!inf.is_normal());
+        assert_eq!(Fp::Infinite, inf.classify());
+    }
+
+    #[test]
+    fn test_neg_infinity() {
+        let neg_inf: f64 = Float::neg_infinity();
+        assert!(neg_inf.is_infinite());
+        assert!(!neg_inf.is_finite());
+        assert!(!neg_inf.is_positive());
+        assert!(neg_inf.is_negative());
+        assert!(!neg_inf.is_nan());
+        assert!(!neg_inf.is_normal());
+        assert_eq!(Fp::Infinite, neg_inf.classify());
+    }
+
+    #[test]
+    fn test_zero() {
+        let zero: f64 = Float::zero();
+        assert_eq!(0.0, zero);
+        assert!(!zero.is_infinite());
+        assert!(zero.is_finite());
+        assert!(zero.is_positive());
+        assert!(!zero.is_negative());
+        assert!(!zero.is_nan());
+        assert!(!zero.is_normal());
+        assert_eq!(Fp::Zero, zero.classify());
+    }
+
+    #[test]
+    fn test_neg_zero() {
+        let neg_zero: f64 = Float::neg_zero();
+        assert_eq!(0.0, neg_zero);
+        assert!(!neg_zero.is_infinite());
+        assert!(neg_zero.is_finite());
+        assert!(!neg_zero.is_positive());
+        assert!(neg_zero.is_negative());
+        assert!(!neg_zero.is_nan());
+        assert!(!neg_zero.is_normal());
+        assert_eq!(Fp::Zero, neg_zero.classify());
+    }
+
+    #[test]
+    fn test_one() {
+        let one: f64 = Float::one();
+        assert_eq!(1.0, one);
+        assert!(!one.is_infinite());
+        assert!(one.is_finite());
+        assert!(one.is_positive());
+        assert!(!one.is_negative());
+        assert!(!one.is_nan());
+        assert!(one.is_normal());
+        assert_eq!(Fp::Normal, one.classify());
+    }
+
+    #[test]
+    fn test_is_nan() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert!(nan.is_nan());
+        assert!(!0.0f64.is_nan());
+        assert!(!5.3f64.is_nan());
+        assert!(!(-10.732f64).is_nan());
+        assert!(!inf.is_nan());
+        assert!(!neg_inf.is_nan());
+    }
+
+    #[test]
+    fn test_is_infinite() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert!(!nan.is_infinite());
+        assert!(inf.is_infinite());
+        assert!(neg_inf.is_infinite());
+        assert!(!0.0f64.is_infinite());
+        assert!(!42.8f64.is_infinite());
+        assert!(!(-109.2f64).is_infinite());
+    }
+
+    #[test]
+    fn test_is_finite() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert!(!nan.is_finite());
+        assert!(!inf.is_finite());
+        assert!(!neg_inf.is_finite());
+        assert!(0.0f64.is_finite());
+        assert!(42.8f64.is_finite());
+        assert!((-109.2f64).is_finite());
+    }
+
+    #[test]
+    fn test_is_normal() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        let zero: f64 = Float::zero();
+        let neg_zero: f64 = Float::neg_zero();
+        assert!(!nan.is_normal());
+        assert!(!inf.is_normal());
+        assert!(!neg_inf.is_normal());
+        assert!(!zero.is_normal());
+        assert!(!neg_zero.is_normal());
+        assert!(1f64.is_normal());
+        assert!(1e-307f64.is_normal());
+        assert!(!1e-308f64.is_normal());
+    }
+
+    #[test]
+    fn test_classify() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        let zero: f64 = Float::zero();
+        let neg_zero: f64 = Float::neg_zero();
+        assert_eq!(nan.classify(), Fp::Nan);
+        assert_eq!(inf.classify(), Fp::Infinite);
+        assert_eq!(neg_inf.classify(), Fp::Infinite);
+        assert_eq!(zero.classify(), Fp::Zero);
+        assert_eq!(neg_zero.classify(), Fp::Zero);
+        assert_eq!(1e-307f64.classify(), Fp::Normal);
+        assert_eq!(1e-308f64.classify(), Fp::Subnormal);
+    }
+
+    #[test]
+    fn test_integer_decode() {
+        assert_eq!(3.14159265359f64.integer_decode(), (7074237752028906, -51, 1));
+        assert_eq!((-8573.5918555f64).integer_decode(), (4713381968463931, -39, -1));
+        assert_eq!(2f64.powf(100.0).integer_decode(), (4503599627370496, 48, 1));
+        assert_eq!(0f64.integer_decode(), (0, -1075, 1));
+        assert_eq!((-0f64).integer_decode(), (0, -1075, -1));
+        assert_eq!(INFINITY.integer_decode(), (4503599627370496, 972, 1));
+        assert_eq!(NEG_INFINITY.integer_decode(), (4503599627370496, 972, -1));
+        assert_eq!(NAN.integer_decode(), (6755399441055744, 972, 1));
     }
 
     #[test]
@@ -564,6 +723,140 @@ fn test_fract() {
         assert_approx_eq!((-1.7f64).fract(), -0.7f64);
     }
 
+    #[test]
+    fn test_abs() {
+        assert_eq!(INFINITY.abs(), INFINITY);
+        assert_eq!(1f64.abs(), 1f64);
+        assert_eq!(0f64.abs(), 0f64);
+        assert_eq!((-0f64).abs(), 0f64);
+        assert_eq!((-1f64).abs(), 1f64);
+        assert_eq!(NEG_INFINITY.abs(), INFINITY);
+        assert_eq!((1f64/NEG_INFINITY).abs(), 0f64);
+        assert!(NAN.abs().is_nan());
+    }
+
+    #[test]
+    fn test_signum() {
+        assert_eq!(INFINITY.signum(), 1f64);
+        assert_eq!(1f64.signum(), 1f64);
+        assert_eq!(0f64.signum(), 1f64);
+        assert_eq!((-0f64).signum(), -1f64);
+        assert_eq!((-1f64).signum(), -1f64);
+        assert_eq!(NEG_INFINITY.signum(), -1f64);
+        assert_eq!((1f64/NEG_INFINITY).signum(), -1f64);
+        assert!(NAN.signum().is_nan());
+    }
+
+    #[test]
+    fn test_is_positive() {
+        assert!(INFINITY.is_positive());
+        assert!(1f64.is_positive());
+        assert!(0f64.is_positive());
+        assert!(!(-0f64).is_positive());
+        assert!(!(-1f64).is_positive());
+        assert!(!NEG_INFINITY.is_positive());
+        assert!(!(1f64/NEG_INFINITY).is_positive());
+        assert!(!NAN.is_positive());
+    }
+
+    #[test]
+    fn test_is_negative() {
+        assert!(!INFINITY.is_negative());
+        assert!(!1f64.is_negative());
+        assert!(!0f64.is_negative());
+        assert!((-0f64).is_negative());
+        assert!((-1f64).is_negative());
+        assert!(NEG_INFINITY.is_negative());
+        assert!((1f64/NEG_INFINITY).is_negative());
+        assert!(!NAN.is_negative());
+    }
+
+    #[test]
+    fn test_mul_add() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_approx_eq!(12.3f64.mul_add(4.5, 6.7), 62.05);
+        assert_approx_eq!((-12.3f64).mul_add(-4.5, -6.7), 48.65);
+        assert_approx_eq!(0.0f64.mul_add(8.9, 1.2), 1.2);
+        assert_approx_eq!(3.4f64.mul_add(-0.0, 5.6), 5.6);
+        assert!(nan.mul_add(7.8, 9.0).is_nan());
+        assert_eq!(inf.mul_add(7.8, 9.0), inf);
+        assert_eq!(neg_inf.mul_add(7.8, 9.0), neg_inf);
+        assert_eq!(8.9f64.mul_add(inf, 3.2), inf);
+        assert_eq!((-3.2f64).mul_add(2.4, neg_inf), neg_inf);
+    }
+
+    #[test]
+    fn test_recip() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_eq!(1.0f64.recip(), 1.0);
+        assert_eq!(2.0f64.recip(), 0.5);
+        assert_eq!((-0.4f64).recip(), -2.5);
+        assert_eq!(0.0f64.recip(), inf);
+        assert!(nan.recip().is_nan());
+        assert_eq!(inf.recip(), 0.0);
+        assert_eq!(neg_inf.recip(), 0.0);
+    }
+
+    #[test]
+    fn test_powi() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_eq!(1.0f64.powi(1), 1.0);
+        assert_approx_eq!((-3.1f64).powi(2), 9.61);
+        assert_approx_eq!(5.9f64.powi(-2), 0.028727);
+        assert_eq!(8.3f64.powi(0), 1.0);
+        assert!(nan.powi(2).is_nan());
+        assert_eq!(inf.powi(3), inf);
+        assert_eq!(neg_inf.powi(2), inf);
+    }
+
+    #[test]
+    fn test_powf() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_eq!(1.0f64.powf(1.0), 1.0);
+        assert_approx_eq!(3.4f64.powf(4.5), 246.408183);
+        assert_approx_eq!(2.7f64.powf(-3.2), 0.041652);
+        assert_approx_eq!((-3.1f64).powf(2.0), 9.61);
+        assert_approx_eq!(5.9f64.powf(-2.0), 0.028727);
+        assert_eq!(8.3f64.powf(0.0), 1.0);
+        assert!(nan.powf(2.0).is_nan());
+        assert_eq!(inf.powf(2.0), inf);
+        assert_eq!(neg_inf.powf(3.0), neg_inf);
+    }
+
+    #[test]
+    fn test_sqrt_domain() {
+        assert!(NAN.sqrt().is_nan());
+        assert!(NEG_INFINITY.sqrt().is_nan());
+        assert!((-1.0f64).sqrt().is_nan());
+        assert_eq!((-0.0f64).sqrt(), -0.0);
+        assert_eq!(0.0f64.sqrt(), 0.0);
+        assert_eq!(1.0f64.sqrt(), 1.0);
+        assert_eq!(INFINITY.sqrt(), INFINITY);
+    }
+
+    #[test]
+    fn test_rsqrt() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert!(nan.rsqrt().is_nan());
+        assert_eq!(inf.rsqrt(), 0.0);
+        assert!(neg_inf.rsqrt().is_nan());
+        assert!((-1.0f64).rsqrt().is_nan());
+        assert_eq!((-0.0f64).rsqrt(), neg_inf);
+        assert_eq!(0.0f64.rsqrt(), inf);
+        assert_eq!(1.0f64.rsqrt(), 1.0);
+        assert_eq!(4.0f64.rsqrt(), 0.5);
+    }
+
     #[test]
     fn test_exp() {
         assert_eq!(1.0, 0.0f64.exp());
@@ -591,6 +884,172 @@ fn test_exp2() {
         assert!(nan.exp2().is_nan());
     }
 
+    #[test]
+    fn test_ln() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_approx_eq!(1.0f64.exp().ln(), 1.0);
+        assert!(nan.ln().is_nan());
+        assert_eq!(inf.ln(), inf);
+        assert!(neg_inf.ln().is_nan());
+        assert!((-2.3f64).ln().is_nan());
+        assert_eq!((-0.0f64).ln(), neg_inf);
+        assert_eq!(0.0f64.ln(), neg_inf);
+        assert_approx_eq!(4.0f64.ln(), 1.386294);
+    }
+
+    #[test]
+    fn test_log() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_eq!(10.0f64.log(10.0), 1.0);
+        assert_approx_eq!(2.3f64.log(3.5), 0.664858);
+        assert_eq!(1.0f64.exp().log(1.0.exp()), 1.0);
+        assert!(1.0f64.log(1.0).is_nan());
+        assert!(1.0f64.log(-13.9).is_nan());
+        assert!(nan.log(2.3).is_nan());
+        assert_eq!(inf.log(10.0), inf);
+        assert!(neg_inf.log(8.8).is_nan());
+        assert!((-2.3f64).log(0.1).is_nan());
+        assert_eq!((-0.0f64).log(2.0), neg_inf);
+        assert_eq!(0.0f64.log(7.0), neg_inf);
+    }
+
+    #[test]
+    fn test_log2() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_approx_eq!(10.0f64.log2(), 3.321928);
+        assert_approx_eq!(2.3f64.log2(), 1.201634);
+        assert_approx_eq!(1.0f64.exp().log2(), 1.442695);
+        assert!(nan.log2().is_nan());
+        assert_eq!(inf.log2(), inf);
+        assert!(neg_inf.log2().is_nan());
+        assert!((-2.3f64).log2().is_nan());
+        assert_eq!((-0.0f64).log2(), neg_inf);
+        assert_eq!(0.0f64.log2(), neg_inf);
+    }
+
+    #[test]
+    fn test_log10() {
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_eq!(10.0f64.log10(), 1.0);
+        assert_approx_eq!(2.3f64.log10(), 0.361728);
+        assert_approx_eq!(1.0f64.exp().log10(), 0.434294);
+        assert_eq!(1.0f64.log10(), 0.0);
+        assert!(nan.log10().is_nan());
+        assert_eq!(inf.log10(), inf);
+        assert!(neg_inf.log10().is_nan());
+        assert!((-2.3f64).log10().is_nan());
+        assert_eq!((-0.0f64).log10(), neg_inf);
+        assert_eq!(0.0f64.log10(), neg_inf);
+    }
+
+    #[test]
+    fn test_to_degrees() {
+        let pi: f64 = consts::PI;
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_eq!(0.0f64.to_degrees(), 0.0);
+        assert_approx_eq!((-5.8f64).to_degrees(), -332.315521);
+        assert_eq!(pi.to_degrees(), 180.0);
+        assert!(nan.to_degrees().is_nan());
+        assert_eq!(inf.to_degrees(), inf);
+        assert_eq!(neg_inf.to_degrees(), neg_inf);
+    }
+
+    #[test]
+    fn test_to_radians() {
+        let pi: f64 = consts::PI;
+        let nan: f64 = Float::nan();
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        assert_eq!(0.0f64.to_radians(), 0.0);
+        assert_approx_eq!(154.6f64.to_radians(), 2.698279);
+        assert_approx_eq!((-332.31f64).to_radians(), -5.799903);
+        assert_eq!(180.0f64.to_radians(), pi);
+        assert!(nan.to_radians().is_nan());
+        assert_eq!(inf.to_radians(), inf);
+        assert_eq!(neg_inf.to_radians(), neg_inf);
+    }
+
+    #[test]
+    fn test_ldexp() {
+        // We have to use from_str until base-2 exponents
+        // are supported in floating-point literals
+        let f1: f64 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
+        let f2: f64 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
+        let f3: f64 = FromStrRadix::from_str_radix("1.Cp-12", 16).unwrap();
+        assert_eq!(Float::ldexp(1f64, -123), f1);
+        assert_eq!(Float::ldexp(1f64, -111), f2);
+        assert_eq!(Float::ldexp(1.75f64, -12), f3);
+
+        assert_eq!(Float::ldexp(0f64, -123), 0f64);
+        assert_eq!(Float::ldexp(-0f64, -123), -0f64);
+
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        let nan: f64 = Float::nan();
+        assert_eq!(Float::ldexp(inf, -123), inf);
+        assert_eq!(Float::ldexp(neg_inf, -123), neg_inf);
+        assert!(Float::ldexp(nan, -123).is_nan());
+    }
+
+    #[test]
+    fn test_frexp() {
+        // We have to use from_str until base-2 exponents
+        // are supported in floating-point literals
+        let f1: f64 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
+        let f2: f64 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
+        let f3: f64 = FromStrRadix::from_str_radix("1.Cp-123", 16).unwrap();
+        let (x1, exp1) = f1.frexp();
+        let (x2, exp2) = f2.frexp();
+        let (x3, exp3) = f3.frexp();
+        assert_eq!((x1, exp1), (0.5f64, -122));
+        assert_eq!((x2, exp2), (0.5f64, -110));
+        assert_eq!((x3, exp3), (0.875f64, -122));
+        assert_eq!(Float::ldexp(x1, exp1), f1);
+        assert_eq!(Float::ldexp(x2, exp2), f2);
+        assert_eq!(Float::ldexp(x3, exp3), f3);
+
+        assert_eq!(0f64.frexp(), (0f64, 0));
+        assert_eq!((-0f64).frexp(), (-0f64, 0));
+    }
+
+    #[test] #[cfg_attr(windows, ignore)] // FIXME #8755
+    fn test_frexp_nowin() {
+        let inf: f64 = Float::infinity();
+        let neg_inf: f64 = Float::neg_infinity();
+        let nan: f64 = Float::nan();
+        assert_eq!(match inf.frexp() { (x, _) => x }, inf);
+        assert_eq!(match neg_inf.frexp() { (x, _) => x }, neg_inf);
+        assert!(match nan.frexp() { (x, _) => x.is_nan() })
+    }
+
+    #[test]
+    fn test_abs_sub() {
+        assert_eq!((-1f64).abs_sub(1f64), 0f64);
+        assert_eq!(1f64.abs_sub(1f64), 0f64);
+        assert_eq!(1f64.abs_sub(0f64), 1f64);
+        assert_eq!(1f64.abs_sub(-1f64), 2f64);
+        assert_eq!(NEG_INFINITY.abs_sub(0f64), 0f64);
+        assert_eq!(INFINITY.abs_sub(1f64), INFINITY);
+        assert_eq!(0f64.abs_sub(NEG_INFINITY), INFINITY);
+        assert_eq!(0f64.abs_sub(INFINITY), 0f64);
+    }
+
+    #[test]
+    fn test_abs_sub_nowin() {
+        assert!(NAN.abs_sub(-1f64).is_nan());
+        assert!(1f64.abs_sub(NAN).is_nan());
+    }
+
     #[test]
     fn test_asinh() {
         assert_eq!(0.0f64.asinh(), 0.0f64);
@@ -677,173 +1136,4 @@ fn test_real_consts() {
         assert_approx_eq!(ln_2, 2f64.ln());
         assert_approx_eq!(ln_10, 10f64.ln());
     }
-
-    #[test]
-    pub fn test_abs() {
-        assert_eq!(INFINITY.abs(), INFINITY);
-        assert_eq!(1f64.abs(), 1f64);
-        assert_eq!(0f64.abs(), 0f64);
-        assert_eq!((-0f64).abs(), 0f64);
-        assert_eq!((-1f64).abs(), 1f64);
-        assert_eq!(NEG_INFINITY.abs(), INFINITY);
-        assert_eq!((1f64/NEG_INFINITY).abs(), 0f64);
-        assert!(NAN.abs().is_nan());
-    }
-
-    #[test]
-    fn test_abs_sub() {
-        assert_eq!((-1f64).abs_sub(1f64), 0f64);
-        assert_eq!(1f64.abs_sub(1f64), 0f64);
-        assert_eq!(1f64.abs_sub(0f64), 1f64);
-        assert_eq!(1f64.abs_sub(-1f64), 2f64);
-        assert_eq!(NEG_INFINITY.abs_sub(0f64), 0f64);
-        assert_eq!(INFINITY.abs_sub(1f64), INFINITY);
-        assert_eq!(0f64.abs_sub(NEG_INFINITY), INFINITY);
-        assert_eq!(0f64.abs_sub(INFINITY), 0f64);
-    }
-
-    #[test]
-    fn test_abs_sub_nowin() {
-        assert!(NAN.abs_sub(-1f64).is_nan());
-        assert!(1f64.abs_sub(NAN).is_nan());
-    }
-
-    #[test]
-    fn test_signum() {
-        assert_eq!(INFINITY.signum(), 1f64);
-        assert_eq!(1f64.signum(), 1f64);
-        assert_eq!(0f64.signum(), 1f64);
-        assert_eq!((-0f64).signum(), -1f64);
-        assert_eq!((-1f64).signum(), -1f64);
-        assert_eq!(NEG_INFINITY.signum(), -1f64);
-        assert_eq!((1f64/NEG_INFINITY).signum(), -1f64);
-        assert!(NAN.signum().is_nan());
-    }
-
-    #[test]
-    fn test_is_positive() {
-        assert!(INFINITY.is_positive());
-        assert!(1f64.is_positive());
-        assert!(0f64.is_positive());
-        assert!(!(-0f64).is_positive());
-        assert!(!(-1f64).is_positive());
-        assert!(!NEG_INFINITY.is_positive());
-        assert!(!(1f64/NEG_INFINITY).is_positive());
-        assert!(!NAN.is_positive());
-    }
-
-    #[test]
-    fn test_is_negative() {
-        assert!(!INFINITY.is_negative());
-        assert!(!1f64.is_negative());
-        assert!(!0f64.is_negative());
-        assert!((-0f64).is_negative());
-        assert!((-1f64).is_negative());
-        assert!(NEG_INFINITY.is_negative());
-        assert!((1f64/NEG_INFINITY).is_negative());
-        assert!(!NAN.is_negative());
-    }
-
-    #[test]
-    fn test_is_normal() {
-        let nan: f64 = Float::nan();
-        let inf: f64 = Float::infinity();
-        let neg_inf: f64 = Float::neg_infinity();
-        let zero: f64 = Float::zero();
-        let neg_zero: f64 = Float::neg_zero();
-        assert!(!nan.is_normal());
-        assert!(!inf.is_normal());
-        assert!(!neg_inf.is_normal());
-        assert!(!zero.is_normal());
-        assert!(!neg_zero.is_normal());
-        assert!(1f64.is_normal());
-        assert!(1e-307f64.is_normal());
-        assert!(!1e-308f64.is_normal());
-    }
-
-    #[test]
-    fn test_classify() {
-        let nan: f64 = Float::nan();
-        let inf: f64 = Float::infinity();
-        let neg_inf: f64 = Float::neg_infinity();
-        let zero: f64 = Float::zero();
-        let neg_zero: f64 = Float::neg_zero();
-        assert_eq!(nan.classify(), Fp::Nan);
-        assert_eq!(inf.classify(), Fp::Infinite);
-        assert_eq!(neg_inf.classify(), Fp::Infinite);
-        assert_eq!(zero.classify(), Fp::Zero);
-        assert_eq!(neg_zero.classify(), Fp::Zero);
-        assert_eq!(1e-307f64.classify(), Fp::Normal);
-        assert_eq!(1e-308f64.classify(), Fp::Subnormal);
-    }
-
-    #[test]
-    fn test_ldexp() {
-        // We have to use from_str until base-2 exponents
-        // are supported in floating-point literals
-        let f1: f64 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
-        let f2: f64 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
-        assert_eq!(Float::ldexp(1f64, -123), f1);
-        assert_eq!(Float::ldexp(1f64, -111), f2);
-
-        assert_eq!(Float::ldexp(0f64, -123), 0f64);
-        assert_eq!(Float::ldexp(-0f64, -123), -0f64);
-
-        let inf: f64 = Float::infinity();
-        let neg_inf: f64 = Float::neg_infinity();
-        let nan: f64 = Float::nan();
-        assert_eq!(Float::ldexp(inf, -123), inf);
-        assert_eq!(Float::ldexp(neg_inf, -123), neg_inf);
-        assert!(Float::ldexp(nan, -123).is_nan());
-    }
-
-    #[test]
-    fn test_frexp() {
-        // We have to use from_str until base-2 exponents
-        // are supported in floating-point literals
-        let f1: f64 = FromStrRadix::from_str_radix("1p-123", 16).unwrap();
-        let f2: f64 = FromStrRadix::from_str_radix("1p-111", 16).unwrap();
-        let (x1, exp1) = f1.frexp();
-        let (x2, exp2) = f2.frexp();
-        assert_eq!((x1, exp1), (0.5f64, -122));
-        assert_eq!((x2, exp2), (0.5f64, -110));
-        assert_eq!(Float::ldexp(x1, exp1), f1);
-        assert_eq!(Float::ldexp(x2, exp2), f2);
-
-        assert_eq!(0f64.frexp(), (0f64, 0));
-        assert_eq!((-0f64).frexp(), (-0f64, 0));
-    }
-
-    #[test] #[cfg_attr(windows, ignore)] // FIXME #8755
-    fn test_frexp_nowin() {
-        let inf: f64 = Float::infinity();
-        let neg_inf: f64 = Float::neg_infinity();
-        let nan: f64 = Float::nan();
-        assert_eq!(match inf.frexp() { (x, _) => x }, inf);
-        assert_eq!(match neg_inf.frexp() { (x, _) => x }, neg_inf);
-        assert!(match nan.frexp() { (x, _) => x.is_nan() })
-    }
-
-    #[test]
-    fn test_integer_decode() {
-        assert_eq!(3.14159265359f64.integer_decode(), (7074237752028906u64, -51i16, 1i8));
-        assert_eq!((-8573.5918555f64).integer_decode(), (4713381968463931u64, -39i16, -1i8));
-        assert_eq!(2f64.powf(100.0).integer_decode(), (4503599627370496u64, 48i16, 1i8));
-        assert_eq!(0f64.integer_decode(), (0u64, -1075i16, 1i8));
-        assert_eq!((-0f64).integer_decode(), (0u64, -1075i16, -1i8));
-        assert_eq!(INFINITY.integer_decode(), (4503599627370496u64, 972i16, 1i8));
-        assert_eq!(NEG_INFINITY.integer_decode(), (4503599627370496, 972, -1));
-        assert_eq!(NAN.integer_decode(), (6755399441055744u64, 972i16, 1i8));
-    }
-
-    #[test]
-    fn test_sqrt_domain() {
-        assert!(NAN.sqrt().is_nan());
-        assert!(NEG_INFINITY.sqrt().is_nan());
-        assert!((-1.0f64).sqrt().is_nan());
-        assert_eq!((-0.0f64).sqrt(), -0.0);
-        assert_eq!(0.0f64.sqrt(), 0.0);
-        assert_eq!(1.0f64.sqrt(), 1.0);
-        assert_eq!(INFINITY.sqrt(), INFINITY);
-    }
 }
index d776079efaeeccd00b8cda8e8a180ba26bf3145c..35d973d2d4e6da72919341c02578474f77389eff 100644 (file)
@@ -30,6 +30,7 @@
 pub use core::num::{from_f32, from_f64};
 pub use core::num::{FromStrRadix, from_str_radix};
 pub use core::num::{FpCategory, ParseIntError, ParseFloatError};
+pub use core::num::wrapping;
 
 use option::Option;
 
@@ -311,7 +312,7 @@ pub trait Float
     ///
     /// let num = 2.0f32;
     ///
-    /// // (8388608u64, -22i16, 1i8)
+    /// // (8388608, -22, 1)
     /// let (mantissa, exponent, sign) = num.integer_decode();
     /// let sign_f = sign as f32;
     /// let mantissa_f = mantissa as f32;
@@ -1632,7 +1633,7 @@ fn $test_name() {
                 assert_eq!((3 as $T).is_power_of_two(), false);
                 assert_eq!((4 as $T).is_power_of_two(), true);
                 assert_eq!((5 as $T).is_power_of_two(), false);
-                assert!(($T::MAX / 2 + 1).is_power_of_two(), true);
+                assert_eq!(($T::MAX / 2 + 1).is_power_of_two(), true);
             }
         )
     }
@@ -1754,28 +1755,28 @@ macro_rules! assert_pow {
 
     #[test]
     fn test_uint_to_str_overflow() {
-        let mut u8_val: u8 = 255_u8;
+        let mut u8_val: u8 = 255;
         assert_eq!(u8_val.to_string(), "255");
 
-        u8_val += 1 as u8;
+        u8_val = u8_val.wrapping_add(1);
         assert_eq!(u8_val.to_string(), "0");
 
-        let mut u16_val: u16 = 65_535_u16;
+        let mut u16_val: u16 = 65_535;
         assert_eq!(u16_val.to_string(), "65535");
 
-        u16_val += 1 as u16;
+        u16_val = u16_val.wrapping_add(1);
         assert_eq!(u16_val.to_string(), "0");
 
-        let mut u32_val: u32 = 4_294_967_295_u32;
+        let mut u32_val: u32 = 4_294_967_295;
         assert_eq!(u32_val.to_string(), "4294967295");
 
-        u32_val += 1 as u32;
+        u32_val = u32_val.wrapping_add(1);
         assert_eq!(u32_val.to_string(), "0");
 
-        let mut u64_val: u64 = 18_446_744_073_709_551_615_u64;
+        let mut u64_val: u64 = 18_446_744_073_709_551_615;
         assert_eq!(u64_val.to_string(), "18446744073709551615");
 
-        u64_val += 1 as u64;
+        u64_val = u64_val.wrapping_add(1);
         assert_eq!(u64_val.to_string(), "0");
     }
 
@@ -1785,35 +1786,35 @@ fn from_str<T: ::str::FromStr>(t: &str) -> Option<T> {
 
     #[test]
     fn test_uint_from_str_overflow() {
-        let mut u8_val: u8 = 255_u8;
+        let mut u8_val: u8 = 255;
         assert_eq!(from_str::<u8>("255"), Some(u8_val));
         assert_eq!(from_str::<u8>("256"), None);
 
-        u8_val += 1 as u8;
+        u8_val = u8_val.wrapping_add(1);
         assert_eq!(from_str::<u8>("0"), Some(u8_val));
         assert_eq!(from_str::<u8>("-1"), None);
 
-        let mut u16_val: u16 = 65_535_u16;
+        let mut u16_val: u16 = 65_535;
         assert_eq!(from_str::<u16>("65535"), Some(u16_val));
         assert_eq!(from_str::<u16>("65536"), None);
 
-        u16_val += 1 as u16;
+        u16_val = u16_val.wrapping_add(1);
         assert_eq!(from_str::<u16>("0"), Some(u16_val));
         assert_eq!(from_str::<u16>("-1"), None);
 
-        let mut u32_val: u32 = 4_294_967_295_u32;
+        let mut u32_val: u32 = 4_294_967_295;
         assert_eq!(from_str::<u32>("4294967295"), Some(u32_val));
         assert_eq!(from_str::<u32>("4294967296"), None);
 
-        u32_val += 1 as u32;
+        u32_val = u32_val.wrapping_add(1);
         assert_eq!(from_str::<u32>("0"), Some(u32_val));
         assert_eq!(from_str::<u32>("-1"), None);
 
-        let mut u64_val: u64 = 18_446_744_073_709_551_615_u64;
+        let mut u64_val: u64 = 18_446_744_073_709_551_615;
         assert_eq!(from_str::<u64>("18446744073709551615"), Some(u64_val));
         assert_eq!(from_str::<u64>("18446744073709551616"), None);
 
-        u64_val += 1 as u64;
+        u64_val = u64_val.wrapping_add(1);
         assert_eq!(from_str::<u64>("0"), Some(u64_val));
         assert_eq!(from_str::<u64>("-1"), None);
     }
index f6d05f961e1736efc5e54908730b70c37ba99463..5fdd42dbc7a838bd9d4a6243231c8f6e963fe803 100644 (file)
@@ -104,7 +104,7 @@ fn int_to_str_bytes_common<T, F>(num: T, radix: uint, sign: SignFormat, mut f: F
     // This is just for integral types, the largest of which is a u64. The
     // smallest base that we can have is 2, so the most number of digits we're
     // ever going to have is 64
-    let mut buf = [0u8; 64];
+    let mut buf = [0; 64];
     let mut cur = 0;
 
     // Loop at least once to make sure at least a `0` gets emitted.
@@ -221,10 +221,10 @@ pub fn float_to_str_bytes_common<T: Float>(
     let radix_gen: T = num::cast(radix as int).unwrap();
 
     let (num, exp) = match exp_format {
-        ExpNone => (num, 0i32),
+        ExpNone => (num, 0),
         ExpDec | ExpBin => {
             if num == _0 {
-                (num, 0i32)
+                (num, 0)
             } else {
                 let (exp, exp_base) = match exp_format {
                     ExpDec => (num.abs().log10().floor(), num::cast::<f64, T>(10.0f64).unwrap()),
@@ -253,7 +253,7 @@ pub fn float_to_str_bytes_common<T: Float>(
         deccum = deccum / radix_gen;
         deccum = deccum.trunc();
 
-        buf.push(char::from_digit(current_digit.to_int().unwrap() as u32, radix)
+        buf.push(char::from_digit(current_digit.to_isize().unwrap() as u32, radix)
              .unwrap() as u8);
 
         // No more digits to calculate for the non-fractional part -> break
@@ -310,7 +310,7 @@ pub fn float_to_str_bytes_common<T: Float>(
             let current_digit = deccum.trunc().abs();
 
             buf.push(char::from_digit(
-                current_digit.to_int().unwrap() as u32, radix).unwrap() as u8);
+                current_digit.to_isize().unwrap() as u32, radix).unwrap() as u8);
 
             // Decrease the deccumulator one fractional digit at a time
             deccum = deccum.fract();
@@ -422,37 +422,38 @@ pub fn float_to_str_common<T: Float>(
 
 // Some constants for from_str_bytes_common's input validation,
 // they define minimum radix values for which the character is a valid digit.
-static DIGIT_P_RADIX: u32 = ('p' as u32) - ('a' as u32) + 11;
-static DIGIT_E_RADIX: u32 = ('e' as u32) - ('a' as u32) + 11;
+const DIGIT_P_RADIX: u32 = ('p' as u32) - ('a' as u32) + 11;
+const DIGIT_E_RADIX: u32 = ('e' as u32) - ('a' as u32) + 11;
 
 #[cfg(test)]
 mod tests {
+    use core::num::wrapping::WrappingOps;
     use string::ToString;
 
     #[test]
     fn test_int_to_str_overflow() {
-        let mut i8_val: i8 = 127_i8;
+        let mut i8_val: i8 = 127;
         assert_eq!(i8_val.to_string(), "127");
 
-        i8_val += 1 as i8;
+        i8_val = i8_val.wrapping_add(1);
         assert_eq!(i8_val.to_string(), "-128");
 
-        let mut i16_val: i16 = 32_767_i16;
+        let mut i16_val: i16 = 32_767;
         assert_eq!(i16_val.to_string(), "32767");
 
-        i16_val += 1 as i16;
+        i16_val = i16_val.wrapping_add(1);
         assert_eq!(i16_val.to_string(), "-32768");
 
-        let mut i32_val: i32 = 2_147_483_647_i32;
+        let mut i32_val: i32 = 2_147_483_647;
         assert_eq!(i32_val.to_string(), "2147483647");
 
-        i32_val += 1 as i32;
+        i32_val = i32_val.wrapping_add(1);
         assert_eq!(i32_val.to_string(), "-2147483648");
 
-        let mut i64_val: i64 = 9_223_372_036_854_775_807_i64;
+        let mut i64_val: i64 = 9_223_372_036_854_775_807;
         assert_eq!(i64_val.to_string(), "9223372036854775807");
 
-        i64_val += 1 as i64;
+        i64_val = i64_val.wrapping_add(1);
         assert_eq!(i64_val.to_string(), "-9223372036854775808");
     }
 }
index 2d2d0d8b33a4c9e68ef0bf00e7f2511b878d7b22..cbb7bf043274506cee50a88ae535ac30f79711e2 100644 (file)
@@ -642,14 +642,14 @@ fn test_short_reads() {
 
     #[test]
     fn read_char_buffered() {
-        let buf = [195u8, 159u8];
+        let buf = [195, 159];
         let mut reader = BufferedReader::with_capacity(1, &buf[..]);
         assert_eq!(reader.read_char(), Ok('ß'));
     }
 
     #[test]
     fn test_chars() {
-        let buf = [195u8, 159u8, b'a'];
+        let buf = [195, 159, b'a'];
         let mut reader = BufferedReader::with_capacity(1, &buf[..]);
         let mut it = reader.chars();
         assert_eq!(it.next(), Some(Ok('ß')));
@@ -658,7 +658,7 @@ fn test_chars() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn dont_panic_in_drop_on_panicked_flush() {
         struct FailFlushWriter;
 
index 207d3d39167660b929225e667725357d166a1b63..dec1ae98ba0be10fc8065de87eaacdfe2994fce5 100644 (file)
@@ -30,7 +30,7 @@
 /// # drop(tx);
 /// let mut reader = ChanReader::new(rx);
 ///
-/// let mut buf = [0u8; 100];
+/// let mut buf = [0; 100];
 /// match reader.read(&mut buf) {
 ///     Ok(nread) => println!("Read {} bytes", nread),
 ///     Err(e) => println!("read error: {}", e),
@@ -167,15 +167,15 @@ mod test {
     fn test_rx_reader() {
         let (tx, rx) = channel();
         thread::spawn(move|| {
-          tx.send(vec![1u8, 2u8]).unwrap();
+          tx.send(vec![1, 2]).unwrap();
           tx.send(vec![]).unwrap();
-          tx.send(vec![3u8, 4u8]).unwrap();
-          tx.send(vec![5u8, 6u8]).unwrap();
-          tx.send(vec![7u8, 8u8]).unwrap();
+          tx.send(vec![3, 4]).unwrap();
+          tx.send(vec![5, 6]).unwrap();
+          tx.send(vec![78]).unwrap();
         });
 
         let mut reader = ChanReader::new(rx);
-        let mut buf = [0u8; 3];
+        let mut buf = [0; 3];
 
         assert_eq!(Ok(0), reader.read(&mut []));
 
@@ -233,7 +233,7 @@ fn test_chan_writer() {
         let mut writer = ChanWriter::new(tx);
         writer.write_be_u32(42).unwrap();
 
-        let wanted = vec![0u8, 0u8, 0u8, 42u8];
+        let wanted = vec![0, 0, 0, 42];
         let got = thread::scoped(move|| { rx.recv().unwrap() }).join();
         assert_eq!(wanted, got);
 
index 45a86a9fde72c4322eb32eddd73f2a1b04e21451..ec30121d78db807afbab0b9495dccd6ce7f4b204 100644 (file)
@@ -101,7 +101,7 @@ pub fn u64_to_le_bytes<T, F>(n: u64, size: uint, f: F) -> T where
         let mut i = size;
         let mut n = n;
         while i > 0 {
-            bytes.push((n & 255_u64) as u8);
+            bytes.push((n & 255) as u8);
             n >>= 8;
             i -= 1;
         }
@@ -170,7 +170,7 @@ pub fn u64_from_be_bytes(data: &[u8], start: uint, size: uint) -> u64 {
         panic!("index out of bounds");
     }
 
-    let mut buf = [0u8; 8];
+    let mut buf = [0; 8];
     unsafe {
         let ptr = data.as_ptr().offset(start as int);
         let out = buf.as_mut_ptr();
@@ -396,7 +396,7 @@ fn read_to_end() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn read_to_end_error() {
         let mut reader = ThreeChunkReader {
             count: 0,
@@ -522,8 +522,8 @@ macro_rules! u64_from_be_bytes_bench_impl {
         ({
             use super::u64_from_be_bytes;
 
-            let data = (0u8..$stride*100+$start_index).collect::<Vec<_>>();
-            let mut sum = 0u64;
+            let data = (0..$stride*100+$start_index).collect::<Vec<_>>();
+            let mut sum = 0;
             $b.iter(|| {
                 let mut i = $start_index;
                 while i < data.len() {
index 4e9c1b360552c4ee21d69146e72cf6261ac2bd9e..afffed2278b8d8f0a41651cb41c6d97ca1e4f23b 100644 (file)
@@ -82,6 +82,8 @@
 /// attempted against it for which its underlying file descriptor was not
 /// configured at creation time, via the `FileAccess` parameter to
 /// `File::open_mode()`.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::File")]
+#[unstable(feature = "old_io")]
 pub struct File {
     fd: fs_imp::FileDesc,
     path: Path,
@@ -94,6 +96,8 @@ fn as_inner(&self) -> &fs_imp::FileDesc {
     }
 }
 
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs")]
+#[unstable(feature = "old_io")]
 impl File {
     /// Open a file at `path` in the mode specified by the `mode` and `access`
     /// arguments
@@ -133,6 +137,8 @@ impl File {
     /// * Attempting to open a file with a `FileAccess` that the user lacks
     ///   permissions for
     /// * Filesystem-level errors (full disk, etc)
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs::OpenOptions")]
+    #[unstable(feature = "old_io")]
     pub fn open_mode(path: &Path,
                      mode: FileMode,
                      access: FileAccess) -> IoResult<File> {
@@ -174,6 +180,8 @@ pub fn open_mode(path: &Path,
     ///
     /// let contents = File::open(&Path::new("foo.txt")).read_to_end();
     /// ```
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs::File::open")]
+    #[unstable(feature = "old_io")]
     pub fn open(path: &Path) -> IoResult<File> {
         File::open_mode(path, Open, Read)
     }
@@ -195,12 +203,16 @@ pub fn open(path: &Path) -> IoResult<File> {
     /// # drop(f);
     /// # ::std::old_io::fs::unlink(&Path::new("foo.txt"));
     /// ```
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs::File::create")]
+    #[unstable(feature = "old_io")]
     pub fn create(path: &Path) -> IoResult<File> {
         File::open_mode(path, Truncate, Write)
              .update_desc("couldn't create file")
     }
 
     /// Returns the original path that was used to open this file.
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs")]
+    #[unstable(feature = "old_io")]
     pub fn path<'a>(&'a self) -> &'a Path {
         &self.path
     }
@@ -208,6 +220,8 @@ pub fn path<'a>(&'a self) -> &'a Path {
     /// Synchronizes all modifications to this file to its permanent storage
     /// device. This will flush any internal buffers necessary to perform this
     /// operation.
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs")]
+    #[unstable(feature = "old_io")]
     pub fn fsync(&mut self) -> IoResult<()> {
         self.fd.fsync()
             .update_err("couldn't fsync file",
@@ -218,6 +232,8 @@ pub fn fsync(&mut self) -> IoResult<()> {
     /// file metadata to the filesystem. This is intended for use cases that
     /// must synchronize content, but don't need the metadata on disk. The goal
     /// of this method is to reduce disk operations.
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs")]
+    #[unstable(feature = "old_io")]
     pub fn datasync(&mut self) -> IoResult<()> {
         self.fd.datasync()
             .update_err("couldn't datasync file",
@@ -232,6 +248,8 @@ pub fn datasync(&mut self) -> IoResult<()> {
     /// be shrunk. If it is greater than the current file's size, then the file
     /// will be extended to `size` and have all of the intermediate data filled
     /// in with 0s.
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs")]
+    #[unstable(feature = "old_io")]
     pub fn truncate(&mut self, size: i64) -> IoResult<()> {
         self.fd.truncate(size)
             .update_err("couldn't truncate file", |e|
@@ -247,11 +265,15 @@ pub fn truncate(&mut self, size: i64) -> IoResult<()> {
     /// until you have attempted to read past the end of the file, so if
     /// you've read _exactly_ the number of bytes in the file, this will
     /// return `false`, not `true`.
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs")]
+    #[unstable(feature = "old_io")]
     pub fn eof(&self) -> bool {
         self.last_nread == 0
     }
 
     /// Queries information about the underlying file.
+    #[deprecated(since = "1.0.0", reason = "replaced with std::fs")]
+    #[unstable(feature = "old_io")]
     pub fn stat(&self) -> IoResult<FileStat> {
         self.fd.fstat()
             .update_err("couldn't fstat file", |e|
@@ -280,6 +302,8 @@ pub fn stat(&self) -> IoResult<FileStat> {
 /// This function will return an error if `path` points to a directory, if the
 /// user lacks permissions to remove the file, or if some other filesystem-level
 /// error occurs.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::remove_file")]
+#[unstable(feature = "old_io")]
 pub fn unlink(path: &Path) -> IoResult<()> {
     fs_imp::unlink(path)
            .update_err("couldn't unlink path", |e|
@@ -307,6 +331,8 @@ pub fn unlink(path: &Path) -> IoResult<()> {
 /// This function will return an error if the user lacks the requisite permissions
 /// to perform a `stat` call on the given `path` or if there is no entry in the
 /// filesystem at the provided path.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::metadata")]
+#[unstable(feature = "old_io")]
 pub fn stat(path: &Path) -> IoResult<FileStat> {
     fs_imp::stat(path)
            .update_err("couldn't stat path", |e|
@@ -321,6 +347,7 @@ pub fn stat(path: &Path) -> IoResult<FileStat> {
 /// # Error
 ///
 /// See `stat`
+#[unstable(feature = "old_fs")]
 pub fn lstat(path: &Path) -> IoResult<FileStat> {
     fs_imp::lstat(path)
            .update_err("couldn't lstat path", |e|
@@ -343,6 +370,8 @@ pub fn lstat(path: &Path) -> IoResult<FileStat> {
 /// This function will return an error if the provided `from` doesn't exist, if
 /// the process lacks permissions to view the contents, or if some other
 /// intermittent I/O error occurs.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::rename")]
+#[unstable(feature = "old_io")]
 pub fn rename(from: &Path, to: &Path) -> IoResult<()> {
     fs_imp::rename(from, to)
            .update_err("couldn't rename path", |e|
@@ -377,6 +406,8 @@ pub fn rename(from: &Path, to: &Path) -> IoResult<()> {
 /// Note that this copy is not atomic in that once the destination is
 /// ensured to not exist, there is nothing preventing the destination from
 /// being created and then destroyed by this operation.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::copy")]
+#[unstable(feature = "old_io")]
 pub fn copy(from: &Path, to: &Path) -> IoResult<()> {
     fn update_err<T>(result: IoResult<T>, from: &Path, to: &Path) -> IoResult<T> {
         result.update_err("couldn't copy path", |e| {
@@ -421,6 +452,8 @@ fn update_err<T>(result: IoResult<T>, from: &Path, to: &Path) -> IoResult<T> {
 /// This function will return an error if the provided `path` doesn't exist, if
 /// the process lacks permissions to change the attributes of the file, or if
 /// some other I/O error is encountered.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::set_permissions")]
+#[unstable(feature = "old_io")]
 pub fn chmod(path: &Path, mode: old_io::FilePermission) -> IoResult<()> {
     fs_imp::chmod(path, mode.bits() as uint)
            .update_err("couldn't chmod path", |e|
@@ -428,6 +461,7 @@ pub fn chmod(path: &Path, mode: old_io::FilePermission) -> IoResult<()> {
 }
 
 /// Change the user and group owners of a file at the specified path.
+#[unstable(feature = "old_fs")]
 pub fn chown(path: &Path, uid: int, gid: int) -> IoResult<()> {
     fs_imp::chown(path, uid, gid)
            .update_err("couldn't chown path", |e|
@@ -437,6 +471,8 @@ pub fn chown(path: &Path, uid: int, gid: int) -> IoResult<()> {
 /// Creates a new hard link on the filesystem. The `dst` path will be a
 /// link pointing to the `src` path. Note that systems often require these
 /// two paths to both be located on the same filesystem.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::hard_link")]
+#[unstable(feature = "old_io")]
 pub fn link(src: &Path, dst: &Path) -> IoResult<()> {
     fs_imp::link(src, dst)
            .update_err("couldn't link path", |e|
@@ -445,6 +481,8 @@ pub fn link(src: &Path, dst: &Path) -> IoResult<()> {
 
 /// Creates a new symbolic link on the filesystem. The `dst` path will be a
 /// symlink pointing to the `src` path.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::soft_link")]
+#[unstable(feature = "old_io")]
 pub fn symlink(src: &Path, dst: &Path) -> IoResult<()> {
     fs_imp::symlink(src, dst)
            .update_err("couldn't symlink path", |e|
@@ -457,6 +495,8 @@ pub fn symlink(src: &Path, dst: &Path) -> IoResult<()> {
 ///
 /// This function will return an error on failure. Failure conditions include
 /// reading a file that does not exist or reading a file that is not a symlink.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::read_link")]
+#[unstable(feature = "old_io")]
 pub fn readlink(path: &Path) -> IoResult<Path> {
     fs_imp::readlink(path)
            .update_err("couldn't resolve symlink for path", |e|
@@ -480,6 +520,7 @@ pub fn readlink(path: &Path) -> IoResult<Path> {
 ///
 /// This function will return an error if the user lacks permissions to make a
 /// new directory at the provided `path`, or if the directory already exists.
+#[unstable(feature = "old_fs")]
 pub fn mkdir(path: &Path, mode: FilePermission) -> IoResult<()> {
     fs_imp::mkdir(path, mode.bits() as uint)
            .update_err("couldn't create directory", |e|
@@ -502,6 +543,8 @@ pub fn mkdir(path: &Path, mode: FilePermission) -> IoResult<()> {
 ///
 /// This function will return an error if the user lacks permissions to remove
 /// the directory at the provided `path`, or if the directory isn't empty.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::remove_dir")]
+#[unstable(feature = "old_io")]
 pub fn rmdir(path: &Path) -> IoResult<()> {
     fs_imp::rmdir(path)
            .update_err("couldn't remove directory", |e|
@@ -542,6 +585,8 @@ pub fn rmdir(path: &Path) -> IoResult<()> {
 /// This function will return an error if the provided `path` doesn't exist, if
 /// the process lacks permissions to view the contents or if the `path` points
 /// at a non-directory file
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::read_dir")]
+#[unstable(feature = "old_io")]
 pub fn readdir(path: &Path) -> IoResult<Vec<Path>> {
     fs_imp::readdir(path)
            .update_err("couldn't read directory",
@@ -552,6 +597,8 @@ pub fn readdir(path: &Path) -> IoResult<Vec<Path>> {
 /// rooted at `path`. The path given will not be iterated over, and this will
 /// perform iteration in some top-down order.  The contents of unreadable
 /// subdirectories are ignored.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::walk_dir")]
+#[unstable(feature = "old_io")]
 pub fn walk_dir(path: &Path) -> IoResult<Directories> {
     Ok(Directories {
         stack: try!(readdir(path).update_err("couldn't walk directory",
@@ -561,6 +608,8 @@ pub fn walk_dir(path: &Path) -> IoResult<Directories> {
 
 /// An iterator that walks over a directory
 #[derive(Clone)]
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::ReadDir")]
+#[unstable(feature = "old_io")]
 pub struct Directories {
     stack: Vec<Path>,
 }
@@ -590,6 +639,7 @@ fn next(&mut self) -> Option<Path> {
 /// # Error
 ///
 /// See `fs::mkdir`.
+#[unstable(feature = "old_fs")]
 pub fn mkdir_recursive(path: &Path, mode: FilePermission) -> IoResult<()> {
     // tjc: if directory exists but with different permissions,
     // should we return false?
@@ -627,6 +677,8 @@ pub fn mkdir_recursive(path: &Path, mode: FilePermission) -> IoResult<()> {
 /// # Error
 ///
 /// See `file::unlink` and `fs::readdir`
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::remove_dir_all")]
+#[unstable(feature = "old_io")]
 pub fn rmdir_recursive(path: &Path) -> IoResult<()> {
     let mut rm_stack = Vec::new();
     rm_stack.push(path.clone());
@@ -689,6 +741,8 @@ fn update_err<T>(err: IoResult<T>, path: &Path) -> IoResult<T> {
 /// `atime` and its modification time set to `mtime`. The times specified should
 /// be in milliseconds.
 // FIXME(#10301) these arguments should not be u64
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::set_file_times")]
+#[unstable(feature = "old_io")]
 pub fn change_file_times(path: &Path, atime: u64, mtime: u64) -> IoResult<()> {
     fs_imp::utime(path, atime, mtime)
            .update_err("couldn't change_file_times", |e|
@@ -748,6 +802,8 @@ fn seek(&mut self, pos: i64, style: SeekStyle) -> IoResult<()> {
 }
 
 /// Utility methods for paths.
+#[deprecated(since = "1.0.0", reason = "replaced with std::fs::PathExt")]
+#[unstable(feature = "old_io")]
 pub trait PathExtensions {
     /// Get information on the file, directory, etc at this path.
     ///
@@ -1110,7 +1166,7 @@ fn file_test_directoryinfo_readdir() {
             check!(w.write(msg));
         }
         let files = check!(readdir(dir));
-        let mut mem = [0u8; 4];
+        let mut mem = [0; 4];
         for f in &files {
             {
                 let n = f.filestem_str();
@@ -1142,7 +1198,7 @@ fn file_test_walk_dir() {
         check!(File::create(&dir2.join("14")));
 
         let mut files = check!(walk_dir(dir));
-        let mut cur = [0u8; 2];
+        let mut cur = [0; 2];
         for f in files {
             let stem = f.filestem_str().unwrap();
             let root = stem.as_bytes()[0] - b'0';
index b82572fc08957380c68f439b2ae1919d7ccca064..f2042b384ceea3cce97d5f0ea877e87a5eab6e8f 100644 (file)
@@ -343,8 +343,7 @@ impl IoError {
     pub fn from_errno(errno: i32, detail: bool) -> IoError {
         let mut err = sys::decode_error(errno as i32);
         if detail && err.kind == OtherIoError {
-            err.detail = Some(os::error_string(errno).chars()
-                                 .map(|c| c.to_lowercase()).collect())
+            err.detail = Some(os::error_string(errno).to_lowercase());
         }
         err
     }
@@ -670,7 +669,7 @@ fn read_to_string(&mut self) -> IoResult<String> {
     fn read_le_uint_n(&mut self, nbytes: uint) -> IoResult<u64> {
         assert!(nbytes > 0 && nbytes <= 8);
 
-        let mut val = 0u64;
+        let mut val = 0;
         let mut pos = 0;
         let mut i = nbytes;
         while i > 0 {
@@ -694,7 +693,7 @@ fn read_le_int_n(&mut self, nbytes: uint) -> IoResult<i64> {
     fn read_be_uint_n(&mut self, nbytes: uint) -> IoResult<u64> {
         assert!(nbytes > 0 && nbytes <= 8);
 
-        let mut val = 0u64;
+        let mut val = 0;
         let mut i = nbytes;
         while i > 0 {
             i -= 1;
@@ -714,28 +713,28 @@ fn read_be_int_n(&mut self, nbytes: uint) -> IoResult<i64> {
     ///
     /// The number of bytes returned is system-dependent.
     fn read_le_uint(&mut self) -> IoResult<uint> {
-        self.read_le_uint_n(usize::BYTES).map(|i| i as uint)
+        self.read_le_uint_n(usize::BYTES as usize).map(|i| i as uint)
     }
 
     /// Reads a little-endian integer.
     ///
     /// The number of bytes returned is system-dependent.
     fn read_le_int(&mut self) -> IoResult<int> {
-        self.read_le_int_n(isize::BYTES).map(|i| i as int)
+        self.read_le_int_n(isize::BYTES as usize).map(|i| i as int)
     }
 
     /// Reads a big-endian unsigned integer.
     ///
     /// The number of bytes returned is system-dependent.
     fn read_be_uint(&mut self) -> IoResult<uint> {
-        self.read_be_uint_n(usize::BYTES).map(|i| i as uint)
+        self.read_be_uint_n(usize::BYTES as usize).map(|i| i as uint)
     }
 
     /// Reads a big-endian integer.
     ///
     /// The number of bytes returned is system-dependent.
     fn read_be_int(&mut self) -> IoResult<int> {
-        self.read_be_int_n(isize::BYTES).map(|i| i as int)
+        self.read_be_int_n(isize::BYTES as usize).map(|i| i as int)
     }
 
     /// Reads a big-endian `u64`.
@@ -1078,7 +1077,7 @@ fn write_line(&mut self, s: &str) -> IoResult<()> {
     /// Write a single char, encoded as UTF-8.
     #[inline]
     fn write_char(&mut self, c: char) -> IoResult<()> {
-        let mut buf = [0u8; 4];
+        let mut buf = [0; 4];
         let n = c.encode_utf8(&mut buf).unwrap_or(0);
         self.write_all(&buf[..n])
     }
@@ -1098,25 +1097,25 @@ fn write_uint(&mut self, n: uint) -> IoResult<()> {
     /// Write a little-endian uint (number of bytes depends on system).
     #[inline]
     fn write_le_uint(&mut self, n: uint) -> IoResult<()> {
-        extensions::u64_to_le_bytes(n as u64, usize::BYTES, |v| self.write_all(v))
+        extensions::u64_to_le_bytes(n as u64, usize::BYTES as usize, |v| self.write_all(v))
     }
 
     /// Write a little-endian int (number of bytes depends on system).
     #[inline]
     fn write_le_int(&mut self, n: int) -> IoResult<()> {
-        extensions::u64_to_le_bytes(n as u64, isize::BYTES, |v| self.write_all(v))
+        extensions::u64_to_le_bytes(n as u64, isize::BYTES as usize, |v| self.write_all(v))
     }
 
     /// Write a big-endian uint (number of bytes depends on system).
     #[inline]
     fn write_be_uint(&mut self, n: uint) -> IoResult<()> {
-        extensions::u64_to_be_bytes(n as u64, usize::BYTES, |v| self.write_all(v))
+        extensions::u64_to_be_bytes(n as u64, usize::BYTES as usize, |v| self.write_all(v))
     }
 
     /// Write a big-endian int (number of bytes depends on system).
     #[inline]
     fn write_be_int(&mut self, n: int) -> IoResult<()> {
-        extensions::u64_to_be_bytes(n as u64, isize::BYTES, |v| self.write_all(v))
+        extensions::u64_to_be_bytes(n as u64, isize::BYTES as usize, |v| self.write_all(v))
     }
 
     /// Write a big-endian u64 (8 bytes).
@@ -1896,7 +1895,7 @@ fn read(&mut self, buf: &mut [u8]) -> IoResult<uint> {
     fn test_read_at_least() {
         let mut r = BadReader::new(MemReader::new(b"hello, world!".to_vec()),
                                    vec![GoodBehavior(usize::MAX)]);
-        let buf = &mut [0u8; 5];
+        let buf = &mut [0; 5];
         assert!(r.read_at_least(1, buf).unwrap() >= 1);
         assert!(r.read_exact(5).unwrap().len() == 5); // read_exact uses read_at_least
         assert!(r.read_at_least(0, buf).is_ok());
index 9c89c943994630f46c1b7633ec24cabe5dc8fb6a..6e2f491262dea7f077f6f9653ea63328e65772a6 100644 (file)
@@ -198,7 +198,7 @@ fn parse_digit(c: char, radix: u8) -> Option<u8> {
     }
 
     fn read_number_impl(&mut self, radix: u8, max_digits: u32, upto: u32) -> Option<u32> {
-        let mut r = 0u32;
+        let mut r = 0;
         let mut digit_count = 0;
         loop {
             match self.read_digit(radix) {
@@ -226,7 +226,7 @@ fn read_number(&mut self, radix: u8, max_digits: u32, upto: u32) -> Option<u32>
     }
 
     fn read_ipv4_addr_impl(&mut self) -> Option<IpAddr> {
-        let mut bs = [0u8; 4];
+        let mut bs = [0; 4];
         let mut i = 0;
         while i < 4 {
             if i != 0 && self.read_given_char('.').is_none() {
@@ -251,7 +251,7 @@ fn read_ipv4_addr(&mut self) -> Option<IpAddr> {
     fn read_ipv6_addr_impl(&mut self) -> Option<IpAddr> {
         fn ipv6_addr_from_head_tail(head: &[u16], tail: &[u16]) -> IpAddr {
             assert!(head.len() + tail.len() <= 8);
-            let mut gs = [0u16; 8];
+            let mut gs = [0; 8];
             gs.clone_from_slice(head);
             gs[(8 - tail.len()) .. 8].clone_from_slice(tail);
             Ipv6Addr(gs[0], gs[1], gs[2], gs[3], gs[4], gs[5], gs[6], gs[7])
@@ -294,7 +294,7 @@ fn ipv6_addr_from_head_tail(head: &[u16], tail: &[u16]) -> IpAddr {
             (i, false)
         }
 
-        let mut head = [0u16; 8];
+        let mut head = [0; 8];
         let (head_size, head_ipv4) = read_groups(self, &mut head, 8);
 
         if head_size == 8 {
@@ -313,7 +313,7 @@ fn ipv6_addr_from_head_tail(head: &[u16], tail: &[u16]) -> IpAddr {
             return None;
         }
 
-        let mut tail = [0u16; 8];
+        let mut tail = [0; 8];
         let (tail_size, _) = read_groups(self, &mut tail, 8 - head_size);
         Some(ipv6_addr_from_head_tail(&head[..head_size], &tail[..tail_size]))
     }
@@ -323,22 +323,22 @@ fn read_ipv6_addr(&mut self) -> Option<IpAddr> {
     }
 
     fn read_ip_addr(&mut self) -> Option<IpAddr> {
-        let ipv4_addr = |p: &mut Parser| p.read_ipv4_addr();
-        let ipv6_addr = |p: &mut Parser| p.read_ipv6_addr();
-        self.read_or(&mut [box ipv4_addr, box ipv6_addr])
+        let ipv4_addr: Box<_> = box |p: &mut Parser| p.read_ipv4_addr();
+        let ipv6_addr: Box<_> = box |p: &mut Parser| p.read_ipv6_addr();
+        self.read_or(&mut [ipv4_addr, ipv6_addr])
     }
 
     fn read_socket_addr(&mut self) -> Option<SocketAddr> {
         let ip_addr = |p: &mut Parser| {
-            let ipv4_p = |p: &mut Parser| p.read_ip_addr();
-            let ipv6_p = |p: &mut Parser| {
+            let ipv4_p: Box<_> = box |p: &mut Parser| p.read_ip_addr();
+            let ipv6_p: Box<_> = box |p: &mut Parser| {
                 let open_br = |p: &mut Parser| p.read_given_char('[');
                 let ip_addr = |p: &mut Parser| p.read_ipv6_addr();
                 let clos_br = |p: &mut Parser| p.read_given_char(']');
                 p.read_seq_3::<char, IpAddr, char, _, _, _>(open_br, ip_addr, clos_br)
                         .map(|t| match t { (_, ip, _) => ip })
             };
-            p.read_or(&mut [box ipv4_p, box ipv6_p])
+            p.read_or(&mut [ipv4_p, ipv6_p])
         };
         let colon = |p: &mut Parser| p.read_given_char(':');
         let port  = |p: &mut Parser| p.read_number(10, 5, 0x10000).map(|n| n as u16);
@@ -425,17 +425,17 @@ fn from_str(s: &str) -> Result<SocketAddr, ParseError> {
 ///     // The following lines are equivalent modulo possible "localhost" name resolution
 ///     // differences
 ///     let tcp_s = TcpStream::connect(SocketAddr { ip: Ipv4Addr(127, 0, 0, 1), port: 12345 });
-///     let tcp_s = TcpStream::connect((Ipv4Addr(127, 0, 0, 1), 12345u16));
-///     let tcp_s = TcpStream::connect(("127.0.0.1", 12345u16));
-///     let tcp_s = TcpStream::connect(("localhost", 12345u16));
+///     let tcp_s = TcpStream::connect((Ipv4Addr(127, 0, 0, 1), 12345));
+///     let tcp_s = TcpStream::connect(("127.0.0.1", 12345));
+///     let tcp_s = TcpStream::connect(("localhost", 12345));
 ///     let tcp_s = TcpStream::connect("127.0.0.1:12345");
 ///     let tcp_s = TcpStream::connect("localhost:12345");
 ///
 ///     // TcpListener::bind(), UdpSocket::bind() and UdpSocket::send_to() behave similarly
 ///     let tcp_l = TcpListener::bind("localhost:12345");
 ///
-///     let mut udp_s = UdpSocket::bind(("127.0.0.1", 23451u16)).unwrap();
-///     udp_s.send_to([7u8, 7u8, 7u8].as_slice(), (Ipv4Addr(127, 0, 0, 1), 23451u16));
+///     let mut udp_s = UdpSocket::bind(("127.0.0.1", 23451)).unwrap();
+///     udp_s.send_to([7, 7, 7].as_slice(), (Ipv4Addr(127, 0, 0, 1), 23451));
 /// }
 /// ```
 pub trait ToSocketAddr {
@@ -674,7 +674,7 @@ fn to_socket_addr_socketaddr() {
     #[test]
     fn to_socket_addr_ipaddr_u16() {
         let a = Ipv4Addr(77, 88, 21, 11);
-        let p = 12345u16;
+        let p = 12345;
         let e = SocketAddr { ip: a, port: p };
         assert_eq!(Ok(e), (a, p).to_socket_addr());
         assert_eq!(Ok(vec![e]), (a, p).to_socket_addr_all());
@@ -683,15 +683,15 @@ fn to_socket_addr_ipaddr_u16() {
     #[test]
     fn to_socket_addr_str_u16() {
         let a = SocketAddr { ip: Ipv4Addr(77, 88, 21, 11), port: 24352 };
-        assert_eq!(Ok(a), ("77.88.21.11", 24352u16).to_socket_addr());
-        assert_eq!(Ok(vec![a]), ("77.88.21.11", 24352u16).to_socket_addr_all());
+        assert_eq!(Ok(a), ("77.88.21.11", 24352).to_socket_addr());
+        assert_eq!(Ok(vec![a]), ("77.88.21.11", 24352).to_socket_addr_all());
 
         let a = SocketAddr { ip: Ipv6Addr(0x2a02, 0x6b8, 0, 1, 0, 0, 0, 1), port: 53 };
         assert_eq!(Ok(a), ("2a02:6b8:0:1::1", 53).to_socket_addr());
         assert_eq!(Ok(vec![a]), ("2a02:6b8:0:1::1", 53).to_socket_addr_all());
 
         let a = SocketAddr { ip: Ipv4Addr(127, 0, 0, 1), port: 23924 };
-        assert!(("localhost", 23924u16).to_socket_addr_all().unwrap().contains(&a));
+        assert!(("localhost", 23924).to_socket_addr_all().unwrap().contains(&a));
     }
 
     #[test]
index bbe3a71dcc0d17a12057884758c81e22de430900..a3567290b0e16395a83003ed874f3301bb469e50 100644 (file)
 
 //! Networking I/O
 
+#![deprecated(since = "1.0.0",
+              reason = "replaced with new I/O primitives in `std::net`")]
+#![unstable(feature = "old_io")]
+
 use old_io::{IoError, IoResult, InvalidInput};
 use ops::FnMut;
 use option::Option::None;
index d05669d32b8cfc0d7f3b8b411b2bce5adc0cb471..2ecaf515f081b226a341af1af38b205e20ece099 100644 (file)
 //! instances as clients.
 
 #![allow(missing_docs)]
+#![deprecated(since = "1.0.0",
+              reason = "will be removed to be reintroduced at a later date; \
+                        in the meantime consider using the `unix_socket` crate \
+                        for unix sockets; there is currently no replacement \
+                        for named pipes")]
+#![unstable(feature = "old_io")]
 
 use prelude::v1::*;
 
index 19a6f6e3defa7be42a677cea30cfdc75df58081d..73ef21fa3aa9609703011a3078862eb588a3bfe4 100644 (file)
@@ -1162,7 +1162,7 @@ fn accept_timeout() {
                 tx.send(TcpStream::connect(addr).unwrap()).unwrap();
             });
             let _l = rx.recv().unwrap();
-            for i in 0i32..1001 {
+            for i in 0..1001 {
                 match a.accept() {
                     Ok(..) => break,
                     Err(ref e) if e.kind == TimedOut => {}
@@ -1262,7 +1262,7 @@ fn readwrite_timeouts() {
         assert_eq!(s.read(&mut [0]).err().unwrap().kind, TimedOut);
 
         s.set_timeout(Some(20));
-        for i in 0i32..1001 {
+        for i in 0..1001 {
             match s.write(&[0; 128 * 1024]) {
                 Ok(()) | Err(IoError { kind: ShortWrite(..), .. }) => {},
                 Err(IoError { kind: TimedOut, .. }) => break,
@@ -1320,7 +1320,7 @@ fn write_timeouts() {
 
         let mut s = a.accept().unwrap();
         s.set_write_timeout(Some(20));
-        for i in 0i32..1001 {
+        for i in 0..1001 {
             match s.write(&[0; 128 * 1024]) {
                 Ok(()) | Err(IoError { kind: ShortWrite(..), .. }) => {},
                 Err(IoError { kind: TimedOut, .. }) => break,
index a13295b1ccb5014ea8137156559b628cca769547..a30dcd9d9f0ab72ce9a8f927b58d5847564d9d3a 100644 (file)
@@ -11,6 +11,9 @@
 //! Bindings for executing child processes
 
 #![allow(non_upper_case_globals)]
+#![unstable(feature = "old_io")]
+#![deprecated(since = "1.0.0",
+              reason = "replaced with the std::process module")]
 
 pub use self::StdioContainer::*;
 pub use self::ProcessExit::*;
@@ -107,10 +110,11 @@ pub struct Process {
 #[cfg(windows)]
 impl hash::Hash for EnvKey {
     fn hash<H: hash::Hasher>(&self, state: &mut H) {
+        use ascii::AsciiExt;
         let &EnvKey(ref x) = self;
         match str::from_utf8(x.as_bytes()) {
             Ok(s) => for ch in s.chars() {
-                (ch as u8 as char).to_lowercase().hash(state);
+                ch.to_ascii_lowercase().hash(state);
             },
             Err(..) => x.hash(state)
         }
@@ -120,6 +124,7 @@ fn hash<H: hash::Hasher>(&self, state: &mut H) {
 #[cfg(windows)]
 impl PartialEq for EnvKey {
     fn eq(&self, other: &EnvKey) -> bool {
+        use ascii::AsciiExt;
         let &EnvKey(ref x) = self;
         let &EnvKey(ref y) = other;
         match (str::from_utf8(x.as_bytes()), str::from_utf8(y.as_bytes())) {
@@ -128,7 +133,7 @@ fn eq(&self, other: &EnvKey) -> bool {
                     return false
                 } else {
                     for (xch, ych) in xs.chars().zip(ys.chars()) {
-                        if xch.to_lowercase() != ych.to_lowercase() {
+                        if xch.to_ascii_lowercase() != ych.to_ascii_lowercase() {
                             return false;
                         }
                     }
index a5df21749e22e3023580e1ae8ef4b6a48a130c67..85bf4908f8397bf5ffe65c9835134109a8b4b84e 100644 (file)
@@ -547,8 +547,9 @@ fn capture_stdout() {
 
         let (tx, rx) = channel();
         let (mut r, w) = (ChanReader::new(rx), ChanWriter::new(tx));
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
         let _t = thread::spawn(move|| {
-            set_stdout(box w);
+            set_stdout(Box::new(w));
             println!("hello!");
         });
         assert_eq!(r.read_to_string().unwrap(), "hello!\n");
@@ -560,8 +561,9 @@ fn capture_stderr() {
 
         let (tx, rx) = channel();
         let (mut r, w) = (ChanReader::new(rx), ChanWriter::new(tx));
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
         let _t = thread::spawn(move || -> () {
-            set_stderr(box w);
+            set_stderr(Box::new(w));
             panic!("my special message");
         });
         let s = r.read_to_string().unwrap();
index 43c0b9268a242d065cc90b9c53c0a71a3207cb9c..9fbdac84a80dbc79e5fad48372ec75072a92df14 100644 (file)
@@ -73,8 +73,8 @@ pub fn next_test_ip6() -> SocketAddr {
 */
 fn base_port() -> u16 {
 
-    let base = 9600u16;
-    let range = 1000u16;
+    let base = 9600;
+    let range = 1000;
 
     let bases = [
         ("32-opt", base + range * 1),
index 1f2ef50fcae453627b63568cf7e0b92697cac72b..375fe6ce483aae520dbb3236ce0bbf75c0af3d15 100644 (file)
@@ -15,6 +15,7 @@
 
 // FIXME: These functions take Durations but only pass ms to the backend impls.
 
+use boxed::Box;
 use sync::mpsc::{Receiver, Sender, channel};
 use time::Duration;
 use old_io::IoResult;
@@ -143,7 +144,7 @@ pub fn oneshot(&mut self, duration: Duration) -> Receiver<()> {
         let (tx, rx) = channel();
         // Short-circuit the timer backend for 0 duration
         if in_ms_u64(duration) != 0 {
-            self.inner.oneshot(in_ms_u64(duration), box TimerCallback { tx: tx });
+            self.inner.oneshot(in_ms_u64(duration), Box::new(TimerCallback { tx: tx }));
         } else {
             tx.send(()).unwrap();
         }
@@ -204,7 +205,7 @@ pub fn periodic(&mut self, duration: Duration) -> Receiver<()> {
         // not clear what use a 0ms period is anyway...
         let ms = if ms == 0 { 1 } else { ms };
         let (tx, rx) = channel();
-        self.inner.period(ms, box TimerCallback { tx: tx });
+        self.inner.period(ms, Box::new(TimerCallback { tx: tx }));
         return rx
     }
 }
@@ -332,7 +333,7 @@ fn sleep() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn oneshot_fail() {
         let mut timer = Timer::new().unwrap();
         let _rx = timer.oneshot(Duration::milliseconds(1));
@@ -340,7 +341,7 @@ fn oneshot_fail() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn period_fail() {
         let mut timer = Timer::new().unwrap();
         let _rx = timer.periodic(Duration::milliseconds(1));
@@ -348,7 +349,7 @@ fn period_fail() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn normal_fail() {
         let _timer = Timer::new().unwrap();
         panic!();
index 8e49335ed5469e110114ab9823866d113903e071..4faf8af57b4c4392da158935f543aa28436e15ef 100644 (file)
@@ -10,6 +10,8 @@
 
 //! Utility implementations of Reader and Writer
 
+#![allow(deprecated)]
+
 use prelude::v1::*;
 use cmp;
 use old_io;
 
 /// Wraps a `Reader`, limiting the number of bytes that can be read from it.
 #[derive(Debug)]
+#[deprecated(since = "1.0.0", reason = "use std::io::Take")]
+#[unstable(feature = "old_io")]
 pub struct LimitReader<R> {
     limit: uint,
     inner: R
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io::Take")]
+#[unstable(feature = "old_io")]
 impl<R: Reader> LimitReader<R> {
     /// Creates a new `LimitReader`
+    #[deprecated(since = "1.0.0", reason = "use std::io's take method instead")]
+    #[unstable(feature = "old_io")]
     pub fn new(r: R, limit: uint) -> LimitReader<R> {
         LimitReader { limit: limit, inner: r }
     }
@@ -41,6 +49,8 @@ pub fn into_inner(self) -> R { self.inner }
     pub fn limit(&self) -> uint { self.limit }
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io's take method instead")]
+#[unstable(feature = "old_io")]
 impl<R: Reader> Reader for LimitReader<R> {
     fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
         if self.limit == 0 {
@@ -57,6 +67,8 @@ fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
     }
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io's take method instead")]
+#[unstable(feature = "old_io")]
 impl<R: Buffer> Buffer for LimitReader<R> {
     fn fill_buf<'a>(&'a mut self) -> old_io::IoResult<&'a [u8]> {
         let amt = try!(self.inner.fill_buf());
@@ -79,8 +91,12 @@ fn consume(&mut self, amt: uint) {
 
 /// A `Writer` which ignores bytes written to it, like /dev/null.
 #[derive(Copy, Debug)]
+#[deprecated(since = "1.0.0", reason = "use std::io::sink() instead")]
+#[unstable(feature = "old_io")]
 pub struct NullWriter;
 
+#[deprecated(since = "1.0.0", reason = "use std::io::sink() instead")]
+#[unstable(feature = "old_io")]
 impl Writer for NullWriter {
     #[inline]
     fn write_all(&mut self, _buf: &[u8]) -> old_io::IoResult<()> { Ok(()) }
@@ -88,8 +104,12 @@ fn write_all(&mut self, _buf: &[u8]) -> old_io::IoResult<()> { Ok(()) }
 
 /// A `Reader` which returns an infinite stream of 0 bytes, like /dev/zero.
 #[derive(Copy, Debug)]
+#[deprecated(since = "1.0.0", reason = "use std::io::repeat(0) instead")]
+#[unstable(feature = "old_io")]
 pub struct ZeroReader;
 
+#[deprecated(since = "1.0.0", reason = "use std::io::repeat(0) instead")]
+#[unstable(feature = "old_io")]
 impl Reader for ZeroReader {
     #[inline]
     fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
@@ -98,6 +118,8 @@ fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
     }
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io::repeat(0) instead")]
+#[unstable(feature = "old_io")]
 impl Buffer for ZeroReader {
     fn fill_buf<'a>(&'a mut self) -> old_io::IoResult<&'a [u8]> {
         static DATA: [u8; 64] = [0; 64];
@@ -109,8 +131,12 @@ fn consume(&mut self, _amt: uint) {}
 
 /// A `Reader` which is always at EOF, like /dev/null.
 #[derive(Copy, Debug)]
+#[deprecated(since = "1.0.0", reason = "use std::io::empty() instead")]
+#[unstable(feature = "old_io")]
 pub struct NullReader;
 
+#[deprecated(since = "1.0.0", reason = "use std::io::empty() instead")]
+#[unstable(feature = "old_io")]
 impl Reader for NullReader {
     #[inline]
     fn read(&mut self, _buf: &mut [u8]) -> old_io::IoResult<uint> {
@@ -118,6 +144,8 @@ fn read(&mut self, _buf: &mut [u8]) -> old_io::IoResult<uint> {
     }
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io::empty() instead")]
+#[unstable(feature = "old_io")]
 impl Buffer for NullReader {
     fn fill_buf<'a>(&'a mut self) -> old_io::IoResult<&'a [u8]> {
         Err(old_io::standard_error(old_io::EndOfFile))
@@ -130,17 +158,23 @@ fn consume(&mut self, _amt: uint) {}
 /// The `Writer`s are delegated to in order. If any `Writer` returns an error,
 /// that error is returned immediately and remaining `Writer`s are not called.
 #[derive(Debug)]
+#[deprecated(since = "1.0.0", reason = "use std::io::Broadcast instead")]
+#[unstable(feature = "old_io")]
 pub struct MultiWriter<W> {
     writers: Vec<W>
 }
 
 impl<W> MultiWriter<W> where W: Writer {
     /// Creates a new `MultiWriter`
+    #[deprecated(since = "1.0.0", reason = "use std::io's broadcast method instead")]
+    #[unstable(feature = "old_io")]
     pub fn new(writers: Vec<W>) -> MultiWriter<W> {
         MultiWriter { writers: writers }
     }
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io::Broadcast instead")]
+#[unstable(feature = "old_io")]
 impl<W> Writer for MultiWriter<W> where W: Writer {
     #[inline]
     fn write_all(&mut self, buf: &[u8]) -> old_io::IoResult<()> {
@@ -162,6 +196,8 @@ fn flush(&mut self) -> old_io::IoResult<()> {
 /// A `Reader` which chains input from multiple `Reader`s, reading each to
 /// completion before moving onto the next.
 #[derive(Clone, Debug)]
+#[deprecated(since = "1.0.0", reason = "use std::io::Chain instead")]
+#[unstable(feature = "old_io")]
 pub struct ChainedReader<I, R> {
     readers: I,
     cur_reader: Option<R>,
@@ -169,12 +205,16 @@ pub struct ChainedReader<I, R> {
 
 impl<R: Reader, I: Iterator<Item=R>> ChainedReader<I, R> {
     /// Creates a new `ChainedReader`
+    #[deprecated(since = "1.0.0", reason = "use std::io's chain method instead")]
+    #[unstable(feature = "old_io")]
     pub fn new(mut readers: I) -> ChainedReader<I, R> {
         let r = readers.next();
         ChainedReader { readers: readers, cur_reader: r }
     }
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io::Chain instead")]
+#[unstable(feature = "old_io")]
 impl<R: Reader, I: Iterator<Item=R>> Reader for ChainedReader<I, R> {
     fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
         loop {
@@ -201,13 +241,19 @@ fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
 /// A `Reader` which forwards input from another `Reader`, passing it along to
 /// a `Writer` as well. Similar to the `tee(1)` command.
 #[derive(Debug)]
+#[deprecated(since = "1.0.0", reason = "use std::io::Tee instead")]
+#[unstable(feature = "old_io")]
 pub struct TeeReader<R, W> {
     reader: R,
     writer: W,
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io::Tee instead")]
+#[unstable(feature = "old_io")]
 impl<R: Reader, W: Writer> TeeReader<R, W> {
     /// Creates a new `TeeReader`
+    #[deprecated(since = "1.0.0", reason = "use std::io's tee method instead")]
+    #[unstable(feature = "old_io")]
     pub fn new(r: R, w: W) -> TeeReader<R, W> {
         TeeReader { reader: r, writer: w }
     }
@@ -220,6 +266,8 @@ pub fn into_inner(self) -> (R, W) {
     }
 }
 
+#[deprecated(since = "1.0.0", reason = "use std::io::Tee instead")]
+#[unstable(feature = "old_io")]
 impl<R: Reader, W: Writer> Reader for TeeReader<R, W> {
     fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
         self.reader.read(buf).and_then(|len| {
@@ -229,6 +277,8 @@ fn read(&mut self, buf: &mut [u8]) -> old_io::IoResult<uint> {
 }
 
 /// Copies all data from a `Reader` to a `Writer`.
+#[deprecated(since = "1.0.0", reason = "use std::io's copy function instead")]
+#[unstable(feature = "old_io")]
 pub fn copy<R: Reader, W: Writer>(r: &mut R, w: &mut W) -> old_io::IoResult<()> {
     let mut buf = [0; super::DEFAULT_BUF_SIZE];
     loop {
@@ -418,7 +468,7 @@ fn limit_reader_buffer() {
 
     #[test]
     fn test_iter_reader() {
-        let mut r = IterReader::new(0u8..8);
+        let mut r = IterReader::new(0..8);
         let mut buf = [0, 0, 0];
         let len = r.read(&mut buf).unwrap();
         assert_eq!(len, 3);
@@ -437,7 +487,7 @@ fn test_iter_reader() {
 
     #[test]
     fn iter_reader_zero_length() {
-        let mut r = IterReader::new(0u8..8);
+        let mut r = IterReader::new(0..8);
         let mut buf = [];
         assert_eq!(Ok(0), r.read(&mut buf));
     }
index 31a8cbe572a0318d60d8c0afb8f2c710d205cd11..5f2f1728be1a6317a65792f4be1f1351f89ec58c 100644 (file)
@@ -1324,7 +1324,7 @@ fn test_null_byte() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_not_utf8_panics() {
         Path::new(b"hello\x80.txt");
     }
old mode 100755 (executable)
new mode 100644 (file)
index b85a0dc..ad8e17f
@@ -90,7 +90,7 @@
 //! * Repeated separators are ignored: `a/b` and `a//b` both have components `a`
 //!   and `b`.
 //!
-//! * Paths ending in a separator are treated as if they has a current directory
+//! * Paths ending in a separator are treated as if they have a current directory
 //!   component at the end (or, in verbatim paths, an empty component).  For
 //!   example, while `a/b` has components `a` and `b`, the paths `a/b/` and
 //!   `a/b/.` both have components `a`, `b`, and `.` (current directory).  The
@@ -872,10 +872,10 @@ pub fn push<P: ?Sized>(&mut self, path: &P) where P: AsPath {
 
         // `path` is a pure relative path
         } else if need_sep {
-            self.inner.push_os_str(OsStr::from_str(MAIN_SEP_STR));
+            self.inner.push(MAIN_SEP_STR);
         }
 
-        self.inner.push_os_str(path.as_os_str());
+        self.inner.push(path);
     }
 
     /// Truncate `self` to `self.parent()`.
@@ -937,8 +937,8 @@ pub fn set_extension<S: ?Sized + AsOsStr>(&mut self, extension: &S) -> bool {
 
         let extension = extension.as_os_str();
         if os_str_as_u8_slice(extension).len() > 0 {
-            stem.push_os_str(OsStr::from_str("."));
-            stem.push_os_str(extension.as_os_str());
+            stem.push(".");
+            stem.push(extension);
         }
         self.set_file_name(&stem);
 
@@ -1193,7 +1193,7 @@ pub fn starts_with<P: ?Sized>(&self, base: &P) -> bool where P: AsPath {
         iter_after(self.components(), base.as_path().components()).is_some()
     }
 
-    /// Determines whether `base` is a suffix of `self`.
+    /// Determines whether `child` is a suffix of `self`.
     pub fn ends_with<P: ?Sized>(&self, child: &P) -> bool where P: AsPath {
         iter_after(self.components().rev(), child.as_path().components().rev()).is_some()
     }
index dad0ff0a15e299424d265b076d15f20f229c525b..60e1354482c8f4626eb1872e3a5fb909afe65cf4 100644 (file)
@@ -58,3 +58,5 @@
 #[doc(no_inline)] pub use old_io::{Buffer, Writer, Reader, Seek, BufferPrelude};
 // NB: remove when range syntax lands
 #[doc(no_inline)] pub use iter::range;
+
+#[doc(no_inline)] pub use num::wrapping::{Wrapping, WrappingOps};
index c24b08deec2dc482d8395a7038214f22fc7762c9..ec4fcec5556223d98fc73eef43e3ef90d3b2ef29 100644 (file)
@@ -10,7 +10,7 @@
 
 //! Working with processes.
 
-#![unstable(feature = "process", reason = "recently added via RFC 579")]
+#![stable(feature = "process", since = "1.0.0")]
 #![allow(non_upper_case_globals)]
 
 use prelude::v1::*;
@@ -48,6 +48,7 @@
 /// let contents = output.stdout;
 /// assert!(output.status.success());
 /// ```
+#[stable(feature = "process", since = "1.0.0")]
 pub struct Child {
     handle: ProcessImp,
 
@@ -55,20 +56,25 @@ pub struct Child {
     status: Option<ExitStatusImp>,
 
     /// The handle for writing to the child's stdin, if it has been captured
+    #[stable(feature = "process", since = "1.0.0")]
     pub stdin: Option<ChildStdin>,
 
     /// The handle for reading from the child's stdout, if it has been captured
+    #[stable(feature = "process", since = "1.0.0")]
     pub stdout: Option<ChildStdout>,
 
     /// The handle for reading from the child's stderr, if it has been captured
+    #[stable(feature = "process", since = "1.0.0")]
     pub stderr: Option<ChildStderr>,
 }
 
 /// A handle to a child procesess's stdin
+#[stable(feature = "process", since = "1.0.0")]
 pub struct ChildStdin {
     inner: AnonPipe
 }
 
+#[stable(feature = "process", since = "1.0.0")]
 impl Write for ChildStdin {
     fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
         self.inner.write(buf)
@@ -80,10 +86,12 @@ fn flush(&mut self) -> io::Result<()> {
 }
 
 /// A handle to a child procesess's stdout
+#[stable(feature = "process", since = "1.0.0")]
 pub struct ChildStdout {
     inner: AnonPipe
 }
 
+#[stable(feature = "process", since = "1.0.0")]
 impl Read for ChildStdout {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         self.inner.read(buf)
@@ -91,10 +99,12 @@ fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
 }
 
 /// A handle to a child procesess's stderr
+#[stable(feature = "process", since = "1.0.0")]
 pub struct ChildStderr {
     inner: AnonPipe
 }
 
+#[stable(feature = "process", since = "1.0.0")]
 impl Read for ChildStderr {
     fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
         self.inner.read(buf)
@@ -108,8 +118,6 @@ fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
 /// to be changed (for example, by adding arguments) prior to spawning:
 ///
 /// ```
-/// # #![feature(process)]
-///
 /// use std::process::Command;
 ///
 /// let output = Command::new("sh").arg("-c").arg("echo hello").output().unwrap_or_else(|e| {
@@ -117,6 +125,7 @@ fn read(&mut self, buf: &mut [u8]) -> io::Result<usize> {
 /// });
 /// let hello = output.stdout;
 /// ```
+#[stable(feature = "process", since = "1.0.0")]
 pub struct Command {
     inner: CommandImp,
 
@@ -137,6 +146,7 @@ impl Command {
     ///
     /// Builder methods are provided to change these defaults and
     /// otherwise configure the process.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn new<S: AsOsStr + ?Sized>(program: &S) -> Command {
         Command {
             inner: CommandImp::new(program.as_os_str()),
@@ -147,12 +157,14 @@ pub fn new<S: AsOsStr + ?Sized>(program: &S) -> Command {
     }
 
     /// Add an argument to pass to the program.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn arg<S: AsOsStr + ?Sized>(&mut self, arg: &S) -> &mut Command {
         self.inner.arg(arg.as_os_str());
         self
     }
 
     /// Add multiple arguments to pass to the program.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn args<S: AsOsStr>(&mut self, args: &[S]) -> &mut Command {
         self.inner.args(args.iter().map(AsOsStr::as_os_str));
         self
@@ -162,26 +174,30 @@ pub fn args<S: AsOsStr>(&mut self, args: &[S]) -> &mut Command {
     ///
     /// Note that environment variable names are case-insensitive (but case-preserving) on Windows,
     /// and case-sensitive on all other platforms.
-    pub fn env<S: ?Sized, T: ?Sized>(&mut self, key: &S, val: &T) -> &mut Command where
-        S: AsOsStr, T: AsOsStr
+    #[stable(feature = "process", since = "1.0.0")]
+    pub fn env<K: ?Sized, V: ?Sized>(&mut self, key: &K, val: &V) -> &mut Command
+        where K: AsOsStr, V: AsOsStr
     {
         self.inner.env(key.as_os_str(), val.as_os_str());
         self
     }
 
     /// Removes an environment variable mapping.
-    pub fn env_remove<S: ?Sized + AsOsStr>(&mut self, key: &S) -> &mut Command {
+    #[stable(feature = "process", since = "1.0.0")]
+    pub fn env_remove<K: ?Sized + AsOsStr>(&mut self, key: &K) -> &mut Command {
         self.inner.env_remove(key.as_os_str());
         self
     }
 
     /// Clears the entire environment map for the child process.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn env_clear(&mut self) -> &mut Command {
         self.inner.env_clear();
         self
     }
 
     /// Set the working directory for the child process.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn current_dir<P: AsPath + ?Sized>(&mut self, dir: &P) -> &mut Command {
         self.inner.cwd(dir.as_path().as_os_str());
         self
@@ -189,6 +205,7 @@ pub fn current_dir<P: AsPath + ?Sized>(&mut self, dir: &P) -> &mut Command {
 
     /// Configuration for the child process's stdin handle (file descriptor 0).
     /// Defaults to `CreatePipe(true, false)` so the input can be written to.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn stdin(&mut self, cfg: Stdio) -> &mut Command {
         self.stdin = Some(cfg.0);
         self
@@ -196,6 +213,7 @@ pub fn stdin(&mut self, cfg: Stdio) -> &mut Command {
 
     /// Configuration for the child process's stdout handle (file descriptor 1).
     /// Defaults to `CreatePipe(false, true)` so the output can be collected.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn stdout(&mut self, cfg: Stdio) -> &mut Command {
         self.stdout = Some(cfg.0);
         self
@@ -203,6 +221,7 @@ pub fn stdout(&mut self, cfg: Stdio) -> &mut Command {
 
     /// Configuration for the child process's stderr handle (file descriptor 2).
     /// Defaults to `CreatePipe(false, true)` so the output can be collected.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn stderr(&mut self, cfg: Stdio) -> &mut Command {
         self.stderr = Some(cfg.0);
         self
@@ -234,6 +253,7 @@ fn spawn_inner(&self, default_io: StdioImp) -> io::Result<Child> {
     /// Executes the command as a child process, returning a handle to it.
     ///
     /// By default, stdin, stdout and stderr are inherited by the parent.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn spawn(&mut self) -> io::Result<Child> {
         self.spawn_inner(StdioImp::Inherit)
     }
@@ -244,7 +264,7 @@ pub fn spawn(&mut self) -> io::Result<Child> {
     /// By default, stdin, stdout and stderr are captured (and used to
     /// provide the resulting output).
     ///
-    /// # Example
+    /// # Examples
     ///
     /// ```
     /// # #![feature(process)]
@@ -255,11 +275,12 @@ pub fn spawn(&mut self) -> io::Result<Child> {
     /// });
     ///
     /// println!("status: {}", output.status);
-    /// println!("stdout: {}", String::from_utf8_lossy(output.stdout.as_slice()));
-    /// println!("stderr: {}", String::from_utf8_lossy(output.stderr.as_slice()));
+    /// println!("stdout: {}", String::from_utf8_lossy(&output.stdout));
+    /// println!("stderr: {}", String::from_utf8_lossy(&output.stderr));
     /// ```
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn output(&mut self) -> io::Result<Output> {
-        self.spawn_inner(StdioImp::Capture).and_then(|p| p.wait_with_output())
+        self.spawn_inner(StdioImp::Piped).and_then(|p| p.wait_with_output())
     }
 
     /// Executes a command as a child process, waiting for it to finish and
@@ -279,6 +300,7 @@ pub fn output(&mut self) -> io::Result<Output> {
     ///
     /// println!("process exited with: {}", status);
     /// ```
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn status(&mut self) -> io::Result<ExitStatus> {
         self.spawn().and_then(|mut p| p.wait())
     }
@@ -317,7 +339,7 @@ fn setup_io(io: &StdioImp, fd: libc::c_int, readable: bool)
         Inherit => {
             (Some(AnonPipe::from_fd(fd)), None)
         }
-        Capture => {
+        Piped => {
             let (reader, writer) = try!(unsafe { pipe2::anon_pipe() });
             if readable {
                 (Some(reader), Some(writer))
@@ -330,45 +352,60 @@ fn setup_io(io: &StdioImp, fd: libc::c_int, readable: bool)
 
 /// The output of a finished process.
 #[derive(PartialEq, Eq, Clone)]
+#[stable(feature = "process", since = "1.0.0")]
 pub struct Output {
     /// The status (exit code) of the process.
+    #[stable(feature = "process", since = "1.0.0")]
     pub status: ExitStatus,
     /// The data that the process wrote to stdout.
+    #[stable(feature = "process", since = "1.0.0")]
     pub stdout: Vec<u8>,
     /// The data that the process wrote to stderr.
+    #[stable(feature = "process", since = "1.0.0")]
     pub stderr: Vec<u8>,
 }
 
 /// Describes what to do with a standard io stream for a child process.
+#[stable(feature = "process", since = "1.0.0")]
 pub struct Stdio(StdioImp);
 
 // The internal enum for stdio setup; see below for descriptions.
 #[derive(Clone)]
 enum StdioImp {
-    Capture,
+    Piped,
     Inherit,
     Null,
 }
 
 impl Stdio {
     /// A new pipe should be arranged to connect the parent and child processes.
-    pub fn capture() -> Stdio { Stdio(StdioImp::Capture) }
+    #[unstable(feature = "process_capture")]
+    #[deprecated(since = "1.0.0", reason = "renamed to `Stdio::piped`")]
+    pub fn capture() -> Stdio { Stdio::piped() }
+
+    /// A new pipe should be arranged to connect the parent and child processes.
+    #[stable(feature = "process", since = "1.0.0")]
+    pub fn piped() -> Stdio { Stdio(StdioImp::Piped) }
 
     /// The child inherits from the corresponding parent descriptor.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn inherit() -> Stdio { Stdio(StdioImp::Inherit) }
 
     /// This stream will be ignored. This is the equivalent of attaching the
     /// stream to `/dev/null`
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn null() -> Stdio { Stdio(StdioImp::Null) }
 }
 
 /// Describes the result of a process after it has terminated.
 #[derive(PartialEq, Eq, Clone, Copy, Debug)]
+#[stable(feature = "process", since = "1.0.0")]
 pub struct ExitStatus(ExitStatusImp);
 
 impl ExitStatus {
     /// Was termination successful? Signal termination not considered a success,
     /// and success is defined as a zero exit status.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn success(&self) -> bool {
         self.0.success()
     }
@@ -378,6 +415,7 @@ pub fn success(&self) -> bool {
     /// On Unix, this will return `None` if the process was terminated
     /// by a signal; `std::os::unix` provides an extension trait for
     /// extracting the signal and other details from the `ExitStatus`.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn code(&self) -> Option<i32> {
         self.0.code()
     }
@@ -387,6 +425,7 @@ impl AsInner<ExitStatusImp> for ExitStatus {
     fn as_inner(&self) -> &ExitStatusImp { &self.0 }
 }
 
+#[stable(feature = "process", since = "1.0.0")]
 impl fmt::Display for ExitStatus {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
         self.0.fmt(f)
@@ -396,6 +435,7 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
 impl Child {
     /// Forces the child to exit. This is equivalent to sending a
     /// SIGKILL on unix platforms.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn kill(&mut self) -> io::Result<()> {
         #[cfg(unix)] fn collect_status(p: &mut Child) {
             // On Linux (and possibly other unices), a process that has exited will
@@ -436,6 +476,7 @@ pub fn kill(&mut self) -> io::Result<()> {
     /// before waiting. This helps avoid deadlock: it ensures that the
     /// child does not block waiting for input from the parent, while
     /// the parent waits for the child to exit.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn wait(&mut self) -> io::Result<ExitStatus> {
         drop(self.stdin.take());
         match self.status {
@@ -456,6 +497,7 @@ pub fn wait(&mut self) -> io::Result<ExitStatus> {
     /// before waiting. This helps avoid deadlock: it ensures that the
     /// child does not block waiting for input from the parent, while
     /// the parent waits for the child to exit.
+    #[stable(feature = "process", since = "1.0.0")]
     pub fn wait_with_output(mut self) -> io::Result<Output> {
         drop(self.stdin.take());
         fn read<T: Read + Send + 'static>(stream: Option<T>) -> Receiver<io::Result<Vec<u8>>> {
@@ -557,7 +599,7 @@ pub fn run_output(mut cmd: Command) -> String {
     #[test]
     fn stdout_works() {
         let mut cmd = Command::new("echo");
-        cmd.arg("foobar").stdout(Stdio::capture());
+        cmd.arg("foobar").stdout(Stdio::piped());
         assert_eq!(run_output(cmd), "foobar\n");
     }
 
@@ -567,7 +609,7 @@ fn set_current_dir_works() {
         let mut cmd = Command::new("/bin/sh");
         cmd.arg("-c").arg("pwd")
            .current_dir("/")
-           .stdout(Stdio::capture());
+           .stdout(Stdio::piped());
         assert_eq!(run_output(cmd), "/\n");
     }
 
@@ -576,8 +618,8 @@ fn set_current_dir_works() {
     fn stdin_works() {
         let mut p = Command::new("/bin/sh")
                             .arg("-c").arg("read line; echo $line")
-                            .stdin(Stdio::capture())
-                            .stdout(Stdio::capture())
+                            .stdin(Stdio::piped())
+                            .stdout(Stdio::piped())
                             .spawn().unwrap();
         p.stdin.as_mut().unwrap().write("foobar".as_bytes()).unwrap();
         drop(p.stdin.take());
@@ -675,7 +717,7 @@ fn test_finish_twice() {
     #[cfg(not(target_os="android"))]
     #[test]
     fn test_wait_with_output_once() {
-        let prog = Command::new("echo").arg("hello").stdout(Stdio::capture())
+        let prog = Command::new("echo").arg("hello").stdout(Stdio::piped())
             .spawn().unwrap();
         let Output {status, stdout, stderr} = prog.wait_with_output().unwrap();
         let output_str = str::from_utf8(stdout.as_slice()).unwrap();
@@ -761,17 +803,16 @@ pub fn env_cmd() -> Command {
     #[cfg(not(target_os="android"))]
     #[test]
     fn test_inherit_env() {
-        use os;
+        use std::env;
         if running_on_valgrind() { return; }
 
         let result = env_cmd().output().unwrap();
         let output = String::from_utf8(result.stdout).unwrap();
 
-        let r = os::env();
-        for &(ref k, ref v) in &r {
+        for (ref k, ref v) in env::vars() {
             // don't check windows magical empty-named variables
             assert!(k.is_empty() ||
-                    output.contains(format!("{}={}", *k, *v).as_slice()),
+                    output.contains(&format!("{}={}", *k, *v)),
                     "output doesn't contain `{}={}`\n{}",
                     k, v, output);
         }
@@ -789,12 +830,12 @@ fn test_inherit_env() {
         for &(ref k, ref v) in &r {
             // don't check android RANDOM variables
             if *k != "RANDOM".to_string() {
-                assert!(output.contains(format!("{}={}",
-                                                *k,
-                                                *v).as_slice()) ||
-                        output.contains(format!("{}=\'{}\'",
-                                                *k,
-                                                *v).as_slice()));
+                assert!(output.contains(&format!("{}={}",
+                                                 *k,
+                                                 *v)) ||
+                        output.contains(&format!("{}=\'{}\'",
+                                                 *k,
+                                                 *v)));
             }
         }
     }
index 5c891441198039940cab0e08776a06379d9bf860..7382cc6e2eb33cd1f19fb15e21593ac01247ca11 100644 (file)
@@ -321,7 +321,7 @@ fn reseed(&mut self, rng: &mut StdRng) {
         }
     }
 }
-static THREAD_RNG_RESEED_THRESHOLD: usize = 32_768;
+const THREAD_RNG_RESEED_THRESHOLD: usize = 32_768;
 type ThreadRngInner = reseeding::ReseedingRng<StdRng, ThreadRngReseeder>;
 
 /// The thread-local RNG.
@@ -386,8 +386,8 @@ fn fill_bytes(&mut self, bytes: &mut [u8]) {
 /// ```
 /// use std::rand;
 ///
-/// let x = rand::random();
-/// println!("{}", 2u8 * x);
+/// let x: u8 = rand::random();
+/// println!("{}", 2 * x as u16);
 ///
 /// let y = rand::random::<f64>();
 /// println!("{}", y);
@@ -468,7 +468,7 @@ fn test_fill_bytes_default() {
         let lengths = [0, 1, 2, 3, 4, 5, 6, 7,
                        80, 81, 82, 83, 84, 85, 86, 87];
         for &n in &lengths {
-            let mut v = repeat(0u8).take(n).collect::<Vec<_>>();
+            let mut v = repeat(0).take(n).collect::<Vec<_>>();
             r.fill_bytes(&mut v);
 
             // use this to get nicer error messages.
@@ -500,14 +500,14 @@ fn test_gen_range() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_gen_range_panic_int() {
         let mut r = thread_rng();
         r.gen_range(5, -2);
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_gen_range_panic_uint() {
         let mut r = thread_rng();
         r.gen_range(5, 2);
@@ -638,19 +638,18 @@ fn test_std_rng_reseed() {
     }
 }
 
-#[cfg(test)]
-static RAND_BENCH_N: u64 = 100;
-
 #[cfg(test)]
 mod bench {
     extern crate test;
     use prelude::v1::*;
 
     use self::test::Bencher;
-    use super::{XorShiftRng, StdRng, IsaacRng, Isaac64Rng, Rng, RAND_BENCH_N};
+    use super::{XorShiftRng, StdRng, IsaacRng, Isaac64Rng, Rng};
     use super::{OsRng, weak_rng};
     use mem::size_of;
 
+    const RAND_BENCH_N: u64 = 100;
+
     #[bench]
     fn rand_xorshift(b: &mut Bencher) {
         let mut rng: XorShiftRng = OsRng::new().unwrap().gen();
index 1a13405633d2ede6f2218e4caa596c67baf7d4e1..6cb3eb4d16e613a4102bbe5fadcdd28d927521fb 100644 (file)
@@ -80,13 +80,13 @@ fn getrandom_fill_bytes(v: &mut [u8]) {
     }
 
     fn getrandom_next_u32() -> u32 {
-        let mut buf: [u8; 4] = [0u8; 4];
+        let mut buf: [u8; 4] = [0; 4];
         getrandom_fill_bytes(&mut buf);
         unsafe { mem::transmute::<[u8; 4], u32>(buf) }
     }
 
     fn getrandom_next_u64() -> u64 {
-        let mut buf: [u8; 8] = [0u8; 8];
+        let mut buf: [u8; 8] = [0; 8];
         getrandom_fill_bytes(&mut buf);
         unsafe { mem::transmute::<[u8; 8], u64>(buf) }
     }
@@ -231,12 +231,12 @@ pub fn new() -> IoResult<OsRng> {
 
     impl Rng for OsRng {
         fn next_u32(&mut self) -> u32 {
-            let mut v = [0u8; 4];
+            let mut v = [0; 4];
             self.fill_bytes(&mut v);
             unsafe { mem::transmute(v) }
         }
         fn next_u64(&mut self) -> u64 {
-            let mut v = [0u8; 8];
+            let mut v = [0; 8];
             self.fill_bytes(&mut v);
             unsafe { mem::transmute(v) }
         }
@@ -281,9 +281,9 @@ pub struct OsRng {
         hcryptprov: HCRYPTPROV
     }
 
-    static PROV_RSA_FULL: DWORD = 1;
-    static CRYPT_SILENT: DWORD = 64;
-    static CRYPT_VERIFYCONTEXT: DWORD = 0xF0000000;
+    const PROV_RSA_FULL: DWORD = 1;
+    const CRYPT_SILENT: DWORD = 64;
+    const CRYPT_VERIFYCONTEXT: DWORD = 0xF0000000;
 
     #[allow(non_snake_case)]
     extern "system" {
@@ -318,12 +318,12 @@ pub fn new() -> IoResult<OsRng> {
 
     impl Rng for OsRng {
         fn next_u32(&mut self) -> u32 {
-            let mut v = [0u8; 4];
+            let mut v = [0; 4];
             self.fill_bytes(&mut v);
             unsafe { mem::transmute(v) }
         }
         fn next_u64(&mut self) -> u64 {
-            let mut v = [0u8; 8];
+            let mut v = [0; 8];
             self.fill_bytes(&mut v);
             unsafe { mem::transmute(v) }
         }
@@ -366,7 +366,7 @@ fn test_os_rng() {
         r.next_u32();
         r.next_u64();
 
-        let mut v = [0u8; 1000];
+        let mut v = [0; 1000];
         r.fill_bytes(&mut v);
     }
 
@@ -386,7 +386,7 @@ fn test_os_rng_tasks() {
                 // as possible (XXX: is this a good test?)
                 let mut r = OsRng::new().unwrap();
                 thread::yield_now();
-                let mut v = [0u8; 1000];
+                let mut v = [0; 1000];
 
                 for _ in 0..100 {
                     r.next_u32();
index b71e8b4fd61e8dadebd3d9fa754e559b23ee4532..c56dc387b7fe6773fa0c69ad0188242c729e3974 100644 (file)
@@ -84,28 +84,28 @@ mod test {
     #[test]
     fn test_reader_rng_u64() {
         // transmute from the target to avoid endianness concerns.
-        let v = vec![0u8, 0, 0, 0, 0, 0, 0, 1,
+        let v = vec![0, 0, 0, 0, 0, 0, 0, 1,
                      0  , 0, 0, 0, 0, 0, 0, 2,
                      0,   0, 0, 0, 0, 0, 0, 3];
         let mut rng = ReaderRng::new(MemReader::new(v));
 
-        assert_eq!(rng.next_u64(), 1_u64.to_be());
-        assert_eq!(rng.next_u64(), 2_u64.to_be());
-        assert_eq!(rng.next_u64(), 3_u64.to_be());
+        assert_eq!(rng.next_u64(), 1.to_be());
+        assert_eq!(rng.next_u64(), 2.to_be());
+        assert_eq!(rng.next_u64(), 3.to_be());
     }
     #[test]
     fn test_reader_rng_u32() {
-        let v = vec![0u8, 0, 0, 1, 0, 0, 0, 2, 0, 0, 0, 3];
+        let v = vec![0, 0, 0, 1, 0, 0, 0, 2, 0, 0, 0, 3];
         let mut rng = ReaderRng::new(MemReader::new(v));
 
-        assert_eq!(rng.next_u32(), 1_u32.to_be());
-        assert_eq!(rng.next_u32(), 2_u32.to_be());
-        assert_eq!(rng.next_u32(), 3_u32.to_be());
+        assert_eq!(rng.next_u32(), 1.to_be());
+        assert_eq!(rng.next_u32(), 2.to_be());
+        assert_eq!(rng.next_u32(), 3.to_be());
     }
     #[test]
     fn test_reader_rng_fill_bytes() {
-        let v = [1u8, 2, 3, 4, 5, 6, 7, 8];
-        let mut w = [0u8; 8];
+        let v = [1, 2, 3, 4, 5, 6, 7, 8];
+        let mut w = [0; 8];
 
         let mut rng = ReaderRng::new(MemReader::new(v.to_vec()));
         rng.fill_bytes(&mut w);
@@ -114,10 +114,10 @@ fn test_reader_rng_fill_bytes() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_reader_rng_insufficient_bytes() {
         let mut rng = ReaderRng::new(MemReader::new(vec!()));
-        let mut v = [0u8; 3];
+        let mut v = [0; 3];
         rng.fill_bytes(&mut v);
     }
 }
index 42cca73e5e24128e2b40b92b64615277aa01da82..fe32a51e81c9ac323cab3852cefd967634658e79 100644 (file)
@@ -27,6 +27,7 @@
 use ops::FnOnce;
 use sys;
 use thunk::Thunk;
+use usize;
 
 // Reexport some of our utilities which are expected by other crates.
 pub use self::util::{default_sched_threads, min_stack, running_on_valgrind};
@@ -78,7 +79,20 @@ fn lang_start(main: *const u8, argc: int, argv: *const *const u8) -> int {
     // FIXME #11359 we just assume that this thread has a stack of a
     // certain size, and estimate that there's at most 20KB of stack
     // frames above our current position.
-    let my_stack_bottom = my_stack_top + 20000 - OS_DEFAULT_STACK_ESTIMATE;
+    const TWENTY_KB: uint = 20000;
+
+    // saturating-add to sidestep overflow
+    let top_plus_spill = if usize::MAX - TWENTY_KB < my_stack_top {
+        usize::MAX
+    } else {
+        my_stack_top + TWENTY_KB
+    };
+    // saturating-sub to sidestep underflow
+    let my_stack_bottom = if top_plus_spill < OS_DEFAULT_STACK_ESTIMATE {
+        0
+    } else {
+        top_plus_spill - OS_DEFAULT_STACK_ESTIMATE
+    };
 
     let failed = unsafe {
         // First, make sure we don't trigger any __morestack overflow checks,
index 4dda3ea8c998800e94cde11c237296ab2ee502da..ebb2a2e4827a10770098405b7c2b3e9d44c60c21 100644 (file)
@@ -166,7 +166,7 @@ fn rust_panic(cause: Box<Any + Send + 'static>) -> ! {
     rtdebug!("begin_unwind()");
 
     unsafe {
-        let exception = box Exception {
+        let exception: Box<_> = box Exception {
             uwe: uw::_Unwind_Exception {
                 exception_class: rust_exception_class(),
                 exception_cleanup: exception_cleanup,
@@ -506,7 +506,7 @@ pub fn begin_unwind_fmt(msg: fmt::Arguments, file_line: &(&'static str, uint)) -
 
     let mut s = String::new();
     let _ = write!(&mut s, "{}", msg);
-    begin_unwind_inner(box s, file_line)
+    begin_unwind_inner(Box::new(s), file_line)
 }
 
 /// This is the entry point of unwinding for panic!() and assert!().
@@ -521,7 +521,7 @@ pub fn begin_unwind<M: Any + Send>(msg: M, file_line: &(&'static str, uint)) ->
     // panicking.
 
     // see below for why we do the `Any` coercion here.
-    begin_unwind_inner(box msg, file_line)
+    begin_unwind_inner(Box::new(msg), file_line)
 }
 
 /// The core of the unwinding.
index a304f1f844d748f8f263fc73db78d984ec38bbe9..dc55740315349b56c87d4042f3e209e81050c34b 100644 (file)
@@ -139,7 +139,7 @@ fn write_str(&mut self, bytes: &str) -> fmt::Result {
     }
 
     // Convert the arguments into a stack-allocated string
-    let mut msg = [0u8; 512];
+    let mut msg = [0; 512];
     let mut w = BufWriter { buf: &mut msg, pos: 0 };
     let _ = write!(&mut w, "{}", args);
     let msg = str::from_utf8(&w.buf[..w.pos]).unwrap_or("aborted");
index e7ee9bd2066514f4e47a04b3bf2eb102de874fc6..3499675f5422d81c508f37c405ae3ecbc4c5c05b 100644 (file)
@@ -479,7 +479,7 @@ fn wait_timeout_with() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn two_mutexes() {
         static M1: StaticMutex = MUTEX_INIT;
         static M2: StaticMutex = MUTEX_INIT;
index d60e27388086444a4323c8f53525a8046b28ecec..ee9bcd3dd89bf630d28886e8357f62ea41297def 100644 (file)
@@ -204,7 +204,7 @@ fn test_spawn() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_future_panic() {
         let mut f = Future::spawn(move|| panic!());
         let _x: String = f.get();
index 1310d476f8ee20f15540b6bc75f7df4a64eb7acc..2ae1d4a9d50bc42f7adc9b130052740c45cbdcc6 100644 (file)
 use prelude::v1::*;
 
 use sync::Arc;
+use error;
 use fmt;
 use mem;
 use cell::UnsafeCell;
@@ -975,6 +976,18 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T> error::Error for SendError<T> {
+
+    fn description(&self) -> &str {
+        "sending on a closed channel"
+    }
+
+    fn cause(&self) -> Option<&error::Error> {
+        None
+    }
+}
+
 #[stable(feature = "rust1", since = "1.0.0")]
 impl<T> fmt::Debug for TrySendError<T> {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
@@ -999,6 +1012,25 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
+impl<T> error::Error for TrySendError<T> {
+
+    fn description(&self) -> &str {
+        match *self {
+            TrySendError::Full(..) => {
+                "sending on a full channel"
+            }
+            TrySendError::Disconnected(..) => {
+                "sending on a closed channel"
+            }
+        }
+    }
+
+    fn cause(&self) -> Option<&error::Error> {
+        None
+    }
+}
+
 #[stable(feature = "rust1", since = "1.0.0")]
 impl fmt::Display for RecvError {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
@@ -1006,6 +1038,18 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
+impl error::Error for RecvError {
+
+    fn description(&self) -> &str {
+        "receiving on a closed channel"
+    }
+
+    fn cause(&self) -> Option<&error::Error> {
+        None
+    }
+}
+
 #[stable(feature = "rust1", since = "1.0.0")]
 impl fmt::Display for TryRecvError {
     fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
@@ -1020,6 +1064,25 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
     }
 }
 
+#[stable(feature = "rust1", since = "1.0.0")]
+impl error::Error for TryRecvError {
+
+    fn description(&self) -> &str {
+        match *self {
+            TryRecvError::Empty => {
+                "receiving on an empty channel"
+            }
+            TryRecvError::Disconnected => {
+                "receiving on a closed channel"
+            }
+        }
+    }
+
+    fn cause(&self) -> Option<&error::Error> {
+        None
+    }
+}
+
 #[cfg(test)]
 mod test {
     use prelude::v1::*;
@@ -1044,13 +1107,13 @@ fn smoke() {
 
     #[test]
     fn drop_full() {
-        let (tx, _rx) = channel();
+        let (tx, _rx) = channel::<Box<int>>();
         tx.send(box 1).unwrap();
     }
 
     #[test]
     fn drop_full_shared() {
-        let (tx, _rx) = channel();
+        let (tx, _rx) = channel::<Box<int>>();
         drop(tx.clone());
         drop(tx.clone());
         tx.send(box 1).unwrap();
@@ -1157,8 +1220,8 @@ fn stress() {
 
     #[test]
     fn stress_shared() {
-        static AMT: u32 = 10000;
-        static NTHREADS: u32 = 8;
+        const AMT: u32 = 10000;
+        const NTHREADS: u32 = 8;
         let (tx, rx) = channel::<i32>();
 
         let t = thread::spawn(move|| {
@@ -1389,7 +1452,7 @@ fn oneshot_multi_thread_recv_close_stress() {
     #[test]
     fn oneshot_multi_thread_send_recv_stress() {
         for _ in 0..stress_factor() {
-            let (tx, rx) = channel();
+            let (tx, rx) = channel::<Box<int>>();
             let _t = thread::spawn(move|| {
                 tx.send(box 10).unwrap();
             });
@@ -1566,7 +1629,7 @@ fn smoke() {
 
     #[test]
     fn drop_full() {
-        let (tx, _rx) = sync_channel(1);
+        let (tx, _rx) = sync_channel::<Box<int>>(1);
         tx.send(box 1).unwrap();
     }
 
@@ -1663,8 +1726,8 @@ fn stress() {
 
     #[test]
     fn stress_shared() {
-        static AMT: u32 = 1000;
-        static NTHREADS: u32 = 8;
+        const AMT: u32 = 1000;
+        const NTHREADS: u32 = 8;
         let (tx, rx) = sync_channel::<i32>(0);
         let (dtx, drx) = sync_channel::<()>(0);
 
index 59fa2e6bc9a91c31dc28cc60f8e3ad8b0dfd9861..14ed253d8e27ef8f056d7c1e62a4dd5edeb7be09 100644 (file)
@@ -164,7 +164,7 @@ mod tests {
 
     #[test]
     fn test_full() {
-        let q = Queue::new();
+        let q: Queue<Box<_>> = Queue::new();
         q.push(box 1);
         q.push(box 2);
     }
index 8de5bbc6206658c10d740bc67974e19edb00434f..2c14c9fe3f199020cd1edb9682123c4d1a759c6b 100644 (file)
@@ -473,7 +473,7 @@ fn both_ready() {
 
     #[test]
     fn stress() {
-        static AMT: i32 = 10000;
+        const AMT: i32 = 10000;
         let (tx1, rx1) = channel::<i32>();
         let (tx2, rx2) = channel::<i32>();
         let (tx3, rx3) = channel::<()>();
index ce40fa2672ab32555339aca56e87deed24dbf4a9..3fb13739aa75af4b0a4cc766791a73fc7b39da81 100644 (file)
@@ -289,7 +289,7 @@ fn peek() {
     #[test]
     fn drop_full() {
         unsafe {
-            let q = Queue::new(0);
+            let q: Queue<Box<_>> = Queue::new(0);
             q.push(box 1);
             q.push(box 2);
         }
index 4c3b5d98a3cb172e13673201c2296d49b27f1c54..6f0febd61e80376b8d5d826c9609037436950923 100644 (file)
@@ -390,8 +390,8 @@ fn smoke_static() {
     fn lots_and_lots() {
         static M: StaticMutex = MUTEX_INIT;
         static mut CNT: u32 = 0;
-        static J: u32 = 1000;
-        static K: u32 = 3;
+        const J: u32 = 1000;
+        const K: u32 = 3;
 
         fn inc() {
             for _ in 0..J {
index 454c5b4f0cf7b20eb6bca82ca9cc7d9d3a73a89f..e9ff6c0bf9df0fa2123c09316de7a965fddc0063 100644 (file)
@@ -436,8 +436,8 @@ fn static_smoke() {
     #[test]
     fn frob() {
         static R: StaticRwLock = RW_LOCK_INIT;
-        static N: usize = 10;
-        static M: usize = 1000;
+        const N: usize = 10;
+        const M: usize = 1000;
 
         let (tx, rx) = channel::<()>();
         for _ in 0..N {
index efb6689e7855a40da3f9d374ead25439b9bee138..e41bc6d8683abb14a32df9de279ace42423ad01b 100644 (file)
@@ -164,7 +164,7 @@ fn test_works() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_zero_tasks_panic() {
         TaskPool::new(0);
     }
index 228362e3d62ae2450ed349fae0b518f02db651b6..344645dfc1a159904c59a03698103a3b2a5b9a31 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![allow(deprecated)]
+
 use prelude::v1::*;
 use self::SocketStatus::*;
 use self::InAddr::*;
index 27b8784e3943a6a46320fbddc45c6ee8066d88da..91de2662883f8ce6aa717b326fd6ddccbf954897 100644 (file)
@@ -55,6 +55,7 @@
 //! ```
 
 #![allow(non_camel_case_types)]
+#![unstable(feature = "thread_local_internals")]
 
 use prelude::v1::*;
 
 ///     KEY.set(1 as *mut u8);
 /// }
 /// ```
-#[stable(feature = "rust1", since = "1.0.0")]
 pub struct StaticKey {
     /// Inner static TLS key (internals), created with by `INIT_INNER` in this
     /// module.
-    #[stable(feature = "rust1", since = "1.0.0")]
     pub inner: StaticKeyInner,
     /// Destructor for the TLS value.
     ///
     /// See `Key::new` for information about when the destructor runs and how
     /// it runs.
-    #[stable(feature = "rust1", since = "1.0.0")]
     pub dtor: Option<unsafe extern fn(*mut u8)>,
 }
 
@@ -131,7 +129,6 @@ pub struct Key {
 /// Constant initialization value for static TLS keys.
 ///
 /// This value specifies no destructor by default.
-#[stable(feature = "rust1", since = "1.0.0")]
 pub const INIT: StaticKey = StaticKey {
     inner: INIT_INNER,
     dtor: None,
@@ -140,7 +137,6 @@ pub struct Key {
 /// Constant initialization value for the inner part of static TLS keys.
 ///
 /// This value allows specific configuration of the destructor for a TLS key.
-#[stable(feature = "rust1", since = "1.0.0")]
 pub const INIT_INNER: StaticKeyInner = StaticKeyInner {
     key: atomic::ATOMIC_USIZE_INIT,
 };
index fb9d6fef1faa7e0071343937f6aad0eea519eba4..7a02df23b19c5659a287d06dceab3c16a7b23a6d 100644 (file)
 use ops;
 use slice;
 use str;
-use string::{String, CowString};
+use string::String;
 use sys_common::AsInner;
 use unicode::str::{Utf16Item, utf16_items};
 use vec::Vec;
 
-static UTF8_REPLACEMENT_CHARACTER: &'static [u8] = b"\xEF\xBF\xBD";
+const UTF8_REPLACEMENT_CHARACTER: &'static [u8] = b"\xEF\xBF\xBD";
 
 /// A Unicode code point: from U+0000 to U+10FFFF.
 ///
@@ -530,7 +530,7 @@ pub fn as_str(&self) -> Option<&str> {
     /// Surrogates are replaced with `"\u{FFFD}"` (the replacement character “�”).
     ///
     /// This only copies the data if necessary (if it contains any surrogate).
-    pub fn to_string_lossy(&self) -> CowString {
+    pub fn to_string_lossy(&self) -> Cow<str> {
         let surrogate_pos = match self.next_surrogate(0) {
             None => return Cow::Borrowed(unsafe { str::from_utf8_unchecked(&self.bytes) }),
             Some((pos, _)) => pos,
@@ -714,7 +714,7 @@ pub fn is_code_point_boundary(slice: &Wtf8, index: uint) -> bool {
     if index == slice.len() { return true; }
     match slice.bytes.get(index) {
         None => false,
-        Some(&b) => b < 128u8 || b >= 192u8,
+        Some(&b) => b < 128 || b >= 192,
     }
 }
 
@@ -776,7 +776,7 @@ fn next(&mut self) -> Option<u16> {
             return Some(tmp);
         }
 
-        let mut buf = [0u16; 2];
+        let mut buf = [0; 2];
         self.code_points.next().map(|code_point| {
             let n = encode_utf16_raw(code_point.value, &mut buf)
                 .unwrap_or(0);
@@ -844,7 +844,6 @@ mod tests {
     use borrow::Cow;
     use super::*;
     use mem::transmute;
-    use string::CowString;
 
     #[test]
     fn code_point_from_u32() {
@@ -1031,14 +1030,14 @@ fn wtf8buf_truncate() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn wtf8buf_truncate_fail_code_point_boundary() {
         let mut string = Wtf8Buf::from_str("aé");
         string.truncate(2);
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn wtf8buf_truncate_fail_longer() {
         let mut string = Wtf8Buf::from_str("aé");
         string.truncate(4);
@@ -1134,7 +1133,7 @@ fn wtf8_slice() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn wtf8_slice_not_code_point_boundary() {
         &Wtf8::from_str("aé 💩")[2.. 4];
     }
@@ -1145,7 +1144,7 @@ fn wtf8_slice_from() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn wtf8_slice_from_not_code_point_boundary() {
         &Wtf8::from_str("aé 💩")[2..];
     }
@@ -1156,7 +1155,7 @@ fn wtf8_slice_to() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn wtf8_slice_to_not_code_point_boundary() {
         &Wtf8::from_str("aé 💩")[5..];
     }
@@ -1224,7 +1223,7 @@ fn wtf8_to_string_lossy() {
         assert_eq!(Wtf8::from_str("aé 💩").to_string_lossy(), Cow::Borrowed("aé 💩"));
         let mut string = Wtf8Buf::from_str("aé 💩");
         string.push(CodePoint::from_u32(0xD800).unwrap());
-        let expected: CowString = Cow::Owned(String::from_str("aé 💩�"));
+        let expected: Cow<str> = Cow::Owned(String::from_str("aé 💩�"));
         assert_eq!(string.to_string_lossy(), expected);
     }
 
index 3695b615f62b8fe17237684d631f6f9b733bf700..e7ac6e2cd011c865a44b31653108766e79da8a93 100644 (file)
@@ -176,7 +176,7 @@ struct Context<'a> {
         let mut ip = unsafe {
             uw::_Unwind_GetIPInfo(ctx, &mut ip_before_insn) as *mut libc::c_void
         };
-        if ip_before_insn == 0 {
+        if !ip.is_null() && ip_before_insn == 0 {
             // this is a non-signaling frame, so `ip` refers to the address
             // after the calling instruction. account for that.
             ip = (ip as usize - 1) as *mut _;
@@ -566,7 +566,7 @@ fn _Unwind_VRS_Get(ctx: *mut _Unwind_Context,
 
     // This function doesn't exist on Android or ARM/Linux, so make it same
     // to _Unwind_GetIP
-    #[cfg(any(target_os = "android",
+    #[cfg(any(all(target_os = "android", target_arch = "arm"),
               all(target_os = "linux", target_arch = "arm")))]
     pub unsafe fn _Unwind_GetIPInfo(ctx: *mut _Unwind_Context,
                                     ip_before_insn: *mut libc::c_int)
index 14394a653b0ed5f4d848d51ca0143b43af8c7d03..4e9f9c80a1821c9996dba6a4c6fe6fac8309b3fc 100644 (file)
@@ -194,12 +194,12 @@ mod select {
     #[repr(C)]
     pub struct fd_set {
         // FIXME: shouldn't this be a c_ulong?
-        fds_bits: [libc::uintptr_t; (FD_SETSIZE / usize::BITS)]
+        fds_bits: [libc::uintptr_t; (FD_SETSIZE / usize::BITS as usize)]
     }
 
     pub fn fd_set(set: &mut fd_set, fd: i32) {
         let fd = fd as uint;
-        set.fds_bits[fd / usize::BITS] |= 1 << (fd % usize::BITS);
+        set.fds_bits[fd / usize::BITS as usize] |= 1 << (fd % usize::BITS as usize);
     }
 }
 
index 3f9da6e3c51bb004fb6b1cf40a917825237136b5..ca7f7c4c0ca4446521eb2072efcffe6a7151c2f0 100644 (file)
@@ -54,6 +54,7 @@ pub trait AsRawFd {
     fn as_raw_fd(&self) -> Fd;
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::fs::File {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
@@ -72,42 +73,49 @@ fn as_raw_fd(&self) -> Fd {
     }
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::net::pipe::UnixStream {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::net::pipe::UnixListener {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::net::pipe::UnixAcceptor {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::net::tcp::TcpStream {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::net::tcp::TcpListener {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::net::tcp::TcpAcceptor {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawFd for old_io::net::udp::UdpSocket {
     fn as_raw_fd(&self) -> Fd {
         self.as_inner().fd()
index 71b6214460f4b9550926f95e1488fe2dd73519a1..3d490380bfd61bdce3a33673c7f257887ba0e374 100644 (file)
@@ -389,7 +389,7 @@ fn test_file_desc() {
         let mut writer = FileDesc::new(writer, true);
 
         writer.write(b"test").ok().unwrap();
-        let mut buf = [0u8; 4];
+        let mut buf = [0; 4];
         match reader.read(&mut buf) {
             Ok(4) => {
                 assert_eq!(buf[0], 't' as u8);
index 023d951dc4f8a8aad9152e24f5fc2d527b859425..c8ac524876b5bdfd651ee2d976604f6ea2a90ca8 100644 (file)
 
 use core::prelude::*;
 
+use borrow::Cow;
 use fmt::{self, Debug};
 use vec::Vec;
 use slice::SliceExt as StdSliceExt;
 use str;
-use string::{String, CowString};
+use string::String;
 use mem;
 
 #[derive(Clone, Hash)]
@@ -76,7 +77,7 @@ pub fn to_str(&self) -> Option<&str> {
         str::from_utf8(&self.inner).ok()
     }
 
-    pub fn to_string_lossy(&self) -> CowString {
+    pub fn to_string_lossy(&self) -> Cow<str> {
         String::from_utf8_lossy(&self.inner)
     }
 
index 68c5c65e7cdb11cfac9bf64ff25732d8efbba32b..62a1799de94c938fe0c3ef9f94ef6632323bff86 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![allow(deprecated)]
+
 use prelude::v1::*;
 use self::Req::*;
 
index b08f6ef9b9032ebe19b9af176d086164f0de2d7a..4fcaf504c3da5d7f447c1a933064ad5fe932c89a 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![allow(deprecated)]
+
 use prelude::v1::*;
 
 use old_io::net::ip;
index ac1006e653f09dc7c76c1e423e8c536f54d93a81..b30aec084392761fbf54326228a9e037efa7f285 100644 (file)
@@ -39,6 +39,7 @@ pub trait AsRawHandle {
     fn as_raw_handle(&self) -> Handle;
 }
 
+#[allow(deprecated)]
 impl AsRawHandle for old_io::fs::File {
     fn as_raw_handle(&self) -> Handle {
         self.as_inner().handle()
@@ -57,18 +58,21 @@ fn as_raw_handle(&self) -> Handle {
     }
 }
 
+#[allow(deprecated)]
 impl AsRawHandle for old_io::net::pipe::UnixStream {
     fn as_raw_handle(&self) -> Handle {
         self.as_inner().handle()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawHandle for old_io::net::pipe::UnixListener {
     fn as_raw_handle(&self) -> Handle {
         self.as_inner().handle()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawHandle for old_io::net::pipe::UnixAcceptor {
     fn as_raw_handle(&self) -> Handle {
         self.as_inner().handle()
@@ -80,24 +84,28 @@ pub trait AsRawSocket {
     fn as_raw_socket(&self) -> Socket;
 }
 
+#[allow(deprecated)]
 impl AsRawSocket for old_io::net::tcp::TcpStream {
     fn as_raw_socket(&self) -> Socket {
         self.as_inner().fd()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawSocket for old_io::net::tcp::TcpListener {
     fn as_raw_socket(&self) -> Socket {
         self.as_inner().socket()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawSocket for old_io::net::tcp::TcpAcceptor {
     fn as_raw_socket(&self) -> Socket {
         self.as_inner().socket()
     }
 }
 
+#[allow(deprecated)]
 impl AsRawSocket for old_io::net::udp::UdpSocket {
     fn as_raw_socket(&self) -> Socket {
         self.as_inner().fd()
index 587ab7924fd1dc541fd7751cb82a61ff077f3362..89cf8a08a68f9448dffb18582f02d8672a68bda8 100644 (file)
@@ -59,8 +59,8 @@ fn FormatMessageW(flags: DWORD,
                           -> DWORD;
     }
 
-    static FORMAT_MESSAGE_FROM_SYSTEM: DWORD = 0x00001000;
-    static FORMAT_MESSAGE_IGNORE_INSERTS: DWORD = 0x00000200;
+    const FORMAT_MESSAGE_FROM_SYSTEM: DWORD = 0x00001000;
+    const FORMAT_MESSAGE_IGNORE_INSERTS: DWORD = 0x00000200;
 
     // This value is calculated from the macro
     // MAKELANGID(LANG_SYSTEM_DEFAULT, SUBLANG_SYS_DEFAULT)
index af94b56bf1f71aaf39433a4072093ca4ee64475e..ad1e6c4b0e727eeb0f0776f3ae4bf8c6f2e802a4 100644 (file)
 /// The underlying OsString/OsStr implementation on Windows is a
 /// wrapper around the "WTF-8" encoding; see the `wtf8` module for more.
 
+use borrow::Cow;
 use fmt::{self, Debug};
 use sys_common::wtf8::{Wtf8, Wtf8Buf};
-use string::{String, CowString};
+use string::String;
 use result::Result;
 use option::Option;
 use mem;
@@ -70,7 +71,7 @@ pub fn to_str(&self) -> Option<&str> {
         self.inner.as_str()
     }
 
-    pub fn to_string_lossy(&self) -> CowString {
+    pub fn to_string_lossy(&self) -> Cow<str> {
         self.inner.to_string_lossy()
     }
 
index 334cafd3eb1136767fa4cc355360e44aafa50183..ca3ed54eb036a4b2e55e11235fe21d63086dfbfb 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![allow(deprecated)]
+
 use prelude::v1::*;
 
 use collections;
@@ -17,7 +19,7 @@
 use libc::{pid_t, c_void};
 use libc;
 use mem;
-use old_io::fs::PathExtensions;
+#[allow(deprecated)] use old_io::fs::PathExtensions;
 use old_io::process::{ProcessExit, ExitStatus};
 use old_io::{IoResult, IoError};
 use old_io;
index 25b70918591d0fc54c6ad488f36f8e42643013ac..8547de145f8c40cddbc83a7180562288affd924e 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![allow(deprecated)]
+
 use old_io::net::ip;
 use old_io::IoResult;
 use libc;
index 5dd4be336ec25b382f3729c73ddc5be12811a0b0..7d0df679591079e8fa6d149973c0a58de5e30eba 100644 (file)
 //! a thread will unwind the stack, running destructors and freeing
 //! owned resources. Thread panic is unrecoverable from within
 //! the panicking thread (i.e. there is no 'try/catch' in Rust), but
-//! panic may optionally be detected from a different thread. If
-//! the main thread panics the application will exit with a non-zero
+//! the panic may optionally be detected from a different thread. If
+//! the main thread panics, the application will exit with a non-zero
 //! exit code.
 //!
 //! When the main thread of a Rust program terminates, the entire program shuts
 //! down, even if other threads are still running. However, this module provides
 //! convenient facilities for automatically waiting for the termination of a
-//! child thread (i.e., join), described below.
+//! child thread (i.e., join).
 //!
 //! ## The `Thread` type
 //!
-//! Already-running threads are represented via the `Thread` type, which you can
+//! Threads are represented via the `Thread` type, which you can
 //! get in one of two ways:
 //!
-//! * By spawning a new thread, e.g. using the `thread::spawn` constructor;
+//! * By spawning a new thread, e.g. using the `thread::spawn` function.
 //! * By requesting the current thread, using the `thread::current` function.
 //!
 //! Threads can be named, and provide some built-in support for low-level
-//! synchronization described below.
+//! synchronization (described below).
 //!
 //! The `thread::current()` function is available even for threads not spawned
 //! by the APIs of this module.
 //! use std::thread;
 //!
 //! thread::spawn(move || {
-//!     println!("Hello, World!");
-//!     // some computation here
+//!     // some work here
 //! });
 //! ```
 //!
 //! In this example, the spawned thread is "detached" from the current
-//! thread, meaning that it can outlive the thread that spawned
-//! it. (Note, however, that when the main thread terminates all
-//! detached threads are terminated as well.)
+//! thread. This means that it can outlive its parent (the thread that spawned
+//! it), unless this parent is the main thread.
 //!
 //! ## Scoped threads
 //!
 //! Often a parent thread uses a child thread to perform some particular task,
 //! and at some point must wait for the child to complete before continuing.
-//! For this scenario, use the `scoped` constructor:
+//! For this scenario, use the `thread::scoped` function:
 //!
 //! ```rust
 //! use std::thread;
 //!
 //! let guard = thread::scoped(move || {
-//!     println!("Hello, World!");
-//!     // some computation here
+//!     // some work here
 //! });
+//!
 //! // do some other work in the meantime
 //! let output = guard.join();
 //! ```
 //! terminates) when it is dropped. You can join the child thread in
 //! advance by calling the `join` method on the guard, which will also
 //! return the result produced by the thread.  A handle to the thread
-//! itself is available via the `thread` method on the join guard.
-//!
-//! (Note: eventually, the `scoped` constructor will allow the parent and child
-//! threads to data that lives on the parent thread's stack, but some language
-//! changes are needed before this is possible.)
+//! itself is available via the `thread` method of the join guard.
 //!
 //! ## Configuring threads
 //!
 //! use std::thread;
 //!
 //! thread::Builder::new().name("child1".to_string()).spawn(move || {
-//!     println!("Hello, world!")
+//!     println!("Hello, world!");
 //! });
 //! ```
 //!
 //! initially not present:
 //!
 //! * The `thread::park()` function blocks the current thread unless or until
-//!   the token is available for its thread handle, at which point It atomically
+//!   the token is available for its thread handle, at which point it atomically
 //!   consumes the token. It may also return *spuriously*, without consuming the
 //!   token. `thread::park_timeout()` does the same, but allows specifying a
 //!   maximum time to block the thread for.
 //! * It avoids the need to allocate mutexes and condvars when building new
 //!   synchronization primitives; the threads already provide basic blocking/signaling.
 //!
-//! * It can be implemented highly efficiently on many platforms.
+//! * It can be implemented very efficiently on many platforms.
 
 #![stable(feature = "rust1", since = "1.0.0")]
 
@@ -283,14 +277,14 @@ fn spawn_inner<T: Send>(self, f: Thunk<(), T>) -> io::Result<JoinInner<T>> {
         // address at which our stack started).
         let main = move || {
             let something_around_the_top_of_the_stack = 1;
-            let addr = &something_around_the_top_of_the_stack as *const isize;
+            let addr = &something_around_the_top_of_the_stack as *const i32;
             let my_stack_top = addr as usize;
             let my_stack_bottom = my_stack_top - stack_size + 1024;
             unsafe {
                 stack::record_os_managed_stack_bounds(my_stack_bottom, my_stack_top);
             }
             match their_thread.name() {
-                Some(name) => unsafe { imp::set_name(name.as_slice()); },
+                Some(name) => unsafe { imp::set_name(name); },
                 None => {}
             }
             thread_info::set(
@@ -808,13 +802,13 @@ fn test_spawn_sched_childs_on_default_sched() {
     }
 
     fn avoid_copying_the_body<F>(spawnfn: F) where F: FnOnce(Thunk<'static>) {
-        let (tx, rx) = channel::<u32>();
+        let (tx, rx) = channel();
 
-        let x = box 1;
-        let x_in_parent = (&*x) as *const isize as u32;
+        let x: Box<_> = box 1;
+        let x_in_parent = (&*x) as *const i32 as usize;
 
         spawnfn(Thunk::new(move|| {
-            let x_in_child = (&*x) as *const isize as u32;
+            let x_in_child = (&*x) as *const i32 as usize;
             tx.send(x_in_child).unwrap();
         }));
 
@@ -853,8 +847,8 @@ fn test_child_doesnt_ref_parent() {
         // climbing the task tree to dereference each ancestor. (See #1789)
         // (well, it would if the constant were 8000+ - I lowered it to be more
         // valgrind-friendly. try this at home, instead..!)
-        static GENERATIONS: usize = 16;
-        fn child_no(x: usize) -> Thunk<'static> {
+        const GENERATIONS: u32 = 16;
+        fn child_no(x: u32) -> Thunk<'static> {
             return Thunk::new(move|| {
                 if x < GENERATIONS {
                     thread::spawn(move|| child_no(x+1).invoke(()));
@@ -907,7 +901,7 @@ fn test_try_panic_message_any() {
                 assert!(e.is::<T>());
                 let any = e.downcast::<T>().ok().unwrap();
                 assert!(any.is::<u16>());
-                assert_eq!(*any.downcast::<u16>().ok().unwrap(), 413u16);
+                assert_eq!(*any.downcast::<u16>().ok().unwrap(), 413);
             }
             Ok(()) => panic!()
         }
index 764c7d730cb0e448d4c20c390c08769e3624fa49..6bba73420d8512cd7b7c563230941ec171792d5b 100644 (file)
@@ -45,7 +45,7 @@
 
 // Sure wish we had macro hygiene, no?
 #[doc(hidden)]
-#[stable(feature = "rust1", since = "1.0.0")]
+#[unstable(feature = "thread_local_internals")]
 pub mod __impl {
     pub use super::imp::Key as KeyInner;
     pub use super::imp::destroy_value;
@@ -117,6 +117,7 @@ pub struct Key<T> {
 /// Declare a new thread local storage key of type `std::thread_local::Key`.
 #[macro_export]
 #[stable(feature = "rust1", since = "1.0.0")]
+#[allow_internal_unstable]
 macro_rules! thread_local {
     (static $name:ident: $t:ty = $init:expr) => (
         static $name: ::std::thread_local::Key<$t> = {
@@ -176,6 +177,7 @@ fn __getit() -> &'static __KeyInner<__UnsafeCell<__Option<$t>>> {
 
 #[macro_export]
 #[doc(hidden)]
+#[allow_internal_unstable]
 macro_rules! __thread_local_inner {
     (static $name:ident: $t:ty = $init:expr) => (
         #[cfg_attr(all(any(target_os = "macos", target_os = "linux"),
@@ -337,7 +339,7 @@ mod imp {
     use ptr;
 
     #[doc(hidden)]
-    #[stable(since = "1.0.0", feature = "rust1")]
+    #[unstable(feature = "thread_local_internals")]
     pub struct Key<T> {
         // Place the inner bits in an `UnsafeCell` to currently get around the
         // "only Sync statics" restriction. This allows any type to be placed in
@@ -345,14 +347,14 @@ pub struct Key<T> {
         //
         // Note that all access requires `T: 'static` so it can't be a type with
         // any borrowed pointers still.
-        #[stable(since = "1.0.0", feature = "rust1")]
+        #[unstable(feature = "thread_local_internals")]
         pub inner: UnsafeCell<T>,
 
         // Metadata to keep track of the state of the destructor. Remember that
         // these variables are thread-local, not global.
-        #[stable(since = "1.0.0", feature = "rust1")]
+        #[unstable(feature = "thread_local_internals")]
         pub dtor_registered: UnsafeCell<bool>, // should be Cell
-        #[stable(since = "1.0.0", feature = "rust1")]
+        #[unstable(feature = "thread_local_internals")]
         pub dtor_running: UnsafeCell<bool>, // should be Cell
     }
 
@@ -455,7 +457,7 @@ fn _tlv_atexit(dtor: unsafe extern fn(*mut u8),
     }
 
     #[doc(hidden)]
-    #[stable(feature = "rust1", since = "1.0.0")]
+    #[unstable(feature = "thread_local_internals")]
     pub unsafe extern fn destroy_value<T>(ptr: *mut u8) {
         let ptr = ptr as *mut Key<T>;
         // Right before we run the user destructor be sure to flag the
@@ -477,15 +479,15 @@ mod imp {
     use sys_common::thread_local::StaticKey as OsStaticKey;
 
     #[doc(hidden)]
-    #[stable(since = "1.0.0", feature = "rust1")]
+    #[unstable(feature = "thread_local_internals")]
     pub struct Key<T> {
         // Statically allocated initialization expression, using an `UnsafeCell`
         // for the same reasons as above.
-        #[stable(since = "1.0.0", feature = "rust1")]
+        #[unstable(feature = "thread_local_internals")]
         pub inner: UnsafeCell<T>,
 
         // OS-TLS key that we'll use to key off.
-        #[stable(since = "1.0.0", feature = "rust1")]
+        #[unstable(feature = "thread_local_internals")]
         pub os: OsStaticKey,
     }
 
@@ -528,7 +530,7 @@ unsafe fn ptr(&'static self) -> Option<*mut T> {
     }
 
     #[doc(hidden)]
-    #[stable(feature = "rust1", since = "1.0.0")]
+    #[unstable(feature = "thread_local_internals")]
     pub unsafe extern fn destroy_value<T: 'static>(ptr: *mut u8) {
         // The OS TLS ensures that this key contains a NULL value when this
         // destructor starts to run. We set it back to a sentinel value of 1 to
index a2a5d8b81f40458e43b018fe77bb9d5426ee294d..a5339568e9ef69088cce9f97f73686c4ad6a9a0e 100644 (file)
@@ -65,6 +65,7 @@ pub struct Key<T> { #[doc(hidden)] pub inner: __impl::KeyInner<T> }
 /// This macro declares a `static` item on which methods are used to get and
 /// set the value stored within.
 #[macro_export]
+#[allow_internal_unstable]
 macro_rules! scoped_thread_local {
     (static $name:ident: $t:ty) => (
         __scoped_thread_local_inner!(static $name: $t);
@@ -76,6 +77,7 @@ macro_rules! scoped_thread_local {
 
 #[macro_export]
 #[doc(hidden)]
+#[allow_internal_unstable]
 macro_rules! __scoped_thread_local_inner {
     (static $name:ident: $t:ty) => (
         #[cfg_attr(not(any(windows,
@@ -119,7 +121,7 @@ macro_rules! __scoped_thread_local_inner {
         const _INIT: __Key<$t> = __Key {
             inner: ::std::thread_local::scoped::__impl::KeyInner {
                 inner: ::std::thread_local::scoped::__impl::OS_INIT,
-                marker: ::std::marker::InvariantType,
+                marker: ::std::marker::PhantomData::<::std::cell::Cell<$t>>,
             }
         };
 
@@ -244,12 +246,13 @@ pub unsafe fn get(&self) -> *mut T { *self.inner.get() }
           target_arch = "aarch64"))]
 mod imp {
     use marker;
+    use std::cell::Cell;
     use sys_common::thread_local::StaticKey as OsStaticKey;
 
     #[doc(hidden)]
     pub struct KeyInner<T> {
         pub inner: OsStaticKey,
-        pub marker: marker::InvariantType<T>,
+        pub marker: marker::PhantomData<Cell<T>>,
     }
 
     unsafe impl<T> ::marker::Sync for KeyInner<T> { }
index 5bede984f13c7bc37bdb9bb00ccc443419664340..a9cb05b368f02a200acd64526b82dee685153639 100644 (file)
@@ -33,7 +33,7 @@ pub fn with_arg<F>(func: F) -> Thunk<'a,A,R>
         where F : FnOnce(A) -> R, F : Send + 'a
     {
         Thunk {
-            invoke: box func
+            invoke: Box::<F>::new(func)
         }
     }
 
index 42ef3459a0ed7cf931f191e300a7940ca87b21e9..958417d864c1fa7b477975d0f287d9ba2bb0b088 100644 (file)
@@ -68,7 +68,7 @@ pub struct Duration {
 
 impl Duration {
     /// Makes a new `Duration` with given number of weeks.
-    /// Equivalent to `Duration::seconds(weeks * 7 * 24 * 60 * 60), with overflow checks.
+    /// Equivalent to `Duration::seconds(weeks * 7 * 24 * 60 * 60)` with overflow checks.
     /// Panics when the duration is out of bounds.
     #[inline]
     #[unstable(feature = "std_misc")]
index 988b13cd160462b42fa62200dcc8fac8663d7005..41b70889c9f276f96735a7d473b56960bb8f64dd 100644 (file)
@@ -53,7 +53,7 @@
 //! assert!(b == c);
 //!
 //! let d : (u32, f32) = Default::default();
-//! assert_eq!(d, (0u32, 0.0f32));
+//! assert_eq!(d, (0, 0.0f32));
 //! ```
 
 #![doc(primitive = "tuple")]
index 2cf157bd245227f3710a0243b14c4b52919a0d4c..896e638deb46540ccb910309fd3f8d345aaf94a1 100644 (file)
@@ -77,11 +77,11 @@ pub enum AbiArchitecture {
 }
 
 #[allow(non_upper_case_globals)]
-static AbiDatas: &'static [AbiData] = &[
+const AbiDatas: &'static [AbiData] = &[
     // Platform-specific ABIs
     AbiData {abi: Cdecl, name: "cdecl" },
     AbiData {abi: Stdcall, name: "stdcall" },
-    AbiData {abi: Fastcall, name:"fastcall" },
+    AbiData {abi: Fastcall, name: "fastcall" },
     AbiData {abi: Aapcs, name: "aapcs" },
     AbiData {abi: Win64, name: "win64" },
 
index 6d6fdffa95095b25c6fd6b5684df59d12d8ae611..550ce3bb8c8734fe05a5cf27d0acfe5b1a7193dd 100644 (file)
 use codemap::{Span, Spanned, DUMMY_SP, ExpnId};
 use abi::Abi;
 use ast_util;
+use ext::base;
+use ext::tt::macro_parser;
 use owned_slice::OwnedSlice;
 use parse::token::{InternedString, str_to_ident};
 use parse::token;
+use parse::lexer;
 use ptr::P;
 
 use std::fmt;
@@ -960,6 +963,18 @@ pub fn get_span(&self) -> Span {
             TtSequence(span, _)  => span,
         }
     }
+
+    /// Use this token tree as a matcher to parse given tts.
+    pub fn parse(cx: &base::ExtCtxt, mtch: &[TokenTree], tts: &[TokenTree])
+                 -> macro_parser::NamedParseResult {
+        // `None` is because we're not interpolating
+        let arg_rdr = lexer::new_tt_reader_with_doc_flag(&cx.parse_sess().span_diagnostic,
+                                                         None,
+                                                         None,
+                                                         tts.iter().cloned().collect(),
+                                                         true);
+        macro_parser::parse(cx.parse_sess(), cx.cfg(), arg_rdr, mtch)
+    }
 }
 
 pub type Mac = Spanned<Mac_>;
@@ -1249,7 +1264,7 @@ pub struct BareFnTy {
 /// The different kinds of types recognized by the compiler
 pub enum Ty_ {
     TyVec(P<Ty>),
-    /// A fixed length array (`[T, ..n]`)
+    /// A fixed length array (`[Tn]`)
     TyFixedLengthVec(P<Ty>, P<Expr>),
     /// A raw pointer (`*const T` or `*mut T`)
     TyPtr(MutTy),
@@ -1728,6 +1743,7 @@ pub struct MacroDef {
     pub imported_from: Option<Ident>,
     pub export: bool,
     pub use_locally: bool,
+    pub allow_internal_unstable: bool,
     pub body: Vec<TokenTree>,
 }
 
index c33158193ce215a6c835df3798bed0694c5ce294..b96d735d92dbdd1e6ed59d3681f92bb6ecae9bcd 100644 (file)
@@ -25,7 +25,7 @@
 use arena::TypedArena;
 use std::cell::RefCell;
 use std::fmt;
-use std::old_io::IoResult;
+use std::io;
 use std::iter::{self, repeat};
 use std::mem;
 use std::slice;
@@ -457,35 +457,32 @@ fn with_path_next<T, F>(&self, id: NodeId, next: LinkedPath, f: F) -> T where
         }
     }
 
-    /// Given a node ID and a closure, apply the closure to the array
-    /// of attributes associated with the AST corresponding to the Node ID
-    pub fn with_attrs<T, F>(&self, id: NodeId, f: F) -> T where
-        F: FnOnce(Option<&[Attribute]>) -> T,
-    {
-        let attrs = match self.get(id) {
-            NodeItem(i) => Some(&i.attrs[..]),
-            NodeForeignItem(fi) => Some(&fi.attrs[..]),
-            NodeTraitItem(ref tm) => match **tm {
+    /// Given a node ID, get a list of of attributes associated with the AST
+    /// corresponding to the Node ID
+    pub fn attrs(&self, id: NodeId) -> &[Attribute] {
+        let attrs = match self.find(id) {
+            Some(NodeItem(i)) => Some(&i.attrs[..]),
+            Some(NodeForeignItem(fi)) => Some(&fi.attrs[..]),
+            Some(NodeTraitItem(ref tm)) => match **tm {
                 RequiredMethod(ref type_m) => Some(&type_m.attrs[..]),
                 ProvidedMethod(ref m) => Some(&m.attrs[..]),
                 TypeTraitItem(ref typ) => Some(&typ.attrs[..]),
             },
-            NodeImplItem(ref ii) => {
+            Some(NodeImplItem(ref ii)) => {
                 match **ii {
                     MethodImplItem(ref m) => Some(&m.attrs[..]),
                     TypeImplItem(ref t) => Some(&t.attrs[..]),
                 }
             }
-            NodeVariant(ref v) => Some(&v.node.attrs[..]),
+            Some(NodeVariant(ref v)) => Some(&v.node.attrs[..]),
             // unit/tuple structs take the attributes straight from
             // the struct definition.
-            // FIXME(eddyb) make this work again (requires access to the map).
-            NodeStructCtor(_) => {
-                return self.with_attrs(self.get_parent(id), f);
+            Some(NodeStructCtor(_)) => {
+                return self.attrs(self.get_parent(id));
             }
             _ => None
         };
-        f(attrs)
+        attrs.unwrap_or(&[])
     }
 
     /// Returns an iterator that yields the node id's with paths that
@@ -997,11 +994,11 @@ pub fn map_decoded_item<'ast, F: FoldOps>(map: &Map<'ast>,
 }
 
 pub trait NodePrinter {
-    fn print_node(&mut self, node: &Node) -> IoResult<()>;
+    fn print_node(&mut self, node: &Node) -> io::Result<()>;
 }
 
 impl<'a> NodePrinter for pprust::State<'a> {
-    fn print_node(&mut self, node: &Node) -> IoResult<()> {
+    fn print_node(&mut self, node: &Node) -> io::Result<()> {
         match *node {
             NodeItem(a)        => self.print_item(&*a),
             NodeForeignItem(a) => self.print_foreign_item(&*a),
index 264e05f5c8d31ec1229b01ff6f6c39c0316b97ab..26d7562cdb2d4c4c408fc71d12ee5021a8c38a7a 100644 (file)
@@ -159,10 +159,10 @@ pub fn int_ty_to_string(t: IntTy, val: Option<i64>) -> String {
 
 pub fn int_ty_max(t: IntTy) -> u64 {
     match t {
-        TyI8 => 0x80u64,
-        TyI16 => 0x8000u64,
-        TyIs(_) | TyI32 => 0x80000000u64, // actually ni about TyIs
-        TyI64 => 0x8000000000000000u64
+        TyI8 => 0x80,
+        TyI16 => 0x8000,
+        TyIs(_) | TyI32 => 0x80000000, // actually ni about TyIs
+        TyI64 => 0x8000000000000000
     }
 }
 
@@ -185,10 +185,10 @@ pub fn uint_ty_to_string(t: UintTy, val: Option<u64>) -> String {
 
 pub fn uint_ty_max(t: UintTy) -> u64 {
     match t {
-        TyU8 => 0xffu64,
-        TyU16 => 0xffffu64,
-        TyUs(_) | TyU32 => 0xffffffffu64, // actually ni about TyUs
-        TyU64 => 0xffffffffffffffffu64
+        TyU8 => 0xff,
+        TyU16 => 0xffff,
+        TyUs(_) | TyU32 => 0xffffffff, // actually ni about TyUs
+        TyU64 => 0xffffffffffffffff
     }
 }
 
index 099f646294235d175dcdf47b59ac0daa419f7024..7d2d4e53fe9fd43002db11920e775e60bfa7b06a 100644 (file)
 use libc::c_uint;
 use serialize::{Encodable, Decodable, Encoder, Decoder};
 
+
+// _____________________________________________________________________________
+// Pos, BytePos, CharPos
+//
+
 pub trait Pos {
     fn from_usize(n: usize) -> Self;
     fn to_usize(&self) -> usize;
@@ -69,6 +74,18 @@ fn sub(self, rhs: BytePos) -> BytePos {
     }
 }
 
+impl Encodable for BytePos {
+    fn encode<S: Encoder>(&self, s: &mut S) -> Result<(), S::Error> {
+        s.emit_u32(self.0)
+    }
+}
+
+impl Decodable for BytePos {
+    fn decode<D: Decoder>(d: &mut D) -> Result<BytePos, D::Error> {
+        Ok(BytePos(try!{ d.read_u32() }))
+    }
+}
+
 impl Pos for CharPos {
     fn from_usize(n: usize) -> CharPos { CharPos(n) }
     fn to_usize(&self) -> usize { let CharPos(n) = *self; n }
@@ -90,6 +107,10 @@ fn sub(self, rhs: CharPos) -> CharPos {
     }
 }
 
+// _____________________________________________________________________________
+// Span, Spanned
+//
+
 /// Spans represent a region of code, used for error reporting. Positions in spans
 /// are *absolute* positions from the beginning of the codemap, not positions
 /// relative to FileMaps. Methods on the CodeMap can be used to relate spans back
@@ -126,15 +147,20 @@ fn ne(&self, other: &Span) -> bool { !(*self).eq(other) }
 impl Eq for Span {}
 
 impl Encodable for Span {
-    /* Note #1972 -- spans are encoded but not decoded */
     fn encode<S: Encoder>(&self, s: &mut S) -> Result<(), S::Error> {
-        s.emit_nil()
+        // Encode spans as a single u64 in order to cut down on tagging overhead
+        // added by the RBML metadata encoding. The should be solved differently
+        // altogether some time (FIXME #21482)
+        s.emit_u64( (self.lo.0 as u64) | ((self.hi.0 as u64) << 32) )
     }
 }
 
 impl Decodable for Span {
-    fn decode<D: Decoder>(_d: &mut D) -> Result<Span, D::Error> {
-        Ok(DUMMY_SP)
+    fn decode<D: Decoder>(d: &mut D) -> Result<Span, D::Error> {
+        let lo_hi: u64 = try! { d.read_u64() };
+        let lo = BytePos(lo_hi as u32);
+        let hi = BytePos((lo_hi >> 32) as u32);
+        Ok(mk_sp(lo, hi))
     }
 }
 
@@ -168,6 +194,10 @@ pub fn original_sp(cm: &CodeMap, sp: Span, enclosing_sp: Span) -> Span {
     }
 }
 
+// _____________________________________________________________________________
+// Loc, LocWithOpt, FileMapAndLine, FileMapAndBytePos
+//
+
 /// A source code location used for error reporting
 pub struct Loc {
     /// Information about the original source
@@ -192,6 +222,11 @@ pub struct LocWithOpt {
 pub struct FileMapAndLine { pub fm: Rc<FileMap>, pub line: usize }
 pub struct FileMapAndBytePos { pub fm: Rc<FileMap>, pub pos: BytePos }
 
+
+// _____________________________________________________________________________
+// MacroFormat, NameAndSpan, ExpnInfo, ExpnId
+//
+
 /// The syntax with which a macro was invoked.
 #[derive(Clone, Copy, Hash, Debug)]
 pub enum MacroFormat {
@@ -208,6 +243,10 @@ pub struct NameAndSpan {
     pub name: String,
     /// The format with which the macro was invoked.
     pub format: MacroFormat,
+    /// Whether the macro is allowed to use #[unstable]/feature-gated
+    /// features internally without forcing the whole crate to opt-in
+    /// to them.
+    pub allow_internal_unstable: bool,
     /// The span of the macro definition itself. The macro may not
     /// have a sensible definition span (e.g. something defined
     /// completely inside libsyntax) in which case this is None.
@@ -254,6 +293,10 @@ pub fn to_llvm_cookie(self) -> i32 {
     }
 }
 
+// _____________________________________________________________________________
+// FileMap, MultiByteChar, FileName, FileLines
+//
+
 pub type FileName = String;
 
 pub struct FileLines {
@@ -262,7 +305,7 @@ pub struct FileLines {
 }
 
 /// Identifies an offset of a multi-byte character in a FileMap
-#[derive(Copy)]
+#[derive(Copy, RustcEncodable, RustcDecodable, Eq, PartialEq)]
 pub struct MultiByteChar {
     /// The absolute offset of the character in the CodeMap
     pub pos: BytePos,
@@ -277,13 +320,134 @@ pub struct FileMap {
     /// e.g. `<anon>`
     pub name: FileName,
     /// The complete source code
-    pub src: String,
+    pub src: Option<Rc<String>>,
     /// The start position of this source in the CodeMap
     pub start_pos: BytePos,
+    /// The end position of this source in the CodeMap
+    pub end_pos: BytePos,
     /// Locations of lines beginnings in the source code
-    pub lines: RefCell<Vec<BytePos> >,
+    pub lines: RefCell<Vec<BytePos>>,
     /// Locations of multi-byte characters in the source code
-    pub multibyte_chars: RefCell<Vec<MultiByteChar> >,
+    pub multibyte_chars: RefCell<Vec<MultiByteChar>>,
+}
+
+impl Encodable for FileMap {
+    fn encode<S: Encoder>(&self, s: &mut S) -> Result<(), S::Error> {
+        s.emit_struct("FileMap", 5, |s| {
+            try! { s.emit_struct_field("name", 0, |s| self.name.encode(s)) };
+            try! { s.emit_struct_field("start_pos", 1, |s| self.start_pos.encode(s)) };
+            try! { s.emit_struct_field("end_pos", 2, |s| self.end_pos.encode(s)) };
+            try! { s.emit_struct_field("lines", 3, |s| {
+                    let lines = self.lines.borrow();
+                    // store the length
+                    try! { s.emit_u32(lines.len() as u32) };
+
+                    if lines.len() > 0 {
+                        // In order to preserve some space, we exploit the fact that
+                        // the lines list is sorted and individual lines are
+                        // probably not that long. Because of that we can store lines
+                        // as a difference list, using as little space as possible
+                        // for the differences.
+                        let max_line_length = if lines.len() == 1 {
+                            0
+                        } else {
+                            lines.as_slice()
+                                 .windows(2)
+                                 .map(|w| w[1] - w[0])
+                                 .map(|bp| bp.to_usize())
+                                 .max()
+                                 .unwrap()
+                        };
+
+                        let bytes_per_diff: u8 = match max_line_length {
+                            0 ... 0xFF => 1,
+                            0x100 ... 0xFFFF => 2,
+                            _ => 4
+                        };
+
+                        // Encode the number of bytes used per diff.
+                        try! { bytes_per_diff.encode(s) };
+
+                        // Encode the first element.
+                        try! { lines[0].encode(s) };
+
+                        let diff_iter = (&lines[..]).windows(2)
+                                                    .map(|w| (w[1] - w[0]));
+
+                        match bytes_per_diff {
+                            1 => for diff in diff_iter { try! { (diff.0 as u8).encode(s) } },
+                            2 => for diff in diff_iter { try! { (diff.0 as u16).encode(s) } },
+                            4 => for diff in diff_iter { try! { (diff.0 as u32).encode(s) } },
+                            _ => unreachable!()
+                        }
+                    }
+
+                    Ok(())
+                })
+            };
+            s.emit_struct_field("multibyte_chars", 4, |s| {
+                (*self.multibyte_chars.borrow()).encode(s)
+            })
+        })
+    }
+}
+
+impl Decodable for FileMap {
+    fn decode<D: Decoder>(d: &mut D) -> Result<FileMap, D::Error> {
+
+        d.read_struct("FileMap", 5, |d| {
+            let name: String = try! {
+                d.read_struct_field("name", 0, |d| Decodable::decode(d))
+            };
+            let start_pos: BytePos = try! {
+                d.read_struct_field("start_pos", 1, |d| Decodable::decode(d))
+            };
+            let end_pos: BytePos = try! {
+                d.read_struct_field("end_pos", 2, |d| Decodable::decode(d))
+            };
+            let lines: Vec<BytePos> = try! {
+                d.read_struct_field("lines", 3, |d| {
+                    let num_lines: u32 = try! { Decodable::decode(d) };
+                    let mut lines = Vec::with_capacity(num_lines as usize);
+
+                    if num_lines > 0 {
+                        // Read the number of bytes used per diff.
+                        let bytes_per_diff: u8 = try! { Decodable::decode(d) };
+
+                        // Read the first element.
+                        let mut line_start: BytePos = try! { Decodable::decode(d) };
+                        lines.push(line_start);
+
+                        for _ in 1..num_lines {
+                            let diff = match bytes_per_diff {
+                                1 => try! { d.read_u8() } as u32,
+                                2 => try! { d.read_u16() } as u32,
+                                4 => try! { d.read_u32() },
+                                _ => unreachable!()
+                            };
+
+                            line_start = line_start + BytePos(diff);
+
+                            lines.push(line_start);
+                        }
+                    }
+
+                    Ok(lines)
+                })
+            };
+            let multibyte_chars: Vec<MultiByteChar> = try! {
+                d.read_struct_field("multibyte_chars", 4, |d| Decodable::decode(d))
+            };
+            Ok(FileMap {
+                name: name,
+                start_pos: start_pos,
+                end_pos: end_pos,
+                src: None,
+                lines: RefCell::new(lines),
+                multibyte_chars: RefCell::new(multibyte_chars)
+            })
+        })
+    }
 }
 
 impl FileMap {
@@ -307,16 +471,21 @@ pub fn next_line(&self, pos: BytePos) {
     /// get a line from the list of pre-computed line-beginnings
     ///
     pub fn get_line(&self, line_number: usize) -> Option<String> {
-        let lines = self.lines.borrow();
-        lines.get(line_number).map(|&line| {
-            let begin: BytePos = line - self.start_pos;
-            let begin = begin.to_usize();
-            let slice = &self.src[begin..];
-            match slice.find('\n') {
-                Some(e) => &slice[..e],
-                None => slice
-            }.to_string()
-        })
+        match self.src {
+            Some(ref src) => {
+                let lines = self.lines.borrow();
+                lines.get(line_number).map(|&line| {
+                    let begin: BytePos = line - self.start_pos;
+                    let begin = begin.to_usize();
+                    let slice = &src[begin..];
+                    match slice.find('\n') {
+                        Some(e) => &slice[..e],
+                        None => slice
+                    }.to_string()
+                })
+            }
+            None => None
+        }
     }
 
     pub fn record_multibyte_char(&self, pos: BytePos, bytes: usize) {
@@ -332,8 +501,17 @@ pub fn is_real_file(&self) -> bool {
         !(self.name.starts_with("<") &&
           self.name.ends_with(">"))
     }
+
+    pub fn is_imported(&self) -> bool {
+        self.src.is_none()
+    }
 }
 
+
+// _____________________________________________________________________________
+// CodeMap
+//
+
 pub struct CodeMap {
     pub files: RefCell<Vec<Rc<FileMap>>>,
     expansions: RefCell<Vec<ExpnInfo>>
@@ -351,7 +529,7 @@ pub fn new_filemap(&self, filename: FileName, src: String) -> Rc<FileMap> {
         let mut files = self.files.borrow_mut();
         let start_pos = match files.last() {
             None => 0,
-            Some(last) => last.start_pos.to_usize() + last.src.len(),
+            Some(last) => last.end_pos.to_usize(),
         };
 
         // Remove utf-8 BOM if any.
@@ -372,10 +550,13 @@ pub fn new_filemap(&self, filename: FileName, src: String) -> Rc<FileMap> {
             src.push('\n');
         }
 
+        let end_pos = start_pos + src.len();
+
         let filemap = Rc::new(FileMap {
             name: filename,
-            src: src.to_string(),
+            src: Some(Rc::new(src)),
             start_pos: Pos::from_usize(start_pos),
+            end_pos: Pos::from_usize(end_pos),
             lines: RefCell::new(Vec::new()),
             multibyte_chars: RefCell::new(Vec::new()),
         });
@@ -385,6 +566,45 @@ pub fn new_filemap(&self, filename: FileName, src: String) -> Rc<FileMap> {
         filemap
     }
 
+    /// Allocates a new FileMap representing a source file from an external
+    /// crate. The source code of such an "imported filemap" is not available,
+    /// but we still know enough to generate accurate debuginfo location
+    /// information for things inlined from other crates.
+    pub fn new_imported_filemap(&self,
+                                filename: FileName,
+                                source_len: usize,
+                                file_local_lines: Vec<BytePos>,
+                                file_local_multibyte_chars: Vec<MultiByteChar>)
+                                -> Rc<FileMap> {
+        let mut files = self.files.borrow_mut();
+        let start_pos = match files.last() {
+            None => 0,
+            Some(last) => last.end_pos.to_usize(),
+        };
+
+        let end_pos = Pos::from_usize(start_pos + source_len);
+        let start_pos = Pos::from_usize(start_pos);
+
+        let lines = file_local_lines.map_in_place(|pos| pos + start_pos);
+        let multibyte_chars = file_local_multibyte_chars.map_in_place(|mbc| MultiByteChar {
+            pos: mbc.pos + start_pos,
+            bytes: mbc.bytes
+        });
+
+        let filemap = Rc::new(FileMap {
+            name: filename,
+            src: None,
+            start_pos: start_pos,
+            end_pos: end_pos,
+            lines: RefCell::new(lines),
+            multibyte_chars: RefCell::new(multibyte_chars),
+        });
+
+        files.push(filemap.clone());
+
+        filemap
+    }
+
     pub fn mk_substr_filename(&self, sp: Span) -> String {
         let pos = self.lookup_char_pos(sp.lo);
         (format!("<{}:{}:{}>",
@@ -442,30 +662,42 @@ pub fn span_to_snippet(&self, sp: Span) -> Result<String, SpanSnippetError> {
             return Err(SpanSnippetError::IllFormedSpan(sp));
         }
 
-        let begin = self.lookup_byte_offset(sp.lo);
-        let end = self.lookup_byte_offset(sp.hi);
+        let local_begin = self.lookup_byte_offset(sp.lo);
+        let local_end = self.lookup_byte_offset(sp.hi);
 
-        if begin.fm.start_pos != end.fm.start_pos {
+        if local_begin.fm.start_pos != local_end.fm.start_pos {
             return Err(SpanSnippetError::DistinctSources(DistinctSources {
-                begin: (begin.fm.name.clone(),
-                        begin.fm.start_pos),
-                end: (end.fm.name.clone(),
-                      end.fm.start_pos)
+                begin: (local_begin.fm.name.clone(),
+                        local_begin.fm.start_pos),
+                end: (local_end.fm.name.clone(),
+                      local_end.fm.start_pos)
             }));
         } else {
-            let start = begin.pos.to_usize();
-            let limit = end.pos.to_usize();
-            if start > limit || limit > begin.fm.src.len() {
-                return Err(SpanSnippetError::MalformedForCodemap(
-                    MalformedCodemapPositions {
-                        name: begin.fm.name.clone(),
-                        source_len: begin.fm.src.len(),
-                        begin_pos: begin.pos,
-                        end_pos: end.pos,
-                    }));
-            }
+            match local_begin.fm.src {
+                Some(ref src) => {
+                    let start_index = local_begin.pos.to_usize();
+                    let end_index = local_end.pos.to_usize();
+                    let source_len = (local_begin.fm.end_pos -
+                                      local_begin.fm.start_pos).to_usize();
+
+                    if start_index > end_index || end_index > source_len {
+                        return Err(SpanSnippetError::MalformedForCodemap(
+                            MalformedCodemapPositions {
+                                name: local_begin.fm.name.clone(),
+                                source_len: source_len,
+                                begin_pos: local_begin.pos,
+                                end_pos: local_end.pos,
+                            }));
+                    }
 
-            return Ok((&begin.fm.src[start..limit]).to_string())
+                    return Ok((&src[start_index..end_index]).to_string())
+                }
+                None => {
+                    return Err(SpanSnippetError::SourceNotAvailable {
+                        filename: local_begin.fm.name.clone()
+                    });
+                }
+            }
         }
     }
 
@@ -478,6 +710,7 @@ pub fn get_filemap(&self, filename: &str) -> Rc<FileMap> {
         panic!("asking for {} which we don't know about", filename);
     }
 
+    /// For a global BytePos compute the local offset within the containing FileMap
     pub fn lookup_byte_offset(&self, bpos: BytePos) -> FileMapAndBytePos {
         let idx = self.lookup_filemap_idx(bpos);
         let fm = (*self.files.borrow())[idx].clone();
@@ -601,49 +834,56 @@ pub fn with_expn_info<T, F>(&self, id: ExpnId, f: F) -> T where
         }
     }
 
-    /// Check if a span is "internal" to a macro. This means that it is entirely generated by a
-    /// macro expansion and contains no code that was passed in as an argument.
-    pub fn span_is_internal(&self, span: Span) -> bool {
-        // first, check if the given expression was generated by a macro or not
-        // we need to go back the expn_info tree to check only the arguments
-        // of the initial macro call, not the nested ones.
-        let mut is_internal = false;
-        let mut expnid = span.expn_id;
-        while self.with_expn_info(expnid, |expninfo| {
-            match expninfo {
-                Some(ref info) => {
-                    // save the parent expn_id for next loop iteration
-                    expnid = info.call_site.expn_id;
-                    if info.callee.name == "format_args" {
-                        // This is a hack because the format_args builtin calls unstable APIs.
-                        // I spent like 6 hours trying to solve this more generally but am stupid.
-                        is_internal = true;
-                        false
-                    } else if info.callee.span.is_none() {
-                        // it's a compiler built-in, we *really* don't want to mess with it
-                        // so we skip it, unless it was called by a regular macro, in which case
-                        // we will handle the caller macro next turn
-                        is_internal = true;
-                        true // continue looping
+    /// Check if a span is "internal" to a macro in which #[unstable]
+    /// items can be used (that is, a macro marked with
+    /// `#[allow_internal_unstable]`).
+    pub fn span_allows_unstable(&self, span: Span) -> bool {
+        debug!("span_allows_unstable(span = {:?})", span);
+        let mut allows_unstable = false;
+        let mut expn_id = span.expn_id;
+        loop {
+            let quit = self.with_expn_info(expn_id, |expninfo| {
+                debug!("span_allows_unstable: expninfo = {:?}", expninfo);
+                expninfo.map_or(/* hit the top level */ true, |info| {
+
+                    let span_comes_from_this_expansion =
+                        info.callee.span.map_or(span == info.call_site, |mac_span| {
+                            mac_span.lo <= span.lo && span.hi < mac_span.hi
+                        });
+
+                    debug!("span_allows_unstable: from this expansion? {}, allows unstable? {}",
+                           span_comes_from_this_expansion,
+                           info.callee.allow_internal_unstable);
+                    if span_comes_from_this_expansion {
+                        allows_unstable = info.callee.allow_internal_unstable;
+                        // we've found the right place, stop looking
+                        true
                     } else {
-                        // was this expression from the current macro arguments ?
-                        is_internal = !( span.lo > info.call_site.lo &&
-                                         span.hi < info.call_site.hi );
-                        true // continue looping
+                        // not the right place, keep looking
+                        expn_id = info.call_site.expn_id;
+                        false
                     }
-                },
-                _ => false // stop looping
+                })
+            });
+            if quit {
+                break
             }
-        }) { /* empty while loop body */ }
-        return is_internal;
+        }
+        debug!("span_allows_unstable? {}", allows_unstable);
+        allows_unstable
     }
 }
 
+// _____________________________________________________________________________
+// SpanSnippetError, DistinctSources, MalformedCodemapPositions
+//
+
 #[derive(Clone, PartialEq, Eq, Debug)]
 pub enum SpanSnippetError {
     IllFormedSpan(Span),
     DistinctSources(DistinctSources),
     MalformedForCodemap(MalformedCodemapPositions),
+    SourceNotAvailable { filename: String }
 }
 
 #[derive(Clone, PartialEq, Eq, Debug)]
@@ -660,6 +900,11 @@ pub struct MalformedCodemapPositions {
     end_pos: BytePos
 }
 
+
+// _____________________________________________________________________________
+// Tests
+//
+
 #[cfg(test)]
 mod test {
     use super::*;
@@ -677,7 +922,7 @@ fn t1 () {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn t2 () {
         let cm = CodeMap::new();
         let fm = cm.new_filemap("blork.rs".to_string(),
index 27219774cf148c52f68f8e009fc8d7130691fdd8..e094cbcac5378a8b3aa59ab8332e13057c12d596 100644 (file)
@@ -25,7 +25,7 @@
 use term;
 
 /// maximum number of lines we will print for each error; arbitrary.
-static MAX_LINES: usize = 6;
+const MAX_LINES: usize = 6;
 
 #[derive(Clone, Copy)]
 pub enum RenderSpan {
@@ -223,7 +223,7 @@ pub fn mk_span_handler(handler: Handler, cm: codemap::CodeMap) -> SpanHandler {
 pub fn default_handler(color_config: ColorConfig,
                        registry: Option<diagnostics::registry::Registry>,
                        can_emit_warnings: bool) -> Handler {
-    mk_handler(can_emit_warnings, box EmitterWriter::stderr(color_config, registry))
+    mk_handler(can_emit_warnings, Box::new(EmitterWriter::stderr(color_config, registry)))
 }
 
 pub fn mk_handler(can_emit_warnings: bool, e: Box<Emitter + Send>) -> Handler {
@@ -352,11 +352,11 @@ pub fn stderr(color_config: ColorConfig,
         if use_color {
             let dst = match term::stderr() {
                 Some(t) => Terminal(t),
-                None    => Raw(box stderr),
+                None    => Raw(Box::new(stderr)),
             };
             EmitterWriter { dst: dst, registry: registry }
         } else {
-            EmitterWriter { dst: Raw(box stderr), registry: registry }
+            EmitterWriter { dst: Raw(Box::new(stderr)), registry: registry }
         }
     }
 
index 54689a1f77ad2dddcb9e6fa96bdff67b0de08e53..055ade46a3f01ab482ce08674ca5cb0eb9462f1b 100644 (file)
@@ -52,6 +52,13 @@ macro_rules! span_help {
     })
 }
 
+#[macro_export]
+macro_rules! fileline_help {
+    ($session:expr, $span:expr, $($message:tt)*) => ({
+        ($session).fileline_help($span, &format!($($message)*))
+    })
+}
+
 #[macro_export]
 macro_rules! register_diagnostics {
     ($($code:tt),*) => (
index ae48084947e4393b5531c9dc3c6de0a6c9e206af..d256698b88598cd5cd764379514d23aaf3056785 100644 (file)
@@ -45,7 +45,7 @@ fn next(&self) -> State {
     }
 }
 
-static OPTIONS: &'static [&'static str] = &["volatile", "alignstack", "intel"];
+const OPTIONS: &'static [&'static str] = &["volatile", "alignstack", "intel"];
 
 pub fn expand_asm<'cx>(cx: &'cx mut ExtCtxt, sp: Span, tts: &[ast::TokenTree])
                        -> Box<base::MacResult+'cx> {
@@ -214,6 +214,7 @@ pub fn expand_asm<'cx>(cx: &'cx mut ExtCtxt, sp: Span, tts: &[ast::TokenTree])
             name: "asm".to_string(),
             format: codemap::MacroBang,
             span: None,
+            allow_internal_unstable: false,
         },
     });
 
index e5d1fe2388c50ee2f01937dfd09f8aa9d194097b..8aeafe419daa925cd759c922ea417e1e9859f9cd 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
@@ -430,12 +430,15 @@ pub enum SyntaxExtension {
     /// A normal, function-like syntax extension.
     ///
     /// `bytes!` is a `NormalTT`.
-    NormalTT(Box<TTMacroExpander + 'static>, Option<Span>),
+    ///
+    /// The `bool` dictates whether the contents of the macro can
+    /// directly use `#[unstable]` things (true == yes).
+    NormalTT(Box<TTMacroExpander + 'static>, Option<Span>, bool),
 
     /// A function-like syntax extension that has an extra ident before
     /// the block.
     ///
-    IdentTT(Box<IdentMacroExpander + 'static>, Option<Span>),
+    IdentTT(Box<IdentMacroExpander + 'static>, Option<Span>, bool),
 
     /// Represents `macro_rules!` itself.
     MacroRulesTT,
@@ -465,14 +468,14 @@ fn initial_syntax_expander_table<'feat>(ecfg: &expand::ExpansionConfig<'feat>)
                                         -> SyntaxEnv {
     // utility function to simplify creating NormalTT syntax extensions
     fn builtin_normal_expander(f: MacroExpanderFn) -> SyntaxExtension {
-        NormalTT(box f, None)
+        NormalTT(Box::new(f), None, false)
     }
 
     let mut syntax_expanders = SyntaxEnv::new();
     syntax_expanders.insert(intern("macro_rules"), MacroRulesTT);
     syntax_expanders.insert(intern("format_args"),
-                            builtin_normal_expander(
-                                ext::format::expand_format_args));
+                            // format_args uses `unstable` things internally.
+                            NormalTT(Box::new(ext::format::expand_format_args), None, true));
     syntax_expanders.insert(intern("env"),
                             builtin_normal_expander(
                                     ext::env::expand_env));
@@ -488,10 +491,8 @@ fn builtin_normal_expander(f: MacroExpanderFn) -> SyntaxExtension {
     syntax_expanders.insert(intern("log_syntax"),
                             builtin_normal_expander(
                                     ext::log_syntax::expand_syntax_ext));
-    syntax_expanders.insert(intern("derive"),
-                            Decorator(box ext::deriving::expand_meta_derive));
-    syntax_expanders.insert(intern("deriving"),
-                            Decorator(box ext::deriving::expand_deprecated_deriving));
+
+    ext::deriving::register_all(&mut syntax_expanders);
 
     if ecfg.enable_quotes() {
         // Quasi-quoting expanders
@@ -519,6 +520,12 @@ fn builtin_normal_expander(f: MacroExpanderFn) -> SyntaxExtension {
         syntax_expanders.insert(intern("quote_stmt"),
                            builtin_normal_expander(
                                 ext::quote::expand_quote_stmt));
+        syntax_expanders.insert(intern("quote_matcher"),
+                           builtin_normal_expander(
+                                ext::quote::expand_quote_matcher));
+        syntax_expanders.insert(intern("quote_attr"),
+                           builtin_normal_expander(
+                                ext::quote::expand_quote_attr));
     }
 
     syntax_expanders.insert(intern("line"),
@@ -747,6 +754,10 @@ pub fn span_help(&self, sp: Span, msg: &str) {
         self.print_backtrace();
         self.parse_sess.span_diagnostic.span_help(sp, msg);
     }
+    pub fn fileline_help(&self, sp: Span, msg: &str) {
+        self.print_backtrace();
+        self.parse_sess.span_diagnostic.fileline_help(sp, msg);
+    }
     pub fn bug(&self, msg: &str) -> ! {
         self.print_backtrace();
         self.parse_sess.span_diagnostic.handler().bug(msg);
index 93098484ae01343de6df460a61db1d43048e0916..e408c99935d1cdada38d0ddd43c07bef07061daa 100644 (file)
@@ -8,47 +8,34 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-use ast::{MetaItem, MetaWord, Item};
+use ast::{MetaItem, Item};
 use codemap::Span;
 use ext::base::ExtCtxt;
 use ext::deriving::generic::*;
 use ext::deriving::generic::ty::*;
 use ptr::P;
 
-pub fn expand_deriving_bound<F>(cx: &mut ExtCtxt,
-                                span: Span,
-                                mitem: &MetaItem,
-                                item: &Item,
-                                push: F) where
+pub fn expand_deriving_unsafe_bound<F>(cx: &mut ExtCtxt,
+                                       span: Span,
+                                       _: &MetaItem,
+                                       _: &Item,
+                                       _: F) where
     F: FnOnce(P<Item>),
 {
-    let name = match mitem.node {
-        MetaWord(ref tname) => {
-            match &tname[..] {
-                "Copy" => "Copy",
-                "Send" | "Sync" => {
-                    return cx.span_err(span,
-                                       &format!("{} is an unsafe trait and it \
-                                                 should be implemented explicitly",
-                                                *tname))
-                }
-                ref tname => {
-                    cx.span_bug(span,
-                                &format!("expected built-in trait name but \
-                                          found {}", *tname))
-                }
-            }
-        },
-        _ => {
-            return cx.span_err(span, "unexpected value in deriving, expected \
-                                      a trait")
-        }
-    };
+    cx.span_err(span, "this unsafe trait should be implemented explicitly");
+}
 
+pub fn expand_deriving_copy<F>(cx: &mut ExtCtxt,
+                               span: Span,
+                               mitem: &MetaItem,
+                               item: &Item,
+                               push: F) where
+    F: FnOnce(P<Item>),
+{
     let path = Path::new(vec![
         if cx.use_std { "std" } else { "core" },
         "marker",
-        name
+        "Copy",
     ]);
 
     let trait_def = TraitDef {
index 5f460264216a1567182a5c8b63f3d6bb44623455..f89f3ab55f3f90ec064847743f893c2143e4ebf5 100644 (file)
@@ -40,9 +40,9 @@ pub fn expand_deriving_clone<F>(cx: &mut ExtCtxt,
                 args: Vec::new(),
                 ret_ty: Self_,
                 attributes: attrs,
-                combine_substructure: combine_substructure(box |c, s, sub| {
+                combine_substructure: combine_substructure(Box::new(|c, s, sub| {
                     cs_clone("Clone", c, s, sub)
-                }),
+                })),
             }
         ),
         associated_types: Vec::new(),
index 80ef882745f878e152f3d24b29276bf6624db513..c02af437b1c7b987fdca37f696231b14740941bc 100644 (file)
@@ -40,7 +40,7 @@ fn cs_eq(cx: &mut ExtCtxt, span: Span, substr: &Substructure) -> P<Expr> {
                 cx.expr_binary(span, ast::BiAnd, subexpr, eq)
             },
             cx.expr_bool(span, true),
-            box |cx, span, _, _| cx.expr_bool(span, false),
+            Box::new(|cx, span, _, _| cx.expr_bool(span, false)),
             cx, span, substr)
     }
     fn cs_ne(cx: &mut ExtCtxt, span: Span, substr: &Substructure) -> P<Expr> {
@@ -57,7 +57,7 @@ fn cs_ne(cx: &mut ExtCtxt, span: Span, substr: &Substructure) -> P<Expr> {
                 cx.expr_binary(span, ast::BiOr, subexpr, eq)
             },
             cx.expr_bool(span, false),
-            box |cx, span, _, _| cx.expr_bool(span, true),
+            Box::new(|cx, span, _, _| cx.expr_bool(span, true)),
             cx, span, substr)
     }
 
@@ -72,9 +72,9 @@ macro_rules! md {
                 args: vec!(borrowed_self()),
                 ret_ty: Literal(path_local!(bool)),
                 attributes: attrs,
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     $f(a, b, c)
-                })
+                }))
             }
         } }
     }
index be4a33002aa1c69e87f2227fa0e6490e6571c120..b2b2654801863daa9512e5f9d029332282f3ffbc 100644 (file)
@@ -38,9 +38,9 @@ macro_rules! md {
                 args: vec!(borrowed_self()),
                 ret_ty: Literal(path_local!(bool)),
                 attributes: attrs,
-                combine_substructure: combine_substructure(box |cx, span, substr| {
+                combine_substructure: combine_substructure(Box::new(|cx, span, substr| {
                     cs_op($op, $equal, cx, span, substr)
-                })
+                }))
             }
         } }
     }
@@ -61,9 +61,9 @@ macro_rules! md {
         args: vec![borrowed_self()],
         ret_ty: ret_ty,
         attributes: attrs,
-        combine_substructure: combine_substructure(box |cx, span, substr| {
+        combine_substructure: combine_substructure(Box::new(|cx, span, substr| {
             cs_partial_cmp(cx, span, substr)
-        })
+        }))
     };
 
     let trait_def = TraitDef {
@@ -175,13 +175,13 @@ pub fn cs_partial_cmp(cx: &mut ExtCtxt, span: Span,
             cx.expr_block(cx.block(span, vec!(assign), Some(if_)))
         },
         equals_expr.clone(),
-        box |cx, span, (self_args, tag_tuple), _non_self_args| {
+        Box::new(|cx, span, (self_args, tag_tuple), _non_self_args| {
             if self_args.len() != 2 {
                 cx.span_bug(span, "not exactly 2 arguments in `derive(PartialOrd)`")
             } else {
                 some_ordering_collapsed(cx, span, PartialCmpOp, tag_tuple)
             }
-        },
+        }),
         cx, span, substr)
 }
 
@@ -223,7 +223,7 @@ fn cs_op(less: bool, equal: bool, cx: &mut ExtCtxt,
             cx.expr_binary(span, ast::BiOr, cmp, and)
         },
         cx.expr_bool(span, equal),
-        box |cx, span, (self_args, tag_tuple), _non_self_args| {
+        Box::new(|cx, span, (self_args, tag_tuple), _non_self_args| {
             if self_args.len() != 2 {
                 cx.span_bug(span, "not exactly 2 arguments in `derive(PartialOrd)`")
             } else {
@@ -233,6 +233,6 @@ fn cs_op(less: bool, equal: bool, cx: &mut ExtCtxt,
                 };
                 some_ordering_collapsed(cx, span, op, tag_tuple)
             }
-        },
+        }),
         cx, span, substr)
 }
index 31a754a1254bb486c88936b9674afe9c3d31f7c3..83164d242e8fbd730fdcc9784bc4a4bb104403f0 100644 (file)
@@ -32,7 +32,8 @@ fn cs_total_eq_assert(cx: &mut ExtCtxt, span: Span, substr: &Substructure) -> P<
             let block = cx.block(span, stmts, None);
             cx.expr_block(block)
         },
-                       box |cx, sp, _, _| cx.span_bug(sp, "non matching enums in derive(Eq)?"),
+                       Box::new(|cx, sp, _, _| {
+                           cx.span_bug(sp, "non matching enums in derive(Eq)?") }),
                        cx,
                        span,
                        substr)
@@ -57,9 +58,9 @@ fn cs_total_eq_assert(cx: &mut ExtCtxt, span: Span, substr: &Substructure) -> P<
                 args: vec!(),
                 ret_ty: nil_ty(),
                 attributes: attrs,
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     cs_total_eq_assert(a, b, c)
-                })
+                }))
             }
         ),
         associated_types: Vec::new(),
index 2f6f99bc1ee46211bf4959321e2b09ff43d064db..1de955856e712c208d5375574ccf3e7de76096c4 100644 (file)
@@ -41,9 +41,9 @@ pub fn expand_deriving_totalord<F>(cx: &mut ExtCtxt,
                 args: vec!(borrowed_self()),
                 ret_ty: Literal(path_std!(cx, core::cmp::Ordering)),
                 attributes: attrs,
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     cs_cmp(a, b, c)
-                }),
+                })),
             }
         ),
         associated_types: Vec::new(),
@@ -131,12 +131,12 @@ pub fn cs_cmp(cx: &mut ExtCtxt, span: Span,
             cx.expr_block(cx.block(span, vec!(assign), Some(if_)))
         },
         cx.expr_path(equals_path.clone()),
-        box |cx, span, (self_args, tag_tuple), _non_self_args| {
+        Box::new(|cx, span, (self_args, tag_tuple), _non_self_args| {
             if self_args.len() != 2 {
                 cx.span_bug(span, "not exactly 2 arguments in `derives(Ord)`")
             } else {
                 ordering_collapsed(cx, span, tag_tuple)
             }
-        },
+        }),
         cx, span, substr)
 }
index f27bbc338e5704b05f89bb5573d3834c1ca01695..6ce68948e4b010615b338836b0e85b49cd853a8b 100644 (file)
@@ -82,9 +82,9 @@ fn expand_deriving_decodable_imp<F>(cx: &mut ExtCtxt,
                     true
                 )),
                 attributes: Vec::new(),
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     decodable_substructure(a, b, c, krate)
-                }),
+                })),
             }
         ),
         associated_types: Vec::new(),
index c10975a2d32eb94e370aa0271267a472b6e5048a..f9991a233547c9dbc24511005df9643b38f65802 100644 (file)
@@ -40,9 +40,9 @@ pub fn expand_deriving_default<F>(cx: &mut ExtCtxt,
                 args: Vec::new(),
                 ret_ty: Self_,
                 attributes: attrs,
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     default_substructure(a, b, c)
-                })
+                }))
             }
         ),
         associated_types: Vec::new(),
index 8038074cee14fbe3473da0f0ce5997bbb6a9b800..d7961d7da00f1e2e296bfd2e1f04c0a2b4a18398 100644 (file)
@@ -158,9 +158,9 @@ fn expand_deriving_encodable_imp<F>(cx: &mut ExtCtxt,
                     true
                 )),
                 attributes: Vec::new(),
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     encodable_substructure(a, b, c)
-                }),
+                })),
             }
         ),
         associated_types: Vec::new(),
@@ -181,7 +181,6 @@ fn encodable_substructure(cx: &mut ExtCtxt, trait_span: Span,
         Struct(ref fields) => {
             let emit_struct_field = cx.ident_of("emit_struct_field");
             let mut stmts = Vec::new();
-            let last = fields.len() - 1;
             for (i, &FieldInfo {
                     name,
                     ref self_,
@@ -204,6 +203,7 @@ fn encodable_substructure(cx: &mut ExtCtxt, trait_span: Span,
                                                  lambda));
 
                 // last call doesn't need a try!
+                let last = fields.len() - 1;
                 let call = if i != last {
                     cx.expr_try(span, call)
                 } else {
@@ -240,25 +240,24 @@ fn encodable_substructure(cx: &mut ExtCtxt, trait_span: Span,
             let encoder = cx.expr_ident(trait_span, blkarg);
             let emit_variant_arg = cx.ident_of("emit_enum_variant_arg");
             let mut stmts = Vec::new();
-            let last = fields.len() - 1;
-            for (i, &FieldInfo { ref self_, span, .. }) in fields.iter().enumerate() {
-                let enc = cx.expr_method_call(span, self_.clone(),
-                                              encode, vec!(blkencoder.clone()));
-                let lambda = cx.lambda_expr_1(span, enc, blkarg);
-                let call = cx.expr_method_call(span, blkencoder.clone(),
-                                               emit_variant_arg,
-                                               vec!(cx.expr_usize(span, i),
-                                                 lambda));
-                let call = if i != last {
-                    cx.expr_try(span, call)
-                } else {
-                    cx.expr(span, ExprRet(Some(call)))
-                };
-                stmts.push(cx.stmt_expr(call));
-            }
-
-            // enums with no fields need to return Ok()
-            if stmts.len() == 0 {
+            if fields.len() > 0 {
+                let last = fields.len() - 1;
+                for (i, &FieldInfo { ref self_, span, .. }) in fields.iter().enumerate() {
+                    let enc = cx.expr_method_call(span, self_.clone(),
+                                                  encode, vec!(blkencoder.clone()));
+                    let lambda = cx.lambda_expr_1(span, enc, blkarg);
+                    let call = cx.expr_method_call(span, blkencoder.clone(),
+                                                   emit_variant_arg,
+                                                   vec!(cx.expr_usize(span, i),
+                                                        lambda));
+                    let call = if i != last {
+                        cx.expr_try(span, call)
+                    } else {
+                        cx.expr(span, ExprRet(Some(call)))
+                    };
+                    stmts.push(cx.stmt_expr(call));
+                }
+            } else {
                 let ret_ok = cx.expr(trait_span,
                                      ExprRet(Some(cx.expr_ok(trait_span,
                                                              cx.expr_tuple(trait_span, vec![])))));
index a36d3a155b8d86de2db26d46d15627bfba53e99d..9cd965a8138e083d475da73ced390cc630b3f347 100644 (file)
@@ -1216,7 +1216,8 @@ fn set_expn_info(&self,
             callee: codemap::NameAndSpan {
                 name: format!("derive({})", trait_name),
                 format: codemap::MacroAttribute,
-                span: Some(self.span)
+                span: Some(self.span),
+                allow_internal_unstable: false,
             }
         });
         to_set
index 2149c7a7f77a7da72d86848fd952f24a415865ca..da80c7a0e6d15553f240e727654559bb33b71342 100644 (file)
@@ -45,9 +45,9 @@ pub fn expand_deriving_hash<F>(cx: &mut ExtCtxt,
                 args: vec!(Ptr(box Literal(arg), Borrowed(None, MutMutable))),
                 ret_ty: nil_ty(),
                 attributes: vec![],
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     hash_substructure(a, b, c)
-                })
+                }))
             }
         ),
         associated_types: Vec::new(),
index 973c8f5fa1e0b4b26a39defe621cbe74107aab0f..2631c28cf2fe9296e19e9589a4d01ab13ee114dd 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2013 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2012-2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
 //! FIXME (#2810): hygiene. Search for "__" strings (in other files too). We also assume "extra" is
 //! the standard library, and "std" is the core library.
 
-use ast::{Item, MetaItem, MetaList, MetaNameValue, MetaWord};
-use ext::base::ExtCtxt;
+use ast::{Item, MetaItem, MetaWord};
+use attr::AttrMetaMethods;
+use ext::base::{ExtCtxt, SyntaxEnv, Decorator, ItemDecorator, Modifier};
+use ext::build::AstBuilder;
+use feature_gate;
 use codemap::Span;
+use parse::token::{intern, intern_and_get_ident};
 use ptr::P;
 
 macro_rules! pathvec {
@@ -74,101 +78,133 @@ macro_rules! path_std {
 
 pub mod generic;
 
-pub fn expand_deprecated_deriving(cx: &mut ExtCtxt,
-                                  span: Span,
-                                  _: &MetaItem,
-                                  _: &Item,
-                                  _: &mut FnMut(P<Item>)) {
+fn expand_deprecated_deriving(cx: &mut ExtCtxt,
+                              span: Span,
+                              _: &MetaItem,
+                              _: &Item,
+                              _: &mut FnMut(P<Item>)) {
     cx.span_err(span, "`deriving` has been renamed to `derive`");
 }
 
-pub fn expand_meta_derive(cx: &mut ExtCtxt,
-                          _span: Span,
-                          mitem: &MetaItem,
-                          item: &Item,
-                          push: &mut FnMut(P<Item>)) {
-    match mitem.node {
-        MetaNameValue(_, ref l) => {
-            cx.span_err(l.span, "unexpected value in `derive`");
+fn expand_derive(cx: &mut ExtCtxt,
+                 _: Span,
+                 mitem: &MetaItem,
+                 item: P<Item>) -> P<Item> {
+    item.map(|mut item| {
+        if mitem.value_str().is_some() {
+            cx.span_err(mitem.span, "unexpected value in `derive`");
         }
-        MetaWord(_) => {
+
+        let traits = mitem.meta_item_list().unwrap_or(&[]);
+        if traits.is_empty() {
             cx.span_warn(mitem.span, "empty trait list in `derive`");
         }
-        MetaList(_, ref titems) if titems.len() == 0 => {
-            cx.span_warn(mitem.span, "empty trait list in `derive`");
+
+        for titem in traits.iter().rev() {
+            let tname = match titem.node {
+                MetaWord(ref tname) => tname,
+                _ => {
+                    cx.span_err(titem.span, "malformed `derive` entry");
+                    continue;
+                }
+            };
+
+            if !(is_builtin_trait(tname) || cx.ecfg.enable_custom_derive()) {
+                feature_gate::emit_feature_err(&cx.parse_sess.span_diagnostic,
+                                               "custom_derive",
+                                               titem.span,
+                                               feature_gate::EXPLAIN_CUSTOM_DERIVE);
+                continue;
+            }
+
+            // #[derive(Foo, Bar)] expands to #[derive_Foo] #[derive_Bar]
+            item.attrs.push(cx.attribute(titem.span, cx.meta_word(titem.span,
+                intern_and_get_ident(&format!("derive_{}", tname)))));
         }
-        MetaList(_, ref titems) => {
-            for titem in titems.iter().rev() {
-                match titem.node {
-                    MetaNameValue(ref tname, _) |
-                    MetaList(ref tname, _) |
-                    MetaWord(ref tname) => {
-                        macro_rules! expand {
-                            ($func:path) => ($func(cx, titem.span, &**titem, item,
-                                                   |i| push(i)))
-                        }
-
-                        match &tname[..] {
-                            "Clone" => expand!(clone::expand_deriving_clone),
-
-                            "Hash" => expand!(hash::expand_deriving_hash),
-
-                            "RustcEncodable" => {
-                                expand!(encodable::expand_deriving_rustc_encodable)
-                            }
-                            "RustcDecodable" => {
-                                expand!(decodable::expand_deriving_rustc_decodable)
-                            }
-                            "Encodable" => {
-                                cx.span_warn(titem.span,
-                                             "derive(Encodable) is deprecated \
-                                              in favor of derive(RustcEncodable)");
-
-                                expand!(encodable::expand_deriving_encodable)
-                            }
-                            "Decodable" => {
-                                cx.span_warn(titem.span,
-                                             "derive(Decodable) is deprecated \
-                                              in favor of derive(RustcDecodable)");
-
-                                expand!(decodable::expand_deriving_decodable)
-                            }
-
-                            "PartialEq" => expand!(eq::expand_deriving_eq),
-                            "Eq" => expand!(totaleq::expand_deriving_totaleq),
-                            "PartialOrd" => expand!(ord::expand_deriving_ord),
-                            "Ord" => expand!(totalord::expand_deriving_totalord),
-
-                            "Rand" => expand!(rand::expand_deriving_rand),
-
-                            "Show" => {
-                                cx.span_warn(titem.span,
-                                             "derive(Show) is deprecated \
-                                              in favor of derive(Debug)");
-
-                                expand!(show::expand_deriving_show)
-                            },
-
-                            "Debug" => expand!(show::expand_deriving_show),
-
-                            "Default" => expand!(default::expand_deriving_default),
-
-                            "FromPrimitive" => expand!(primitive::expand_deriving_from_primitive),
-
-                            "Send" => expand!(bounds::expand_deriving_bound),
-                            "Sync" => expand!(bounds::expand_deriving_bound),
-                            "Copy" => expand!(bounds::expand_deriving_bound),
-
-                            ref tname => {
-                                cx.span_err(titem.span,
-                                            &format!("unknown `derive` \
-                                                     trait: `{}`",
-                                                    *tname));
-                            }
-                        };
+
+        item
+    })
+}
+
+macro_rules! derive_traits {
+    ($( $name:expr => $func:path, )*) => {
+        pub fn register_all(env: &mut SyntaxEnv) {
+            // Define the #[derive_*] extensions.
+            $({
+                struct DeriveExtension;
+
+                impl ItemDecorator for DeriveExtension {
+                    fn expand(&self,
+                              ecx: &mut ExtCtxt,
+                              sp: Span,
+                              mitem: &MetaItem,
+                              item: &Item,
+                              push: &mut FnMut(P<Item>)) {
+                        warn_if_deprecated(ecx, sp, $name);
+                        $func(ecx, sp, mitem, item, |i| push(i));
                     }
                 }
+
+                env.insert(intern(concat!("derive_", $name)),
+                           Decorator(Box::new(DeriveExtension)));
+            })*
+
+            env.insert(intern("derive"),
+                       Modifier(Box::new(expand_derive)));
+            env.insert(intern("deriving"),
+                       Decorator(Box::new(expand_deprecated_deriving)));
+        }
+
+        fn is_builtin_trait(name: &str) -> bool {
+            match name {
+                $( $name )|* => true,
+                _ => false,
             }
         }
     }
 }
+
+derive_traits! {
+    "Clone" => clone::expand_deriving_clone,
+
+    "Hash" => hash::expand_deriving_hash,
+
+    "RustcEncodable" => encodable::expand_deriving_rustc_encodable,
+
+    "RustcDecodable" => decodable::expand_deriving_rustc_decodable,
+
+    "PartialEq" => eq::expand_deriving_eq,
+    "Eq" => totaleq::expand_deriving_totaleq,
+    "PartialOrd" => ord::expand_deriving_ord,
+    "Ord" => totalord::expand_deriving_totalord,
+
+    "Rand" => rand::expand_deriving_rand,
+
+    "Debug" => show::expand_deriving_show,
+
+    "Default" => default::expand_deriving_default,
+
+    "FromPrimitive" => primitive::expand_deriving_from_primitive,
+
+    "Send" => bounds::expand_deriving_unsafe_bound,
+    "Sync" => bounds::expand_deriving_unsafe_bound,
+    "Copy" => bounds::expand_deriving_copy,
+
+    // deprecated
+    "Show" => show::expand_deriving_show,
+    "Encodable" => encodable::expand_deriving_encodable,
+    "Decodable" => decodable::expand_deriving_decodable,
+}
+
+#[inline] // because `name` is a compile-time constant
+fn warn_if_deprecated(ecx: &mut ExtCtxt, sp: Span, name: &str) {
+    if let Some(replacement) = match name {
+        "Show" => Some("Debug"),
+        "Encodable" => Some("RustcEncodable"),
+        "Decodable" => Some("RustcDecodable"),
+        _ => None,
+    } {
+        ecx.span_warn(sp, &format!("derive({}) is deprecated in favor of derive({})",
+                                   name, replacement));
+    }
+}
index 3b96292323a95039ab6f17535c704ce75023138b..b2d0a9f6b51ad329a30b044332f2d32cbcc37880 100644 (file)
@@ -45,9 +45,9 @@ pub fn expand_deriving_from_primitive<F>(cx: &mut ExtCtxt,
                                            true)),
                 // #[inline] liable to cause code-bloat
                 attributes: attrs.clone(),
-                combine_substructure: combine_substructure(box |c, s, sub| {
+                combine_substructure: combine_substructure(Box::new(|c, s, sub| {
                     cs_from("i64", c, s, sub)
-                }),
+                })),
             },
             MethodDef {
                 name: "from_u64",
@@ -60,9 +60,9 @@ pub fn expand_deriving_from_primitive<F>(cx: &mut ExtCtxt,
                                            true)),
                 // #[inline] liable to cause code-bloat
                 attributes: attrs,
-                combine_substructure: combine_substructure(box |c, s, sub| {
+                combine_substructure: combine_substructure(Box::new(|c, s, sub| {
                     cs_from("u64", c, s, sub)
-                }),
+                })),
             }
         ),
         associated_types: Vec::new(),
index 029b65351081967166e2793c802ce152d16c8bab..8a764fded6fd9d3cf3aca73028cffb07146ae51f 100644 (file)
@@ -55,9 +55,9 @@ pub fn expand_deriving_rand<F>(cx: &mut ExtCtxt,
                 ),
                 ret_ty: Self_,
                 attributes: Vec::new(),
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     rand_substructure(a, b, c)
-                })
+                }))
             }
         ),
         associated_types: Vec::new(),
index 281f23f9e61e8b232d2c083348bdaa90b873b790..ce89c541fd44b89f6677d9193c266c834b80ac30 100644 (file)
@@ -46,9 +46,9 @@ pub fn expand_deriving_show<F>(cx: &mut ExtCtxt,
                 args: vec!(fmtr),
                 ret_ty: Literal(path_std!(cx, core::fmt::Result)),
                 attributes: Vec::new(),
-                combine_substructure: combine_substructure(box |a, b, c| {
+                combine_substructure: combine_substructure(Box::new(|a, b, c| {
                     show_substructure(a, b, c)
-                })
+                }))
             }
         ],
         associated_types: Vec::new(),
index bea57ae14e4af27c91d8600e7016525bdda30456..98c7aefcd8ad3275f68122308e65b87d790b441e 100644 (file)
@@ -22,7 +22,7 @@
 use codemap;
 use codemap::{Span, Spanned, ExpnInfo, NameAndSpan, MacroBang, MacroAttribute};
 use ext::base::*;
-use feature_gate::{Features};
+use feature_gate::{self, Features};
 use fold;
 use fold::*;
 use parse;
@@ -395,13 +395,14 @@ fn expand_mac_invoc<T, F, G>(mac: ast::Mac, span: codemap::Span,
                     None
                 }
                 Some(rc) => match *rc {
-                    NormalTT(ref expandfun, exp_span) => {
+                    NormalTT(ref expandfun, exp_span, allow_internal_unstable) => {
                         fld.cx.bt_push(ExpnInfo {
                                 call_site: span,
                                 callee: NameAndSpan {
                                     name: extnamestr.to_string(),
                                     format: MacroBang,
                                     span: exp_span,
+                                    allow_internal_unstable: allow_internal_unstable,
                                 },
                             });
                         let fm = fresh_mark();
@@ -530,6 +531,9 @@ fn expand_item_modifiers(mut it: P<ast::Item>, fld: &mut MacroExpander)
                             name: mname.to_string(),
                             format: MacroAttribute,
                             span: None,
+                            // attributes can do whatever they like,
+                            // for now
+                            allow_internal_unstable: true,
                         }
                     });
                     it = mac.expand(fld.cx, attr.span, &*attr.node.value, it);
@@ -571,7 +575,7 @@ fn contains_macro_use(fld: &mut MacroExpander, attrs: &[ast::Attribute]) -> bool
             fld.cx.span_warn(attr.span, "macro_escape is a deprecated synonym for macro_use");
             is_use = true;
             if let ast::AttrInner = attr.node.style {
-                fld.cx.span_help(attr.span, "consider an outer attribute, \
+                fld.cx.fileline_help(attr.span, "consider an outer attribute, \
                                              #[macro_use] mod ...");
             }
         };
@@ -614,7 +618,7 @@ pub fn expand_item_mac(it: P<ast::Item>,
             }
 
             Some(rc) => match *rc {
-                NormalTT(ref expander, span) => {
+                NormalTT(ref expander, span, allow_internal_unstable) => {
                     if it.ident.name != parse::token::special_idents::invalid.name {
                         fld.cx
                             .span_err(path_span,
@@ -628,14 +632,15 @@ pub fn expand_item_mac(it: P<ast::Item>,
                         callee: NameAndSpan {
                             name: extnamestr.to_string(),
                             format: MacroBang,
-                            span: span
+                            span: span,
+                            allow_internal_unstable: allow_internal_unstable,
                         }
                     });
                     // mark before expansion:
                     let marked_before = mark_tts(&tts[..], fm);
                     expander.expand(fld.cx, it.span, &marked_before[..])
                 }
-                IdentTT(ref expander, span) => {
+                IdentTT(ref expander, span, allow_internal_unstable) => {
                     if it.ident.name == parse::token::special_idents::invalid.name {
                         fld.cx.span_err(path_span,
                                         &format!("macro {}! expects an ident argument",
@@ -647,7 +652,8 @@ pub fn expand_item_mac(it: P<ast::Item>,
                         callee: NameAndSpan {
                             name: extnamestr.to_string(),
                             format: MacroBang,
-                            span: span
+                            span: span,
+                            allow_internal_unstable: allow_internal_unstable,
                         }
                     });
                     // mark before expansion:
@@ -661,16 +667,35 @@ pub fn expand_item_mac(it: P<ast::Item>,
                                         );
                         return SmallVector::zero();
                     }
+
                     fld.cx.bt_push(ExpnInfo {
                         call_site: it.span,
                         callee: NameAndSpan {
                             name: extnamestr.to_string(),
                             format: MacroBang,
                             span: None,
+                            // `macro_rules!` doesn't directly allow
+                            // unstable (this is orthogonal to whether
+                            // the macro it creates allows it)
+                            allow_internal_unstable: false,
                         }
                     });
                     // DON'T mark before expansion.
 
+                    let allow_internal_unstable = attr::contains_name(&it.attrs,
+                                                                      "allow_internal_unstable");
+
+                    // ensure any #[allow_internal_unstable]s are
+                    // detected (including nested macro definitions
+                    // etc.)
+                    if allow_internal_unstable && !fld.cx.ecfg.enable_allow_internal_unstable() {
+                        feature_gate::emit_feature_err(
+                            &fld.cx.parse_sess.span_diagnostic,
+                            "allow_internal_unstable",
+                            it.span,
+                            feature_gate::EXPLAIN_ALLOW_INTERNAL_UNSTABLE)
+                    }
+
                     let def = ast::MacroDef {
                         ident: it.ident,
                         attrs: it.attrs.clone(),
@@ -679,6 +704,7 @@ pub fn expand_item_mac(it: P<ast::Item>,
                         imported_from: None,
                         export: attr::contains_name(&it.attrs, "macro_export"),
                         use_locally: true,
+                        allow_internal_unstable: allow_internal_unstable,
                         body: tts,
                     };
                     fld.cx.insert_macro(def);
@@ -959,13 +985,14 @@ fn expand_pat(p: P<ast::Pat>, fld: &mut MacroExpander) -> P<ast::Pat> {
             }
 
             Some(rc) => match *rc {
-                NormalTT(ref expander, tt_span) => {
+                NormalTT(ref expander, tt_span, allow_internal_unstable) => {
                     fld.cx.bt_push(ExpnInfo {
                         call_site: span,
                         callee: NameAndSpan {
                             name: extnamestr.to_string(),
                             format: MacroBang,
-                            span: tt_span
+                            span: tt_span,
+                            allow_internal_unstable: allow_internal_unstable,
                         }
                     });
 
@@ -1094,7 +1121,10 @@ fn expand_annotatable(a: Annotatable,
                         callee: NameAndSpan {
                             name: mname.to_string(),
                             format: MacroAttribute,
-                            span: None
+                            span: None,
+                            // attributes can do whatever they like,
+                            // for now.
+                            allow_internal_unstable: true,
                         }
                     });
 
@@ -1244,6 +1274,9 @@ fn expand_item_multi_modifier(mut it: Annotatable,
                             name: mname.to_string(),
                             format: MacroAttribute,
                             span: None,
+                            // attributes can do whatever they like,
+                            // for now
+                            allow_internal_unstable: true,
                         }
                     });
                     it = mac.expand(fld.cx, attr.span, &*attr.node.value, it);
@@ -1414,6 +1447,19 @@ pub struct ExpansionConfig<'feat> {
     pub recursion_limit: usize,
 }
 
+macro_rules! feature_tests {
+    ($( fn $getter:ident = $field:ident, )*) => {
+        $(
+            pub fn $getter(&self) -> bool {
+                match self.features {
+                    Some(&Features { $field: true, .. }) => true,
+                    _ => false,
+                }
+            }
+        )*
+    }
+}
+
 impl<'feat> ExpansionConfig<'feat> {
     pub fn default(crate_name: String) -> ExpansionConfig<'static> {
         ExpansionConfig {
@@ -1423,39 +1469,14 @@ pub fn default(crate_name: String) -> ExpansionConfig<'static> {
         }
     }
 
-    pub fn enable_quotes(&self) -> bool {
-        match self.features {
-            Some(&Features { allow_quote: true, .. }) => true,
-            _ => false,
-        }
-    }
-
-    pub fn enable_asm(&self) -> bool {
-        match self.features {
-            Some(&Features { allow_asm: true, .. }) => true,
-            _ => false,
-        }
-    }
-
-    pub fn enable_log_syntax(&self) -> bool {
-        match self.features {
-            Some(&Features { allow_log_syntax: true, .. }) => true,
-            _ => false,
-        }
-    }
-
-    pub fn enable_concat_idents(&self) -> bool {
-        match self.features {
-            Some(&Features { allow_concat_idents: true, .. }) => true,
-            _ => false,
-        }
-    }
-
-    pub fn enable_trace_macros(&self) -> bool {
-        match self.features {
-            Some(&Features { allow_trace_macros: true, .. }) => true,
-            _ => false,
-        }
+    feature_tests! {
+        fn enable_quotes = allow_quote,
+        fn enable_asm = allow_asm,
+        fn enable_log_syntax = allow_log_syntax,
+        fn enable_concat_idents = allow_concat_idents,
+        fn enable_trace_macros = allow_trace_macros,
+        fn enable_allow_internal_unstable = allow_internal_unstable,
+        fn enable_custom_derive = allow_custom_derive,
     }
 }
 
@@ -1635,7 +1656,7 @@ fn test_ecfg() -> ExpansionConfig<'static> {
     }
 
     // make sure that macros can't escape fns
-    #[should_fail]
+    #[should_panic]
     #[test] fn macros_cant_escape_fns_test () {
         let src = "fn bogus() {macro_rules! z (() => (3+4));}\
                    fn inty() -> i32 { z!() }".to_string();
@@ -1649,7 +1670,7 @@ fn test_ecfg() -> ExpansionConfig<'static> {
     }
 
     // make sure that macros can't escape modules
-    #[should_fail]
+    #[should_panic]
     #[test] fn macros_cant_escape_mods_test () {
         let src = "mod foo {macro_rules! z (() => (3+4));}\
                    fn inty() -> i32 { z!() }".to_string();
index 544fb15dcde7b0a829963bb40cc694e4009d9b30..737648cd90c37bc56cf3a4715157bd8bea08ed78 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
@@ -401,7 +401,7 @@ pub fn expand_quote_tokens<'cx>(cx: &'cx mut ExtCtxt,
                                 tts: &[ast::TokenTree])
                                 -> Box<base::MacResult+'cx> {
     let (cx_expr, expr) = expand_tts(cx, sp, tts);
-    let expanded = expand_wrapper(cx, sp, cx_expr, expr);
+    let expanded = expand_wrapper(cx, sp, cx_expr, expr, &[&["syntax", "ext", "quote", "rt"]]);
     base::MacEager::expr(expanded)
 }
 
@@ -465,6 +465,32 @@ pub fn expand_quote_stmt(cx: &mut ExtCtxt,
     base::MacEager::expr(expanded)
 }
 
+pub fn expand_quote_attr(cx: &mut ExtCtxt,
+                         sp: Span,
+                         tts: &[ast::TokenTree])
+                         -> Box<base::MacResult+'static> {
+    let expanded = expand_parse_call(cx, sp, "parse_attribute",
+                                    vec!(cx.expr_bool(sp, true)), tts);
+
+    base::MacEager::expr(expanded)
+}
+
+pub fn expand_quote_matcher(cx: &mut ExtCtxt,
+                            sp: Span,
+                            tts: &[ast::TokenTree])
+                            -> Box<base::MacResult+'static> {
+    let (cx_expr, tts) = parse_arguments_to_quote(cx, tts);
+    let mut vector = mk_stmts_let(cx, sp);
+    vector.extend(statements_mk_tts(cx, &tts[..], true).into_iter());
+    let block = cx.expr_block(
+        cx.block_all(sp,
+                     vector,
+                     Some(cx.expr_ident(sp, id_ext("tt")))));
+
+    let expanded = expand_wrapper(cx, sp, cx_expr, block, &[&["syntax", "ext", "quote", "rt"]]);
+    base::MacEager::expr(expanded)
+}
+
 fn ids_ext(strs: Vec<String> ) -> Vec<ast::Ident> {
     strs.iter().map(|str| str_to_ident(&(*str))).collect()
 }
@@ -527,7 +553,7 @@ fn mk_delim(cx: &ExtCtxt, sp: Span, delim: token::DelimToken) -> P<ast::Expr> {
 }
 
 #[allow(non_upper_case_globals)]
-fn mk_token(cx: &ExtCtxt, sp: Span, tok: &token::Token) -> P<ast::Expr> {
+fn expr_mk_token(cx: &ExtCtxt, sp: Span, tok: &token::Token) -> P<ast::Expr> {
     macro_rules! mk_lit {
         ($name: expr, $suffix: expr, $($args: expr),*) => {{
             let inner = cx.expr_call(sp, mk_token_path(cx, sp, $name), vec![$($args),*]);
@@ -606,6 +632,21 @@ macro_rules! mk_lit {
                                 vec!(mk_name(cx, sp, ident.ident())));
         }
 
+        token::MatchNt(name, kind, namep, kindp) => {
+            return cx.expr_call(sp,
+                                mk_token_path(cx, sp, "MatchNt"),
+                                vec!(mk_ident(cx, sp, name),
+                                     mk_ident(cx, sp, kind),
+                                     match namep {
+                                        ModName => mk_token_path(cx, sp, "ModName"),
+                                        Plain   => mk_token_path(cx, sp, "Plain"),
+                                     },
+                                     match kindp {
+                                        ModName => mk_token_path(cx, sp, "ModName"),
+                                        Plain   => mk_token_path(cx, sp, "Plain"),
+                                     }));
+        }
+
         token::Interpolated(_) => panic!("quote! with interpolated token"),
 
         _ => ()
@@ -635,14 +676,15 @@ macro_rules! mk_lit {
         token::FatArrow     => "FatArrow",
         token::Pound        => "Pound",
         token::Dollar       => "Dollar",
+        token::Question     => "Question",
         token::Underscore   => "Underscore",
         token::Eof          => "Eof",
-        _                   => panic!(),
+        _                   => panic!("unhandled token in quote!"),
     };
     mk_token_path(cx, sp, name)
 }
 
-fn mk_tt(cx: &ExtCtxt, tt: &ast::TokenTree) -> Vec<P<ast::Stmt>> {
+fn statements_mk_tt(cx: &ExtCtxt, tt: &ast::TokenTree, matcher: bool) -> Vec<P<ast::Stmt>> {
     match *tt {
         ast::TtToken(sp, SubstNt(ident, _)) => {
             // tt.extend($ident.to_tokens(ext_cx).into_iter())
@@ -663,18 +705,18 @@ fn mk_tt(cx: &ExtCtxt, tt: &ast::TokenTree) -> Vec<P<ast::Stmt>> {
 
             vec!(cx.stmt_expr(e_push))
         }
-        ref tt @ ast::TtToken(_, MatchNt(..)) => {
+        ref tt @ ast::TtToken(_, MatchNt(..)) if !matcher => {
             let mut seq = vec![];
             for i in 0..tt.len() {
                 seq.push(tt.get_tt(i));
             }
-            mk_tts(cx, &seq[..])
+            statements_mk_tts(cx, &seq[..], matcher)
         }
         ast::TtToken(sp, ref tok) => {
             let e_sp = cx.expr_ident(sp, id_ext("_sp"));
             let e_tok = cx.expr_call(sp,
                                      mk_ast_path(cx, sp, "TtToken"),
-                                     vec!(e_sp, mk_token(cx, sp, tok)));
+                                     vec!(e_sp, expr_mk_token(cx, sp, tok)));
             let e_push =
                 cx.expr_method_call(sp,
                                     cx.expr_ident(sp, id_ext("tt")),
@@ -683,27 +725,61 @@ fn mk_tt(cx: &ExtCtxt, tt: &ast::TokenTree) -> Vec<P<ast::Stmt>> {
             vec!(cx.stmt_expr(e_push))
         },
         ast::TtDelimited(_, ref delimed) => {
-            mk_tt(cx, &delimed.open_tt()).into_iter()
-                .chain(delimed.tts.iter().flat_map(|tt| mk_tt(cx, tt).into_iter()))
-                .chain(mk_tt(cx, &delimed.close_tt()).into_iter())
+            statements_mk_tt(cx, &delimed.open_tt(), matcher).into_iter()
+                .chain(delimed.tts.iter()
+                                  .flat_map(|tt| statements_mk_tt(cx, tt, matcher).into_iter()))
+                .chain(statements_mk_tt(cx, &delimed.close_tt(), matcher).into_iter())
                 .collect()
         },
-        ast::TtSequence(..) => panic!("TtSequence in quote!"),
-    }
-}
+        ast::TtSequence(sp, ref seq) => {
+            if !matcher {
+                panic!("TtSequence in quote!");
+            }
 
-fn mk_tts(cx: &ExtCtxt, tts: &[ast::TokenTree]) -> Vec<P<ast::Stmt>> {
-    let mut ss = Vec::new();
-    for tt in tts {
-        ss.extend(mk_tt(cx, tt).into_iter());
+            let e_sp = cx.expr_ident(sp, id_ext("_sp"));
+
+            let stmt_let_tt = cx.stmt_let(sp, true, id_ext("tt"), cx.expr_vec_ng(sp));
+            let mut tts_stmts = vec![stmt_let_tt];
+            tts_stmts.extend(statements_mk_tts(cx, &seq.tts[..], matcher).into_iter());
+            let e_tts = cx.expr_block(cx.block(sp, tts_stmts,
+                                                   Some(cx.expr_ident(sp, id_ext("tt")))));
+            let e_separator = match seq.separator {
+                Some(ref sep) => cx.expr_some(sp, expr_mk_token(cx, sp, sep)),
+                None => cx.expr_none(sp),
+            };
+            let e_op = match seq.op {
+                ast::ZeroOrMore => mk_ast_path(cx, sp, "ZeroOrMore"),
+                ast::OneOrMore => mk_ast_path(cx, sp, "OneOrMore"),
+            };
+            let fields = vec![cx.field_imm(sp, id_ext("tts"), e_tts),
+                              cx.field_imm(sp, id_ext("separator"), e_separator),
+                              cx.field_imm(sp, id_ext("op"), e_op),
+                              cx.field_imm(sp, id_ext("num_captures"),
+                                               cx.expr_usize(sp, seq.num_captures))];
+            let seq_path = vec![id_ext("syntax"), id_ext("ast"), id_ext("SequenceRepetition")];
+            let e_seq_struct = cx.expr_struct(sp, cx.path_global(sp, seq_path), fields);
+            let e_rc_new = cx.expr_call_global(sp, vec![id_ext("std"),
+                                                        id_ext("rc"),
+                                                        id_ext("Rc"),
+                                                        id_ext("new")],
+                                                   vec![e_seq_struct]);
+            let e_tok = cx.expr_call(sp,
+                                     mk_ast_path(cx, sp, "TtSequence"),
+                                     vec!(e_sp, e_rc_new));
+            let e_push =
+                cx.expr_method_call(sp,
+                                    cx.expr_ident(sp, id_ext("tt")),
+                                    id_ext("push"),
+                                    vec!(e_tok));
+            vec!(cx.stmt_expr(e_push))
+        }
     }
-    ss
 }
 
-fn expand_tts(cx: &ExtCtxt, sp: Span, tts: &[ast::TokenTree])
-              -> (P<ast::Expr>, P<ast::Expr>) {
+fn parse_arguments_to_quote(cx: &ExtCtxt, tts: &[ast::TokenTree])
+                            -> (P<ast::Expr>, Vec<ast::TokenTree>) {
     // NB: It appears that the main parser loses its mind if we consider
-    // $foo as a TtNonterminal during the main parse, so we have to re-parse
+    // $foo as a SubstNt during the main parse, so we have to re-parse
     // under quote_depth > 0. This is silly and should go away; the _guess_ is
     // it has to do with transition away from supporting old-style macros, so
     // try removing it when enough of them are gone.
@@ -719,6 +795,10 @@ fn expand_tts(cx: &ExtCtxt, sp: Span, tts: &[ast::TokenTree])
     let tts = p.parse_all_token_trees();
     p.abort_if_errors();
 
+    (cx_expr, tts)
+}
+
+fn mk_stmts_let(cx: &ExtCtxt, sp: Span) -> Vec<P<ast::Stmt>> {
     // We also bind a single value, sp, to ext_cx.call_site()
     //
     // This causes every span in a token-tree quote to be attributed to the
@@ -756,8 +836,23 @@ fn expand_tts(cx: &ExtCtxt, sp: Span, tts: &[ast::TokenTree])
 
     let stmt_let_tt = cx.stmt_let(sp, true, id_ext("tt"), cx.expr_vec_ng(sp));
 
-    let mut vector = vec!(stmt_let_sp, stmt_let_tt);
-    vector.extend(mk_tts(cx, &tts[..]).into_iter());
+    vec!(stmt_let_sp, stmt_let_tt)
+}
+
+fn statements_mk_tts(cx: &ExtCtxt, tts: &[ast::TokenTree], matcher: bool) -> Vec<P<ast::Stmt>> {
+    let mut ss = Vec::new();
+    for tt in tts {
+        ss.extend(statements_mk_tt(cx, tt, matcher).into_iter());
+    }
+    ss
+}
+
+fn expand_tts(cx: &ExtCtxt, sp: Span, tts: &[ast::TokenTree])
+              -> (P<ast::Expr>, P<ast::Expr>) {
+    let (cx_expr, tts) = parse_arguments_to_quote(cx, tts);
+
+    let mut vector = mk_stmts_let(cx, sp);
+    vector.extend(statements_mk_tts(cx, &tts[..], false).into_iter());
     let block = cx.expr_block(
         cx.block_all(sp,
                      vector,
@@ -769,14 +864,14 @@ fn expand_tts(cx: &ExtCtxt, sp: Span, tts: &[ast::TokenTree])
 fn expand_wrapper(cx: &ExtCtxt,
                   sp: Span,
                   cx_expr: P<ast::Expr>,
-                  expr: P<ast::Expr>) -> P<ast::Expr> {
+                  expr: P<ast::Expr>,
+                  imports: &[&[&str]]) -> P<ast::Expr> {
     // Explicitly borrow to avoid moving from the invoker (#16992)
     let cx_expr_borrow = cx.expr_addr_of(sp, cx.expr_deref(sp, cx_expr));
     let stmt_let_ext_cx = cx.stmt_let(sp, false, id_ext("ext_cx"), cx_expr_borrow);
 
-    let stmts = [
-        &["syntax", "ext", "quote", "rt"],
-    ].iter().map(|path| {
+    let stmts = imports.iter().map(|path| {
+        // make item: `use ...;`
         let path = path.iter().map(|s| s.to_string()).collect();
         cx.stmt_item(sp, cx.item_use_glob(sp, ast::Inherited, ids_ext(path)))
     }).chain(Some(stmt_let_ext_cx).into_iter()).collect();
@@ -807,5 +902,10 @@ fn expand_parse_call(cx: &ExtCtxt,
     let expr = cx.expr_method_call(sp, new_parser_call, id_ext(parse_method),
                                    arg_exprs);
 
-    expand_wrapper(cx, sp, cx_expr, expr)
+    if parse_method == "parse_attribute" {
+        expand_wrapper(cx, sp, cx_expr, expr, &[&["syntax", "ext", "quote", "rt"],
+                                                &["syntax", "parse", "attr"]])
+    } else {
+        expand_wrapper(cx, sp, cx_expr, expr, &[&["syntax", "ext", "quote", "rt"]])
+    }
 }
index ba3743cdb335bcf8855af674f06704c605c65aa8..62d98be8b8505e9bca2d0f7f9f64b815f0ef7672 100644 (file)
@@ -20,7 +20,9 @@
 use ptr::P;
 use util::small_vector::SmallVector;
 
-use std::old_io::File;
+use std::fs::File;
+use std::io::prelude::*;
+use std::path::{Path, PathBuf};
 use std::rc::Rc;
 
 // These macros all relate to the file system; they either return
@@ -97,7 +99,7 @@ pub fn expand_include<'cx>(cx: &'cx mut ExtCtxt, sp: Span, tts: &[ast::TokenTree
                                         cx.cfg(),
                                         &res_rel_file(cx,
                                                       sp,
-                                                      &Path::new(file)),
+                                                      Path::new(&file)),
                                         true,
                                         None,
                                         sp);
@@ -136,8 +138,10 @@ pub fn expand_include_str(cx: &mut ExtCtxt, sp: Span, tts: &[ast::TokenTree])
         Some(f) => f,
         None => return DummyResult::expr(sp)
     };
-    let file = res_rel_file(cx, sp, &Path::new(file));
-    let bytes = match File::open(&file).read_to_end() {
+    let file = res_rel_file(cx, sp, Path::new(&file));
+    let mut bytes = Vec::new();
+    match File::open(&file).and_then(|mut f| f.read_to_end(&mut bytes)) {
+        Ok(..) => {}
         Err(e) => {
             cx.span_err(sp,
                         &format!("couldn't read {}: {}",
@@ -145,7 +149,6 @@ pub fn expand_include_str(cx: &mut ExtCtxt, sp: Span, tts: &[ast::TokenTree])
                                 e));
             return DummyResult::expr(sp);
         }
-        Ok(bytes) => bytes,
     };
     match String::from_utf8(bytes) {
         Ok(src) => {
@@ -172,15 +175,15 @@ pub fn expand_include_bytes(cx: &mut ExtCtxt, sp: Span, tts: &[ast::TokenTree])
         Some(f) => f,
         None => return DummyResult::expr(sp)
     };
-    let file = res_rel_file(cx, sp, &Path::new(file));
-    match File::open(&file).read_to_end() {
+    let file = res_rel_file(cx, sp, Path::new(&file));
+    let mut bytes = Vec::new();
+    match File::open(&file).and_then(|mut f| f.read_to_end(&mut bytes)) {
         Err(e) => {
             cx.span_err(sp,
                         &format!("couldn't read {}: {}", file.display(), e));
             return DummyResult::expr(sp);
         }
-        Ok(bytes) => {
-            let bytes = bytes.iter().cloned().collect();
+        Ok(..) => {
             base::MacEager::expr(cx.expr_lit(sp, ast::LitBinary(Rc::new(bytes))))
         }
     }
@@ -188,14 +191,18 @@ pub fn expand_include_bytes(cx: &mut ExtCtxt, sp: Span, tts: &[ast::TokenTree])
 
 // resolve a file-system path to an absolute file-system path (if it
 // isn't already)
-fn res_rel_file(cx: &mut ExtCtxt, sp: codemap::Span, arg: &Path) -> Path {
+fn res_rel_file(cx: &mut ExtCtxt, sp: codemap::Span, arg: &Path) -> PathBuf {
     // NB: relative paths are resolved relative to the compilation unit
     if !arg.is_absolute() {
-        let mut cu = Path::new(cx.codemap().span_to_filename(sp));
-        cu.pop();
+        let mut cu = PathBuf::new(&cx.codemap().span_to_filename(sp));
+        if cu.parent().is_some() {
+            cu.pop();
+        } else {
+            cu = PathBuf::new("");
+        }
         cu.push(arg);
         cu
     } else {
-        arg.clone()
+        arg.to_path_buf()
     }
 }
index ce513bc91f5a998fda321bb638b4a68bbd0d926c..eb15d708232a097c5572a8c92117601ce0e5ac03 100644 (file)
@@ -243,12 +243,15 @@ fn n_rec(p_s: &ParseSess, m: &TokenTree, res: &[Rc<NamedMatch>],
     ret_val
 }
 
-pub enum ParseResult {
-    Success(HashMap<Ident, Rc<NamedMatch>>),
+pub enum ParseResult<T> {
+    Success(T),
     Failure(codemap::Span, String),
     Error(codemap::Span, String)
 }
 
+pub type NamedParseResult = ParseResult<HashMap<Ident, Rc<NamedMatch>>>;
+pub type PositionalParseResult = ParseResult<Vec<Rc<NamedMatch>>>;
+
 pub fn parse_or_else(sess: &ParseSess,
                      cfg: ast::CrateConfig,
                      rdr: TtReader,
@@ -280,7 +283,7 @@ pub fn parse(sess: &ParseSess,
              cfg: ast::CrateConfig,
              mut rdr: TtReader,
              ms: &[TokenTree])
-             -> ParseResult {
+             -> NamedParseResult {
     let mut cur_eis = Vec::new();
     cur_eis.push(initial_matcher_pos(Rc::new(ms.iter()
                                                 .cloned()
@@ -479,7 +482,7 @@ pub fn parse(sess: &ParseSess,
                 }
                 rdr.next_token();
             } else /* bb_eis.len() == 1 */ {
-                let mut rust_parser = Parser::new(sess, cfg.clone(), box rdr.clone());
+                let mut rust_parser = Parser::new(sess, cfg.clone(), Box::new(rdr.clone()));
 
                 let mut ei = bb_eis.pop().unwrap();
                 match ei.top_elts.get_tt(ei.idx) {
index 67011ad21a6dd8eec7111f7c07929e9664a0f7ce..644c6cd7e2833f60c9ff8f4350d306a35eec2355 100644 (file)
@@ -15,7 +15,7 @@
 use ext::tt::macro_parser::{Success, Error, Failure};
 use ext::tt::macro_parser::{NamedMatch, MatchedSeq, MatchedNonterminal};
 use ext::tt::macro_parser::{parse, parse_or_else};
-use parse::lexer::{new_tt_reader, new_tt_reader_with_doc_flag};
+use parse::lexer::new_tt_reader;
 use parse::parser::Parser;
 use parse::attr::ParserAttr;
 use parse::token::{self, special_idents, gensym_ident, NtTT, Token};
@@ -154,15 +154,8 @@ fn generic_extension<'cx>(cx: &'cx ExtCtxt,
                 TtDelimited(_, ref delim) => &delim.tts[..],
                 _ => cx.span_fatal(sp, "malformed macro lhs")
             };
-            // `None` is because we're not interpolating
-            let arg_rdr = new_tt_reader_with_doc_flag(&cx.parse_sess().span_diagnostic,
-                                                      None,
-                                                      None,
-                                                      arg.iter()
-                                                         .cloned()
-                                                         .collect(),
-                                                      true);
-            match parse(cx.parse_sess(), cx.cfg(), arg_rdr, lhs_tt) {
+
+            match TokenTree::parse(cx, lhs_tt, arg) {
               Success(named_matches) => {
                 let rhs = match *rhses[i] {
                     // okay, what's your transcriber?
@@ -180,7 +173,7 @@ fn generic_extension<'cx>(cx: &'cx ExtCtxt,
                                            Some(named_matches),
                                            imported_from,
                                            rhs);
-                let mut p = Parser::new(cx.parse_sess(), cx.cfg(), box trncbr);
+                let mut p = Parser::new(cx.parse_sess(), cx.cfg(), Box::new(trncbr));
                 p.check_unknown_macro_variable();
                 // Let the context choose how to interpret the result.
                 // Weird, but useful for X-macros.
@@ -267,14 +260,14 @@ pub fn compile<'cx>(cx: &'cx mut ExtCtxt,
         _ => cx.span_bug(def.span, "wrong-structured rhs")
     };
 
-    let exp = box MacroRulesMacroExpander {
+    let exp: Box<_> = box MacroRulesMacroExpander {
         name: def.ident,
         imported_from: def.imported_from,
         lhses: lhses,
         rhses: rhses,
     };
 
-    NormalTT(exp, Some(def.span))
+    NormalTT(exp, Some(def.span), def.allow_internal_unstable)
 }
 
 fn check_lhs_nt_follows(cx: &mut ExtCtxt, lhs: &NamedMatch, sp: Span) {
index ffc136d5a1d1a19b41bab604f7774b2e8fabfb54..c3bac0cf57c758cb8921f9f5185462db8b9a7b63 100644 (file)
@@ -45,7 +45,7 @@
 // stable (active).
 // NB: The featureck.py script parses this information directly out of the source
 // so take care when modifying it.
-static KNOWN_FEATURES: &'static [(&'static str, &'static str, Status)] = &[
+const KNOWN_FEATURES: &'static [(&'static str, &'static str, Status)] = &[
     ("globs", "1.0.0", Accepted),
     ("macro_rules", "1.0.0", Accepted),
     ("struct_variant", "1.0.0", Accepted),
     // Allows the use of custom attributes; RFC 572
     ("custom_attribute", "1.0.0", Active),
 
+    // Allows the use of #[derive(Anything)] as sugar for
+    // #[derive_Anything].
+    ("custom_derive", "1.0.0", Active),
+
     // Allows the use of rustc_* attributes; RFC 572
     ("rustc_attrs", "1.0.0", Active),
+
+    // Allows the use of `static_assert`
+    ("static_assert", "1.0.0", Active),
+
+    // Allows the use of #[allow_internal_unstable]. This is an
+    // attribute on macro_rules! and can't use the attribute handling
+    // below (it has to be checked before expansion possibly makes
+    // macros disappear).
+    ("allow_internal_unstable", "1.0.0", Active),
 ];
 // (changing above list without updating src/doc/reference.md makes @cmr sad)
 
@@ -159,7 +172,7 @@ enum Status {
 }
 
 // Attributes that have a special meaning to rustc or rustdoc
-pub static KNOWN_ATTRIBUTES: &'static [(&'static str, AttributeType)] = &[
+pub const KNOWN_ATTRIBUTES: &'static [(&'static str, AttributeType)] = &[
     // Normal attributes
 
     ("warn", Normal),
@@ -173,6 +186,7 @@ enum Status {
     ("plugin_registrar", Normal),
 
     ("cfg", Normal),
+    ("cfg_attr", Normal),
     ("main", Normal),
     ("start", Normal),
     ("test", Normal),
@@ -186,6 +200,7 @@ enum Status {
     ("no_mangle", Normal),
     ("no_link", Normal),
     ("derive", Normal),
+    ("deriving", Normal), // deprecation err in expansion
     ("should_fail", Normal),
     ("should_panic", Normal),
     ("ignore", Normal),
@@ -225,6 +240,9 @@ enum Status {
                                    "the `#[rustc_move_fragments]` attribute \
                                     is an experimental feature")),
 
+    ("allow_internal_unstable", Gated("allow_internal_unstable",
+                                      EXPLAIN_ALLOW_INTERNAL_UNSTABLE)),
+
     // FIXME: #14408 whitelist docs since rustdoc looks at them
     ("doc", Whitelisted),
 
@@ -241,7 +259,8 @@ enum Status {
     ("no_split_stack", Whitelisted),
     ("no_stack_check", Whitelisted),
     ("packed", Whitelisted),
-    ("static_assert", Whitelisted),
+    ("static_assert", Gated("static_assert",
+                            "`#[static_assert]` is an experimental feature, and has a poor API")),
     ("no_debug", Whitelisted),
     ("omit_gdb_pretty_printer_section", Whitelisted),
     ("unsafe_no_drop_flag", Gated("unsafe_no_drop_flag",
@@ -274,7 +293,7 @@ enum Status {
     ("recursion_limit", CrateLevel),
 ];
 
-#[derive(PartialEq, Copy)]
+#[derive(PartialEq, Copy, Debug)]
 pub enum AttributeType {
     /// Normal, builtin attribute that is consumed
     /// by the compiler before the unused_attribute check
@@ -303,6 +322,8 @@ pub struct Features {
     pub allow_log_syntax: bool,
     pub allow_concat_idents: bool,
     pub allow_trace_macros: bool,
+    pub allow_internal_unstable: bool,
+    pub allow_custom_derive: bool,
     pub old_orphan_check: bool,
     pub simd_ffi: bool,
     pub unmarked_api: bool,
@@ -323,6 +344,8 @@ pub fn new() -> Features {
             allow_log_syntax: false,
             allow_concat_idents: false,
             allow_trace_macros: false,
+            allow_internal_unstable: false,
+            allow_custom_derive: false,
             old_orphan_check: false,
             simd_ffi: false,
             unmarked_api: false,
@@ -336,28 +359,62 @@ struct Context<'a> {
     features: Vec<&'static str>,
     span_handler: &'a SpanHandler,
     cm: &'a CodeMap,
+    do_warnings: bool,
 }
 
 impl<'a> Context<'a> {
     fn gate_feature(&self, feature: &str, span: Span, explain: &str) {
-        if !self.has_feature(feature) {
+        let has_feature = self.has_feature(feature);
+        debug!("gate_feature(feature = {:?}, span = {:?}); has? {}", feature, span, has_feature);
+        if !has_feature {
             emit_feature_err(self.span_handler, feature, span, explain);
         }
     }
 
     fn warn_feature(&self, feature: &str, span: Span, explain: &str) {
-        if !self.has_feature(feature) {
+        if !self.has_feature(feature) && self.do_warnings {
             emit_feature_warn(self.span_handler, feature, span, explain);
         }
     }
     fn has_feature(&self, feature: &str) -> bool {
         self.features.iter().any(|&n| n == feature)
     }
+
+    fn check_attribute(&self, attr: &ast::Attribute) {
+        debug!("check_attribute(attr = {:?})", attr);
+        let name = &*attr.name();
+        for &(n, ty) in KNOWN_ATTRIBUTES {
+            if n == name {
+                if let Gated(gate, desc) = ty {
+                    self.gate_feature(gate, attr.span, desc);
+                }
+                debug!("check_attribute: {:?} is known, {:?}", name, ty);
+                return;
+            }
+        }
+        if name.starts_with("rustc_") {
+            self.gate_feature("rustc_attrs", attr.span,
+                              "unless otherwise specified, attributes \
+                               with the prefix `rustc_` \
+                               are reserved for internal compiler diagnostics");
+        } else if name.starts_with("derive_") {
+            self.gate_feature("custom_derive", attr.span,
+                              "attributes of the form `#[derive_*]` are reserved
+                               for the compiler");
+        } else {
+            self.gate_feature("custom_attribute", attr.span,
+                       &format!("The attribute `{}` is currently \
+                                unknown to the the compiler and \
+                                may have meaning \
+                                added to it in the future",
+                                name));
+        }
+    }
 }
 
 pub fn emit_feature_err(diag: &SpanHandler, feature: &str, span: Span, explain: &str) {
     diag.span_err(span, explain);
-    diag.span_help(span, &format!("add #![feature({})] to the \
+    diag.fileline_help(span, &format!("add #![feature({})] to the \
                                    crate attributes to enable",
                                   feature));
 }
@@ -365,7 +422,7 @@ pub fn emit_feature_err(diag: &SpanHandler, feature: &str, span: Span, explain:
 pub fn emit_feature_warn(diag: &SpanHandler, feature: &str, span: Span, explain: &str) {
     diag.span_warn(span, explain);
     if diag.handler.can_emit_warnings {
-        diag.span_help(span, &format!("add #![feature({})] to the \
+        diag.fileline_help(span, &format!("add #![feature({})] to the \
                                        crate attributes to silence this warning",
                                       feature));
     }
@@ -382,6 +439,11 @@ pub fn emit_feature_warn(diag: &SpanHandler, feature: &str, span: Span, explain:
 
 pub const EXPLAIN_TRACE_MACROS: &'static str =
     "`trace_macros` is not stable enough for use and is subject to change";
+pub const EXPLAIN_ALLOW_INTERNAL_UNSTABLE: &'static str =
+    "allow_internal_unstable side-steps feature gating and stability checks";
+
+pub const EXPLAIN_CUSTOM_DERIVE: &'static str =
+    "`#[derive]` for custom traits is not stable enough for use and is subject to change";
 
 struct MacroVisitor<'a> {
     context: &'a Context<'a>
@@ -416,6 +478,10 @@ fn visit_mac(&mut self, mac: &ast::Mac) {
             self.context.gate_feature("concat_idents", path.span, EXPLAIN_CONCAT_IDENTS);
         }
     }
+
+    fn visit_attribute(&mut self, attr: &'v ast::Attribute) {
+        self.context.check_attribute(attr);
+    }
 }
 
 struct PostExpansionVisitor<'a> {
@@ -424,13 +490,19 @@ struct PostExpansionVisitor<'a> {
 
 impl<'a> PostExpansionVisitor<'a> {
     fn gate_feature(&self, feature: &str, span: Span, explain: &str) {
-        if !self.context.cm.span_is_internal(span) {
+        if !self.context.cm.span_allows_unstable(span) {
             self.context.gate_feature(feature, span, explain)
         }
     }
 }
 
 impl<'a, 'v> Visitor<'v> for PostExpansionVisitor<'a> {
+    fn visit_attribute(&mut self, attr: &ast::Attribute) {
+        if !self.context.cm.span_allows_unstable(attr.span) {
+            self.context.check_attribute(attr);
+        }
+    }
+
     fn visit_name(&mut self, sp: Span, name: ast::Name) {
         if !token::get_name(name).is_ascii() {
             self.gate_feature("non_ascii_idents", sp,
@@ -531,12 +603,6 @@ fn visit_item(&mut self, i: &ast::Item) {
     }
 
     fn visit_foreign_item(&mut self, i: &ast::ForeignItem) {
-        if attr::contains_name(&i.attrs, "linkage") {
-            self.gate_feature("linkage", i.span,
-                              "the `linkage` attribute is experimental \
-                               and not portable across platforms")
-        }
-
         let links_to_llvm = match attr::first_attr_value_str_by_name(&i.attrs,
                                                                      "link_name") {
             Some(val) => val.starts_with("llvm."),
@@ -611,31 +677,6 @@ fn visit_expr(&mut self, e: &ast::Expr) {
         visit::walk_expr(self, e);
     }
 
-    fn visit_attribute(&mut self, attr: &ast::Attribute) {
-        let name = &*attr.name();
-        for &(n, ty) in KNOWN_ATTRIBUTES {
-            if n == name {
-                if let Gated(gate, desc) = ty {
-                    self.gate_feature(gate, attr.span, desc);
-                }
-                return;
-            }
-        }
-        if name.starts_with("rustc_") {
-            self.gate_feature("rustc_attrs", attr.span,
-                              "unless otherwise specified, attributes \
-                               with the prefix `rustc_` \
-                               are reserved for internal compiler diagnostics");
-        } else {
-            self.gate_feature("custom_attribute", attr.span,
-                       format!("The attribute `{}` is currently \
-                                unknown to the the compiler and \
-                                may have meaning \
-                                added to it in the future",
-                                name).as_slice());
-        }
-    }
-
     fn visit_pat(&mut self, pattern: &ast::Pat) {
         match pattern.node {
             ast::PatVec(_, Some(_), ref last) if !last.is_empty() => {
@@ -674,6 +715,7 @@ fn visit_fn(&mut self,
 }
 
 fn check_crate_inner<F>(cm: &CodeMap, span_handler: &SpanHandler, krate: &ast::Crate,
+                        do_warnings: bool,
                         check: F)
                        -> Features
     where F: FnOnce(&mut Context, &ast::Crate)
@@ -681,6 +723,7 @@ fn check_crate_inner<F>(cm: &CodeMap, span_handler: &SpanHandler, krate: &ast::C
     let mut cx = Context {
         features: Vec::new(),
         span_handler: span_handler,
+        do_warnings: do_warnings,
         cm: cm,
     };
 
@@ -749,6 +792,8 @@ fn check_crate_inner<F>(cm: &CodeMap, span_handler: &SpanHandler, krate: &ast::C
         allow_log_syntax: cx.has_feature("log_syntax"),
         allow_concat_idents: cx.has_feature("concat_idents"),
         allow_trace_macros: cx.has_feature("trace_macros"),
+        allow_internal_unstable: cx.has_feature("allow_internal_unstable"),
+        allow_custom_derive: cx.has_feature("custom_derive"),
         old_orphan_check: cx.has_feature("old_orphan_check"),
         simd_ffi: cx.has_feature("simd_ffi"),
         unmarked_api: cx.has_feature("unmarked_api"),
@@ -759,14 +804,14 @@ fn check_crate_inner<F>(cm: &CodeMap, span_handler: &SpanHandler, krate: &ast::C
 
 pub fn check_crate_macros(cm: &CodeMap, span_handler: &SpanHandler, krate: &ast::Crate)
 -> Features {
-    check_crate_inner(cm, span_handler, krate,
+    check_crate_inner(cm, span_handler, krate, true,
                       |ctx, krate| visit::walk_crate(&mut MacroVisitor { context: ctx }, krate))
 }
 
-pub fn check_crate(cm: &CodeMap, span_handler: &SpanHandler, krate: &ast::Crate)
--> Features {
-    check_crate_inner(cm, span_handler, krate,
+pub fn check_crate(cm: &CodeMap, span_handler: &SpanHandler, krate: &ast::Crate,
+                   do_warnings: bool) -> Features
+{
+    check_crate_inner(cm, span_handler, krate, do_warnings,
                       |ctx, krate| visit::walk_crate(&mut PostExpansionVisitor { context: ctx },
                                                      krate))
 }
-
index a556b2dfd2a99a88104844817f329d13a9f6669e..959e3bdb31476afab4b4065226d41b40d03cc4ca 100644 (file)
@@ -1432,7 +1432,7 @@ pub fn noop_fold_stmt<T: Folder>(Spanned {node, span}: Stmt, folder: &mut T)
 
 #[cfg(test)]
 mod test {
-    use std::old_io;
+    use std::io;
     use ast;
     use util::parser_testing::{string_to_crate, matches_codepattern};
     use parse::token;
@@ -1442,7 +1442,7 @@ mod test {
 
     // this version doesn't care about getting comments or docstrings in.
     fn fake_print_crate(s: &mut pprust::State,
-                        krate: &ast::Crate) -> old_io::IoResult<()> {
+                        krate: &ast::Crate) -> io::Result<()> {
         s.print_mod(&krate.module, &krate.attrs)
     }
 
index 7acbd10ef03d818476adbcde6be57f32121c134c..ba3f495cdaced73c40188a8b3abff820fcb08229 100644 (file)
@@ -14,6 +14,8 @@
 //!
 //! This API is completely unstable and subject to change.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "syntax"]
 #![unstable(feature = "rustc_private")]
 #![staged_api]
@@ -36,6 +38,9 @@
 #![feature(staged_api)]
 #![feature(std_misc)]
 #![feature(unicode)]
+#![feature(path)]
+#![feature(io)]
+#![feature(path_ext)]
 
 extern crate arena;
 extern crate fmt_macros;
index f5201d4a8bc68f73ea9f46c07e6bca61330a561e..25f1f9b8480a1204d71129325688b6f1d43c72be 100644 (file)
@@ -30,7 +30,7 @@ fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
 
 impl<T> OwnedSlice<T> {
     pub fn empty() -> OwnedSlice<T> {
-        OwnedSlice  { data: box [] }
+        OwnedSlice  { data: Box::new([]) }
     }
 
     #[inline(never)]
index a0e2b4dbf5a70bae65ede6b0efb4c520ac2a8f1e..db5583cf13ac193e119436b1c9ca512f798272c6 100644 (file)
@@ -77,7 +77,7 @@ fn parse_attribute(&mut self, permit_inner: bool) -> ast::Attribute {
                         self.span_err(span,
                                       "an inner attribute is not permitted in \
                                        this context");
-                        self.span_help(span,
+                        self.fileline_help(span,
                                        "place inner attribute at the top of the module or block");
                     }
                     ast::AttrInner
index 7a5d75581a511447cf5cd4c16950f2c80dadaf38..fb9e0480cebc8b8acdbfdf31691b6ac56bc1de3a 100644 (file)
@@ -19,9 +19,8 @@
 use parse::lexer;
 use print::pprust;
 
-use std::old_io;
+use std::io::Read;
 use std::str;
-use std::string::String;
 use std::usize;
 
 #[derive(Clone, Copy, PartialEq)]
@@ -124,8 +123,8 @@ fn horizontal_trim(lines: Vec<String> ) -> Vec<String> {
     }
 
     // one-line comments lose their prefix
-    static ONLINERS: &'static [&'static str] = &["///!", "///", "//!", "//"];
-    for prefix in ONLINERS {
+    const ONELINERS: &'static [&'static str] = &["///!", "///", "//!", "//"];
+    for prefix in ONELINERS {
         if comment.starts_with(*prefix) {
             return (&comment[prefix.len()..]).to_string();
         }
@@ -337,9 +336,10 @@ pub struct Literal {
 // probably not a good thing.
 pub fn gather_comments_and_literals(span_diagnostic: &diagnostic::SpanHandler,
                                     path: String,
-                                    srdr: &mut old_io::Reader)
+                                    srdr: &mut Read)
                                  -> (Vec<Comment>, Vec<Literal>) {
-    let src = srdr.read_to_end().unwrap();
+    let mut src = Vec::new();
+    srdr.read_to_end(&mut src).unwrap();
     let src = String::from_utf8(src).unwrap();
     let cm = CodeMap::new();
     let filemap = cm.new_filemap(path, src);
index 83d2bb0cc70a9b542572ab7ddd6f86a16e80f68c..f5781e0587d245f7d5c6a404a9d634e97a414c3f 100644 (file)
@@ -76,6 +76,10 @@ pub struct StringReader<'a> {
     // are revised to go directly to token-trees.
     /// Is \x00<name>,<ctxt>\x00 is interpreted as encoded ast::Ident?
     read_embedded_ident: bool,
+
+    // cache a direct reference to the source text, so that we don't have to
+    // retrieve it via `self.filemap.src.as_ref().unwrap()` all the time.
+    source_text: Rc<String>
 }
 
 impl<'a> Reader for StringReader<'a> {
@@ -141,7 +145,14 @@ pub fn make_reader_with_embedded_idents<'b>(span_diagnostic: &'b SpanHandler,
 impl<'a> StringReader<'a> {
     /// For comments.rs, which hackily pokes into pos and curr
     pub fn new_raw<'b>(span_diagnostic: &'b SpanHandler,
-                   filemap: Rc<codemap::FileMap>) -> StringReader<'b> {
+                       filemap: Rc<codemap::FileMap>) -> StringReader<'b> {
+        if filemap.src.is_none() {
+            span_diagnostic.handler.bug(&format!("Cannot lex filemap without source: {}",
+                                                 filemap.name)[..]);
+        }
+
+        let source_text = (*filemap.src.as_ref().unwrap()).clone();
+
         let mut sr = StringReader {
             span_diagnostic: span_diagnostic,
             pos: filemap.start_pos,
@@ -153,6 +164,7 @@ pub fn new_raw<'b>(span_diagnostic: &'b SpanHandler,
             peek_tok: token::Eof,
             peek_span: codemap::DUMMY_SP,
             read_embedded_ident: false,
+            source_text: source_text
         };
         sr.bump();
         sr
@@ -213,7 +225,7 @@ fn fatal_span_verbose(&self, from_pos: BytePos, to_pos: BytePos, mut m: String)
         m.push_str(": ");
         let from = self.byte_offset(from_pos).to_usize();
         let to = self.byte_offset(to_pos).to_usize();
-        m.push_str(&self.filemap.src[from..to]);
+        m.push_str(&self.source_text[from..to]);
         self.fatal_span_(from_pos, to_pos, &m[..]);
     }
 
@@ -270,9 +282,8 @@ pub fn name_from_to(&self, start: BytePos, end: BytePos) -> ast::Name {
     fn with_str_from_to<T, F>(&self, start: BytePos, end: BytePos, f: F) -> T where
         F: FnOnce(&str) -> T,
     {
-        f(&self.filemap.src[
-                self.byte_offset(start).to_usize()..
-                self.byte_offset(end).to_usize()])
+        f(&self.source_text[self.byte_offset(start).to_usize()..
+                            self.byte_offset(end).to_usize()])
     }
 
     /// Converts CRLF to LF in the given string, raising an error on bare CR.
@@ -321,12 +332,10 @@ fn translate_crlf_(rdr: &StringReader, start: BytePos,
     pub fn bump(&mut self) {
         self.last_pos = self.pos;
         let current_byte_offset = self.byte_offset(self.pos).to_usize();
-        if current_byte_offset < self.filemap.src.len() {
+        if current_byte_offset < self.source_text.len() {
             assert!(self.curr.is_some());
             let last_char = self.curr.unwrap();
-            let next = self.filemap
-                          .src
-                          .char_range_at(current_byte_offset);
+            let next = self.source_text.char_range_at(current_byte_offset);
             let byte_offset_diff = next.next - current_byte_offset;
             self.pos = self.pos + Pos::from_usize(byte_offset_diff);
             self.curr = Some(next.ch);
@@ -346,8 +355,8 @@ pub fn bump(&mut self) {
 
     pub fn nextch(&self) -> Option<char> {
         let offset = self.byte_offset(self.pos).to_usize();
-        if offset < self.filemap.src.len() {
-            Some(self.filemap.src.char_at(offset))
+        if offset < self.source_text.len() {
+            Some(self.source_text.char_at(offset))
         } else {
             None
         }
@@ -359,7 +368,7 @@ pub fn nextch_is(&self, c: char) -> bool {
 
     pub fn nextnextch(&self) -> Option<char> {
         let offset = self.byte_offset(self.pos).to_usize();
-        let s = &*self.filemap.src;
+        let s = &self.source_text[..];
         if offset >= s.len() { return None }
         let str::CharRange { next, .. } = s.char_range_at(offset);
         if next < s.len() {
@@ -768,13 +777,6 @@ fn scan_hex_digits(&mut self,
         }
     }
 
-    fn old_escape_warning(&mut self, sp: Span) {
-        self.span_diagnostic
-            .span_warn(sp, "\\U00ABCD12 and \\uABCD escapes are deprecated");
-        self.span_diagnostic
-            .span_help(sp, "use \\u{ABCD12} escapes instead");
-    }
-
     /// Scan for a single (possibly escaped) byte or char
     /// in a byte, (non-raw) byte string, char, or (non-raw) string literal.
     /// `start` is the position of `first_source_char`, which is already consumed.
@@ -794,21 +796,8 @@ fn scan_char_or_byte(&mut self, start: BytePos, first_source_char: char,
                         return match e {
                             'n' | 'r' | 't' | '\\' | '\'' | '"' | '0' => true,
                             'x' => self.scan_byte_escape(delim, !ascii_only),
-                            'u' if !ascii_only => {
-                                if self.curr == Some('{') {
-                                    self.scan_unicode_escape(delim)
-                                } else {
-                                    let res = self.scan_hex_digits(4, delim, false);
-                                    let sp = codemap::mk_sp(escaped_pos, self.last_pos);
-                                    self.old_escape_warning(sp);
-                                    res
-                                }
-                            }
-                            'U' if !ascii_only => {
-                                let res = self.scan_hex_digits(8, delim, false);
-                                let sp = codemap::mk_sp(escaped_pos, self.last_pos);
-                                self.old_escape_warning(sp);
-                                res
+                            'u' if self.curr_is('{') => {
+                                self.scan_unicode_escape(delim)
                             }
                             '\n' if delim == '"' => {
                                 self.consume_whitespace();
@@ -1484,8 +1473,9 @@ mod test {
     use std::old_io::util;
 
     fn mk_sh() -> diagnostic::SpanHandler {
-        let emitter = diagnostic::EmitterWriter::new(box util::NullWriter, None);
-        let handler = diagnostic::mk_handler(true, box emitter);
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        let emitter = diagnostic::EmitterWriter::new(Box::new(util::NullWriter), None);
+        let handler = diagnostic::mk_handler(true, Box::new(emitter));
         diagnostic::mk_span_handler(handler, CodeMap::new())
     }
 
index 4d099529cb49ae50439b15fe1b3a03142d419af8..fae305f955174241d46b018609fbfd5a521c50f2 100644 (file)
 use ptr::P;
 
 use std::cell::{Cell, RefCell};
-use std::old_io::File;
-use std::rc::Rc;
+use std::fs::File;
+use std::io::Read;
+use std::iter;
 use std::num::Int;
+use std::path::{Path, PathBuf};
+use std::rc::Rc;
 use std::str;
-use std::iter;
 
 #[macro_use]
 pub mod parser;
@@ -39,7 +41,7 @@
 pub struct ParseSess {
     pub span_diagnostic: SpanHandler, // better be the same as the one in the reader!
     /// Used to determine and report recursive mod inclusions
-    included_mod_stack: RefCell<Vec<Path>>,
+    included_mod_stack: RefCell<Vec<PathBuf>>,
     pub node_id: Cell<ast::NodeId>,
 }
 
@@ -250,24 +252,24 @@ pub fn file_to_filemap(sess: &ParseSess, path: &Path, spanopt: Option<Span>)
             None => sess.span_diagnostic.handler().fatal(msg),
         }
     };
-    let bytes = match File::open(path).read_to_end() {
-        Ok(bytes) => bytes,
+    let mut bytes = Vec::new();
+    match File::open(path).and_then(|mut f| f.read_to_end(&mut bytes)) {
+        Ok(..) => {}
         Err(e) => {
-            err(&format!("couldn't read {:?}: {}",
-                        path.display(), e));
-            unreachable!()
+            err(&format!("couldn't read {:?}: {}", path.display(), e));
+            unreachable!();
         }
     };
     match str::from_utf8(&bytes[..]).ok() {
         Some(s) => {
-            return string_to_filemap(sess, s.to_string(),
-                                     path.as_str().unwrap().to_string())
+            string_to_filemap(sess, s.to_string(),
+                              path.to_str().unwrap().to_string())
         }
         None => {
-            err(&format!("{:?} is not UTF-8 encoded", path.display()))
+            err(&format!("{:?} is not UTF-8 encoded", path.display()));
+            unreachable!();
         }
     }
-    unreachable!()
 }
 
 /// Given a session and a string, add the string to
@@ -722,7 +724,7 @@ pub fn integer_lit(s: &str, suffix: Option<&str>, sd: &SpanHandler, sp: Span) ->
                                               &suf[1..]));
                 } else {
                     sd.span_err(sp, &*format!("illegal suffix `{}` for numeric literal", suf));
-                    sd.span_help(sp, "the suffix must be one of the integral types \
+                    sd.fileline_help(sp, "the suffix must be one of the integral types \
                                       (`u32`, `isize`, etc)");
                 }
 
@@ -751,6 +753,7 @@ pub fn integer_lit(s: &str, suffix: Option<&str>, sd: &SpanHandler, sp: Span) ->
 #[cfg(test)]
 mod test {
     use super::*;
+    use std::rc::Rc;
     use serialize::json;
     use codemap::{Span, BytePos, Pos, Spanned, NO_EXPANSION};
     use owned_slice::OwnedSlice;
@@ -810,7 +813,7 @@ fn sp(a: u32, b: u32) -> Span {
                    }))
     }
 
-    #[should_fail]
+    #[should_panic]
     #[test] fn bad_path_expr_1() {
         string_to_expr("::abc::def::return".to_string());
     }
@@ -855,117 +858,50 @@ fn string_to_tts_macro () {
     }
 
     #[test]
-    fn string_to_tts_1 () {
+    fn string_to_tts_1() {
         let tts = string_to_tts("fn a (b : i32) { b; }".to_string());
-        assert_eq!(json::encode(&tts).unwrap(),
-        "[\
-    {\
-        \"variant\":\"TtToken\",\
-        \"fields\":[\
-            null,\
-            {\
-                \"variant\":\"Ident\",\
-                \"fields\":[\
-                    \"fn\",\
-                    \"Plain\"\
-                ]\
-            }\
-        ]\
-    },\
-    {\
-        \"variant\":\"TtToken\",\
-        \"fields\":[\
-            null,\
-            {\
-                \"variant\":\"Ident\",\
-                \"fields\":[\
-                    \"a\",\
-                    \"Plain\"\
-                ]\
-            }\
-        ]\
-    },\
-    {\
-        \"variant\":\"TtDelimited\",\
-        \"fields\":[\
-            null,\
-            {\
-                \"delim\":\"Paren\",\
-                \"open_span\":null,\
-                \"tts\":[\
-                    {\
-                        \"variant\":\"TtToken\",\
-                        \"fields\":[\
-                            null,\
-                            {\
-                                \"variant\":\"Ident\",\
-                                \"fields\":[\
-                                    \"b\",\
-                                    \"Plain\"\
-                                ]\
-                            }\
-                        ]\
-                    },\
-                    {\
-                        \"variant\":\"TtToken\",\
-                        \"fields\":[\
-                            null,\
-                            \"Colon\"\
-                        ]\
-                    },\
-                    {\
-                        \"variant\":\"TtToken\",\
-                        \"fields\":[\
-                            null,\
-                            {\
-                                \"variant\":\"Ident\",\
-                                \"fields\":[\
-                                    \"i32\",\
-                                    \"Plain\"\
-                                ]\
-                            }\
-                        ]\
-                    }\
-                ],\
-                \"close_span\":null\
-            }\
-        ]\
-    },\
-    {\
-        \"variant\":\"TtDelimited\",\
-        \"fields\":[\
-            null,\
-            {\
-                \"delim\":\"Brace\",\
-                \"open_span\":null,\
-                \"tts\":[\
-                    {\
-                        \"variant\":\"TtToken\",\
-                        \"fields\":[\
-                            null,\
-                            {\
-                                \"variant\":\"Ident\",\
-                                \"fields\":[\
-                                    \"b\",\
-                                    \"Plain\"\
-                                ]\
-                            }\
-                        ]\
-                    },\
-                    {\
-                        \"variant\":\"TtToken\",\
-                        \"fields\":[\
-                            null,\
-                            \"Semi\"\
-                        ]\
-                    }\
-                ],\
-                \"close_span\":null\
-            }\
-        ]\
-    }\
-]"
-        );
+
+        let expected = vec![
+            ast::TtToken(sp(0, 2),
+                         token::Ident(str_to_ident("fn"),
+                         token::IdentStyle::Plain)),
+            ast::TtToken(sp(3, 4),
+                         token::Ident(str_to_ident("a"),
+                         token::IdentStyle::Plain)),
+            ast::TtDelimited(
+                sp(5, 14),
+                Rc::new(ast::Delimited {
+                    delim: token::DelimToken::Paren,
+                    open_span: sp(5, 6),
+                    tts: vec![
+                        ast::TtToken(sp(6, 7),
+                                     token::Ident(str_to_ident("b"),
+                                     token::IdentStyle::Plain)),
+                        ast::TtToken(sp(8, 9),
+                                     token::Colon),
+                        ast::TtToken(sp(10, 13),
+                                     token::Ident(str_to_ident("i32"),
+                                     token::IdentStyle::Plain)),
+                    ],
+                    close_span: sp(13, 14),
+                })),
+            ast::TtDelimited(
+                sp(15, 21),
+                Rc::new(ast::Delimited {
+                    delim: token::DelimToken::Brace,
+                    open_span: sp(15, 16),
+                    tts: vec![
+                        ast::TtToken(sp(17, 18),
+                                     token::Ident(str_to_ident("b"),
+                                     token::IdentStyle::Plain)),
+                        ast::TtToken(sp(18, 19),
+                                     token::Semi)
+                    ],
+                    close_span: sp(20, 21),
+                }))
+        ];
+
+        assert_eq!(tts, expected);
     }
 
     #[test] fn ret_expr() {
index c1acee57cf806805630d305e085a29e01589f00f..28d757e9be96397b2cd7d85771dc941fd0dd1e58 100644 (file)
 use owned_slice::OwnedSlice;
 
 use std::collections::HashSet;
-use std::old_io::fs::PathExtensions;
+use std::io::prelude::*;
 use std::iter;
 use std::mem;
 use std::num::Float;
+use std::path::{Path, PathBuf};
 use std::rc::Rc;
 use std::slice;
 
@@ -973,7 +974,7 @@ pub fn span_fatal(&self, sp: Span, m: &str) -> ! {
     }
     pub fn span_fatal_help(&self, sp: Span, m: &str, help: &str) -> ! {
         self.span_err(sp, m);
-        self.span_help(sp, help);
+        self.fileline_help(sp, help);
         panic!(diagnostic::FatalError);
     }
     pub fn span_note(&self, sp: Span, m: &str) {
@@ -982,6 +983,9 @@ pub fn span_note(&self, sp: Span, m: &str) {
     pub fn span_help(&self, sp: Span, m: &str) {
         self.sess.span_diagnostic.span_help(sp, m)
     }
+    pub fn fileline_help(&self, sp: Span, m: &str) {
+        self.sess.span_diagnostic.fileline_help(sp, m)
+    }
     pub fn bug(&self, m: &str) -> ! {
         self.sess.span_diagnostic.span_bug(self.span, m)
     }
@@ -2531,7 +2535,7 @@ pub fn parse_dot_or_call_expr_with(&mut self, e0: P<Expr>) -> P<Expr> {
                             Some(f) => f,
                             None => continue,
                         };
-                        self.span_help(last_span,
+                        self.fileline_help(last_span,
                             &format!("try parenthesizing the first index; e.g., `(foo.{}){}`",
                                     float.trunc() as usize,
                                     &float.fract().to_string()[1..]));
@@ -2942,7 +2946,7 @@ fn check_no_chained_comparison(&mut self, lhs: &Expr, outer_op: ast::BinOp_) {
                 self.span_err(op_span,
                     "chained comparison operators require parentheses");
                 if op.node == BiLt && outer_op == BiGt {
-                    self.span_help(op_span,
+                    self.fileline_help(op_span,
                         "use `::<...>` instead of `<...>` if you meant to specify type arguments");
                 }
             }
@@ -4698,7 +4702,7 @@ fn complain_if_pub_macro(&mut self, visa: Visibility, span: Span) {
         match visa {
             Public => {
                 self.span_err(span, "can't qualify macro invocation with `pub`");
-                self.span_help(span, "try adjusting the macro to put `pub` inside \
+                self.fileline_help(span, "try adjusting the macro to put `pub` inside \
                                       the invocation");
             }
             Inherited => (),
@@ -5248,14 +5252,23 @@ fn eval_src_mod(&mut self,
                     outer_attrs: &[ast::Attribute],
                     id_sp: Span)
                     -> (ast::Item_, Vec<ast::Attribute> ) {
-        let mut prefix = Path::new(self.sess.span_diagnostic.cm.span_to_filename(self.span));
-        prefix.pop();
-        let mod_path = Path::new(".").join_many(&self.mod_path_stack);
-        let dir_path = prefix.join(&mod_path);
+        let mut prefix = PathBuf::new(&self.sess.span_diagnostic.cm
+                                           .span_to_filename(self.span));
+        // FIXME(acrichto): right now "a".pop() == "a", but need to confirm with
+        //                  aturon whether this is expected or not.
+        if prefix.parent().is_some() {
+            prefix.pop();
+        } else {
+            prefix = PathBuf::new("");
+        }
+        let mut dir_path = prefix;
+        for part in &self.mod_path_stack {
+            dir_path.push(&**part);
+        }
         let mod_string = token::get_ident(id);
         let (file_path, owns_directory) = match ::attr::first_attr_value_str_by_name(
                 outer_attrs, "path") {
-            Some(d) => (dir_path.join(d), true),
+            Some(d) => (dir_path.join(&*d), true),
             None => {
                 let mod_name = mod_string.to_string();
                 let default_path_str = format!("{}.rs", mod_name);
@@ -5319,7 +5332,7 @@ fn eval_src_mod(&mut self,
     }
 
     fn eval_src_mod_from_path(&mut self,
-                              path: Path,
+                              path: PathBuf,
                               owns_directory: bool,
                               name: String,
                               id_sp: Span) -> (ast::Item_, Vec<ast::Attribute> ) {
@@ -5329,10 +5342,10 @@ fn eval_src_mod_from_path(&mut self,
                 let mut err = String::from_str("circular modules: ");
                 let len = included_mod_stack.len();
                 for p in &included_mod_stack[i.. len] {
-                    err.push_str(&p.display().as_cow());
+                    err.push_str(&p.to_string_lossy());
                     err.push_str(" -> ");
                 }
-                err.push_str(&path.display().as_cow());
+                err.push_str(&path.to_string_lossy());
                 self.span_fatal(id_sp, &err[..]);
             }
             None => ()
@@ -5435,7 +5448,7 @@ fn parse_item_extern_crate(&mut self,
                     if self.token.is_ident() { self.bump(); }
 
                     self.span_err(span, "expected `;`, found `as`");
-                    self.span_help(span,
+                    self.fileline_help(span,
                                    &format!("perhaps you meant to enclose the crate name `{}` in \
                                            a string?",
                                           the_ident.as_str()));
@@ -5746,7 +5759,7 @@ fn parse_item_(&mut self, attrs: Vec<Attribute>,
             if self.eat_keyword(keywords::Mut) {
                 let last_span = self.last_span;
                 self.span_err(last_span, "const globals cannot be mutable");
-                self.span_help(last_span, "did you mean to declare a static?");
+                self.fileline_help(last_span, "did you mean to declare a static?");
             }
             let (ident, item_, extra_attrs) = self.parse_item_const(None);
             let last_span = self.last_span;
index 2797ef084d9caf36185d985b3bd46ed437f9b755..61a3a5ca82a326e34bd32721a1c36019115fb374 100644 (file)
@@ -425,10 +425,10 @@ pub mod keywords {
         $( ($rk_name:expr, $rk_variant:ident, $rk_str:expr); )*
     }
 ) => {
-    static STRICT_KEYWORD_START: ast::Name = first!($( ast::Name($sk_name), )*);
-    static STRICT_KEYWORD_FINAL: ast::Name = last!($( ast::Name($sk_name), )*);
-    static RESERVED_KEYWORD_START: ast::Name = first!($( ast::Name($rk_name), )*);
-    static RESERVED_KEYWORD_FINAL: ast::Name = last!($( ast::Name($rk_name), )*);
+    const STRICT_KEYWORD_START: ast::Name = first!($( ast::Name($sk_name), )*);
+    const STRICT_KEYWORD_FINAL: ast::Name = last!($( ast::Name($sk_name), )*);
+    const RESERVED_KEYWORD_START: ast::Name = first!($( ast::Name($rk_name), )*);
+    const RESERVED_KEYWORD_FINAL: ast::Name = last!($( ast::Name($rk_name), )*);
 
     pub mod special_idents {
         use ast;
index 5b3fde8535b3df4dfd1a8a189a722047e0d8e02b..640b7d1c91d503db577ccd3b1bed78392452f759 100644 (file)
@@ -59,7 +59,7 @@
 //! line (which it can't) and so naturally place the content on its own line to
 //! avoid combining it with other lines and making matters even worse.
 
-use std::old_io;
+use std::io;
 use std::string;
 use std::iter::repeat;
 
@@ -159,9 +159,9 @@ pub struct PrintStackElem {
     pbreak: PrintStackBreak
 }
 
-static SIZE_INFINITY: isize = 0xffff;
+const SIZE_INFINITY: isize = 0xffff;
 
-pub fn mk_printer(out: Box<old_io::Writer+'static>, linewidth: usize) -> Printer {
+pub fn mk_printer<'a>(out: Box<io::Write+'a>, linewidth: usize) -> Printer<'a> {
     // Yes 3, it makes the ring buffers big enough to never
     // fall behind.
     let n: usize = 3 * linewidth;
@@ -265,8 +265,8 @@ pub fn mk_printer(out: Box<old_io::Writer+'static>, linewidth: usize) -> Printer
 /// In this implementation (following the paper, again) the SCAN process is
 /// the method called 'pretty_print', and the 'PRINT' process is the method
 /// called 'print'.
-pub struct Printer {
-    pub out: Box<old_io::Writer+'static>,
+pub struct Printer<'a> {
+    pub out: Box<io::Write+'a>,
     buf_len: usize,
     /// Width of lines we're constrained to
     margin: isize,
@@ -303,7 +303,7 @@ pub struct Printer {
     pending_indentation: isize,
 }
 
-impl Printer {
+impl<'a> Printer<'a> {
     pub fn last_token(&mut self) -> Token {
         self.token[self.right].clone()
     }
@@ -311,7 +311,7 @@ pub fn last_token(&mut self) -> Token {
     pub fn replace_last_token(&mut self, t: Token) {
         self.token[self.right] = t;
     }
-    pub fn pretty_print(&mut self, token: Token) -> old_io::IoResult<()> {
+    pub fn pretty_print(&mut self, token: Token) -> io::Result<()> {
         debug!("pp ~[{},{}]", self.left, self.right);
         match token {
           Token::Eof => {
@@ -385,7 +385,7 @@ pub fn pretty_print(&mut self, token: Token) -> old_io::IoResult<()> {
           }
         }
     }
-    pub fn check_stream(&mut self) -> old_io::IoResult<()> {
+    pub fn check_stream(&mut self) -> io::Result<()> {
         debug!("check_stream ~[{}, {}] with left_total={}, right_total={}",
                self.left, self.right, self.left_total, self.right_total);
         if self.right_total - self.left_total > self.space {
@@ -445,7 +445,7 @@ pub fn advance_right(&mut self) {
         self.right %= self.buf_len;
         assert!((self.right != self.left));
     }
-    pub fn advance_left(&mut self) -> old_io::IoResult<()> {
+    pub fn advance_left(&mut self) -> io::Result<()> {
         debug!("advance_left ~[{},{}], sizeof({})={}", self.left, self.right,
                self.left, self.size[self.left]);
 
@@ -506,7 +506,7 @@ pub fn check_stack(&mut self, k: isize) {
             }
         }
     }
-    pub fn print_newline(&mut self, amount: isize) -> old_io::IoResult<()> {
+    pub fn print_newline(&mut self, amount: isize) -> io::Result<()> {
         debug!("NEWLINE {}", amount);
         let ret = write!(self.out, "\n");
         self.pending_indentation = 0;
@@ -529,14 +529,14 @@ pub fn get_top(&mut self) -> PrintStackElem {
             }
         }
     }
-    pub fn print_str(&mut self, s: &str) -> old_io::IoResult<()> {
+    pub fn print_str(&mut self, s: &str) -> io::Result<()> {
         while self.pending_indentation > 0 {
             try!(write!(self.out, " "));
             self.pending_indentation -= 1;
         }
         write!(self.out, "{}", s)
     }
-    pub fn print(&mut self, token: Token, l: isize) -> old_io::IoResult<()> {
+    pub fn print(&mut self, token: Token, l: isize) -> io::Result<()> {
         debug!("print {} {} (remaining line space={})", tok_str(&token), l,
                self.space);
         debug!("{}", buf_str(&self.token,
@@ -620,61 +620,61 @@ pub fn print(&mut self, token: Token, l: isize) -> old_io::IoResult<()> {
 // Convenience functions to talk to the printer.
 //
 // "raw box"
-pub fn rbox(p: &mut Printer, indent: usize, b: Breaks) -> old_io::IoResult<()> {
+pub fn rbox(p: &mut Printer, indent: usize, b: Breaks) -> io::Result<()> {
     p.pretty_print(Token::Begin(BeginToken {
         offset: indent as isize,
         breaks: b
     }))
 }
 
-pub fn ibox(p: &mut Printer, indent: usize) -> old_io::IoResult<()> {
+pub fn ibox(p: &mut Printer, indent: usize) -> io::Result<()> {
     rbox(p, indent, Breaks::Inconsistent)
 }
 
-pub fn cbox(p: &mut Printer, indent: usize) -> old_io::IoResult<()> {
+pub fn cbox(p: &mut Printer, indent: usize) -> io::Result<()> {
     rbox(p, indent, Breaks::Consistent)
 }
 
-pub fn break_offset(p: &mut Printer, n: usize, off: isize) -> old_io::IoResult<()> {
+pub fn break_offset(p: &mut Printer, n: usize, off: isize) -> io::Result<()> {
     p.pretty_print(Token::Break(BreakToken {
         offset: off,
         blank_space: n as isize
     }))
 }
 
-pub fn end(p: &mut Printer) -> old_io::IoResult<()> {
+pub fn end(p: &mut Printer) -> io::Result<()> {
     p.pretty_print(Token::End)
 }
 
-pub fn eof(p: &mut Printer) -> old_io::IoResult<()> {
+pub fn eof(p: &mut Printer) -> io::Result<()> {
     p.pretty_print(Token::Eof)
 }
 
-pub fn word(p: &mut Printer, wrd: &str) -> old_io::IoResult<()> {
+pub fn word(p: &mut Printer, wrd: &str) -> io::Result<()> {
     p.pretty_print(Token::String(/* bad */ wrd.to_string(), wrd.len() as isize))
 }
 
-pub fn huge_word(p: &mut Printer, wrd: &str) -> old_io::IoResult<()> {
+pub fn huge_word(p: &mut Printer, wrd: &str) -> io::Result<()> {
     p.pretty_print(Token::String(/* bad */ wrd.to_string(), SIZE_INFINITY))
 }
 
-pub fn zero_word(p: &mut Printer, wrd: &str) -> old_io::IoResult<()> {
+pub fn zero_word(p: &mut Printer, wrd: &str) -> io::Result<()> {
     p.pretty_print(Token::String(/* bad */ wrd.to_string(), 0))
 }
 
-pub fn spaces(p: &mut Printer, n: usize) -> old_io::IoResult<()> {
+pub fn spaces(p: &mut Printer, n: usize) -> io::Result<()> {
     break_offset(p, n, 0)
 }
 
-pub fn zerobreak(p: &mut Printer) -> old_io::IoResult<()> {
+pub fn zerobreak(p: &mut Printer) -> io::Result<()> {
     spaces(p, 0)
 }
 
-pub fn space(p: &mut Printer) -> old_io::IoResult<()> {
+pub fn space(p: &mut Printer) -> io::Result<()> {
     spaces(p, 1)
 }
 
-pub fn hardbreak(p: &mut Printer) -> old_io::IoResult<()> {
+pub fn hardbreak(p: &mut Printer) -> io::Result<()> {
     spaces(p, SIZE_INFINITY as usize)
 }
 
index af16e19c9f034a1c33399045ef009407cdbf09c1..883c2295a3655340107d9a644e70cf7bf4b01d0d 100644 (file)
@@ -30,7 +30,7 @@
 use std_inject;
 
 use std::{ascii, mem};
-use std::old_io::{self, IoResult};
+use std::io::{self, Write, Read};
 use std::iter;
 
 pub enum AnnNode<'a> {
@@ -43,8 +43,8 @@ pub enum AnnNode<'a> {
 }
 
 pub trait PpAnn {
-    fn pre(&self, _state: &mut State, _node: AnnNode) -> IoResult<()> { Ok(()) }
-    fn post(&self, _state: &mut State, _node: AnnNode) -> IoResult<()> { Ok(()) }
+    fn pre(&self, _state: &mut State, _node: AnnNode) -> io::Result<()> { Ok(()) }
+    fn post(&self, _state: &mut State, _node: AnnNode) -> io::Result<()> { Ok(()) }
 }
 
 #[derive(Copy)]
@@ -59,7 +59,7 @@ pub struct CurrentCommentAndLiteral {
 }
 
 pub struct State<'a> {
-    pub s: pp::Printer,
+    pub s: pp::Printer<'a>,
     cm: Option<&'a CodeMap>,
     comments: Option<Vec<comments::Comment> >,
     literals: Option<Vec<comments::Literal> >,
@@ -69,12 +69,12 @@ pub struct State<'a> {
     encode_idents_with_hygiene: bool,
 }
 
-pub fn rust_printer(writer: Box<old_io::Writer+'static>) -> State<'static> {
+pub fn rust_printer<'a>(writer: Box<Write+'a>) -> State<'a> {
     static NO_ANN: NoAnn = NoAnn;
     rust_printer_annotated(writer, &NO_ANN)
 }
 
-pub fn rust_printer_annotated<'a>(writer: Box<old_io::Writer+'static>,
+pub fn rust_printer_annotated<'a>(writer: Box<Write+'a>,
                                   ann: &'a PpAnn) -> State<'a> {
     State {
         s: pp::mk_printer(writer, default_columns),
@@ -104,10 +104,10 @@ pub fn print_crate<'a>(cm: &'a CodeMap,
                        span_diagnostic: &diagnostic::SpanHandler,
                        krate: &ast::Crate,
                        filename: String,
-                       input: &mut old_io::Reader,
-                       out: Box<old_io::Writer+'static>,
+                       input: &mut Read,
+                       out: Box<Write+'a>,
                        ann: &'a PpAnn,
-                       is_expanded: bool) -> IoResult<()> {
+                       is_expanded: bool) -> io::Result<()> {
     let mut s = State::new_from_input(cm,
                                       span_diagnostic,
                                       filename,
@@ -143,8 +143,8 @@ impl<'a> State<'a> {
     pub fn new_from_input(cm: &'a CodeMap,
                           span_diagnostic: &diagnostic::SpanHandler,
                           filename: String,
-                          input: &mut old_io::Reader,
-                          out: Box<old_io::Writer+'static>,
+                          input: &mut Read,
+                          out: Box<Write+'a>,
                           ann: &'a PpAnn,
                           is_expanded: bool) -> State<'a> {
         let (cmnts, lits) = comments::gather_comments_and_literals(
@@ -164,7 +164,7 @@ pub fn new_from_input(cm: &'a CodeMap,
     }
 
     pub fn new(cm: &'a CodeMap,
-               out: Box<old_io::Writer+'static>,
+               out: Box<Write+'a>,
                ann: &'a PpAnn,
                comments: Option<Vec<comments::Comment>>,
                literals: Option<Vec<comments::Literal>>) -> State<'a> {
@@ -185,14 +185,14 @@ pub fn new(cm: &'a CodeMap,
 }
 
 pub fn to_string<F>(f: F) -> String where
-    F: FnOnce(&mut State) -> IoResult<()>,
+    F: FnOnce(&mut State) -> io::Result<()>,
 {
     use std::raw::TraitObject;
     let mut s = rust_printer(box Vec::new());
     f(&mut s).unwrap();
     eof(&mut s.s).unwrap();
     let wr = unsafe {
-        // FIXME(pcwalton): A nasty function to extract the string from an `old_io::Writer`
+        // FIXME(pcwalton): A nasty function to extract the string from an `Write`
         // that we "know" to be a `Vec<u8>` that works around the lack of checked
         // downcasts.
         let obj: &TraitObject = mem::transmute(&s.s.out);
@@ -440,13 +440,13 @@ pub fn mac_to_string(arg: &ast::Mac) -> String {
 pub mod with_hygiene {
     use abi;
     use ast;
-    use std::old_io::IoResult;
+    use std::io;
     use super::indent_unit;
 
     // This function is the trick that all the rest of the routines
     // hang on.
     pub fn to_string_hyg<F>(f: F) -> String where
-        F: FnOnce(&mut super::State) -> IoResult<()>,
+        F: FnOnce(&mut super::State) -> io::Result<()>,
     {
         super::to_string(move |s| {
             s.encode_idents_with_hygiene = true;
@@ -474,44 +474,44 @@ fn needs_parentheses(expr: &ast::Expr) -> bool {
 }
 
 impl<'a> State<'a> {
-    pub fn ibox(&mut self, u: usize) -> IoResult<()> {
+    pub fn ibox(&mut self, u: usize) -> io::Result<()> {
         self.boxes.push(pp::Breaks::Inconsistent);
         pp::ibox(&mut self.s, u)
     }
 
-    pub fn end(&mut self) -> IoResult<()> {
+    pub fn end(&mut self) -> io::Result<()> {
         self.boxes.pop().unwrap();
         pp::end(&mut self.s)
     }
 
-    pub fn cbox(&mut self, u: usize) -> IoResult<()> {
+    pub fn cbox(&mut self, u: usize) -> io::Result<()> {
         self.boxes.push(pp::Breaks::Consistent);
         pp::cbox(&mut self.s, u)
     }
 
     // "raw box"
-    pub fn rbox(&mut self, u: usize, b: pp::Breaks) -> IoResult<()> {
+    pub fn rbox(&mut self, u: usize, b: pp::Breaks) -> io::Result<()> {
         self.boxes.push(b);
         pp::rbox(&mut self.s, u, b)
     }
 
-    pub fn nbsp(&mut self) -> IoResult<()> { word(&mut self.s, " ") }
+    pub fn nbsp(&mut self) -> io::Result<()> { word(&mut self.s, " ") }
 
-    pub fn word_nbsp(&mut self, w: &str) -> IoResult<()> {
+    pub fn word_nbsp(&mut self, w: &str) -> io::Result<()> {
         try!(word(&mut self.s, w));
         self.nbsp()
     }
 
-    pub fn word_space(&mut self, w: &str) -> IoResult<()> {
+    pub fn word_space(&mut self, w: &str) -> io::Result<()> {
         try!(word(&mut self.s, w));
         space(&mut self.s)
     }
 
-    pub fn popen(&mut self) -> IoResult<()> { word(&mut self.s, "(") }
+    pub fn popen(&mut self) -> io::Result<()> { word(&mut self.s, "(") }
 
-    pub fn pclose(&mut self) -> IoResult<()> { word(&mut self.s, ")") }
+    pub fn pclose(&mut self) -> io::Result<()> { word(&mut self.s, ")") }
 
-    pub fn head(&mut self, w: &str) -> IoResult<()> {
+    pub fn head(&mut self, w: &str) -> io::Result<()> {
         // outer-box is consistent
         try!(self.cbox(indent_unit));
         // head-box is inconsistent
@@ -523,17 +523,17 @@ pub fn head(&mut self, w: &str) -> IoResult<()> {
         Ok(())
     }
 
-    pub fn bopen(&mut self) -> IoResult<()> {
+    pub fn bopen(&mut self) -> io::Result<()> {
         try!(word(&mut self.s, "{"));
         self.end() // close the head-box
     }
 
     pub fn bclose_(&mut self, span: codemap::Span,
-                   indented: usize) -> IoResult<()> {
+                   indented: usize) -> io::Result<()> {
         self.bclose_maybe_open(span, indented, true)
     }
     pub fn bclose_maybe_open (&mut self, span: codemap::Span,
-                              indented: usize, close_box: bool) -> IoResult<()> {
+                              indented: usize, close_box: bool) -> io::Result<()> {
         try!(self.maybe_print_comment(span.hi));
         try!(self.break_offset_if_not_bol(1, -(indented as isize)));
         try!(word(&mut self.s, "}"));
@@ -542,7 +542,7 @@ pub fn bclose_maybe_open (&mut self, span: codemap::Span,
         }
         Ok(())
     }
-    pub fn bclose(&mut self, span: codemap::Span) -> IoResult<()> {
+    pub fn bclose(&mut self, span: codemap::Span) -> io::Result<()> {
         self.bclose_(span, indent_unit)
     }
 
@@ -572,18 +572,18 @@ pub fn in_cbox(&self) -> bool {
         }
     }
 
-    pub fn hardbreak_if_not_bol(&mut self) -> IoResult<()> {
+    pub fn hardbreak_if_not_bol(&mut self) -> io::Result<()> {
         if !self.is_bol() {
             try!(hardbreak(&mut self.s))
         }
         Ok(())
     }
-    pub fn space_if_not_bol(&mut self) -> IoResult<()> {
+    pub fn space_if_not_bol(&mut self) -> io::Result<()> {
         if !self.is_bol() { try!(space(&mut self.s)); }
         Ok(())
     }
     pub fn break_offset_if_not_bol(&mut self, n: usize,
-                                   off: isize) -> IoResult<()> {
+                                   off: isize) -> io::Result<()> {
         if !self.is_bol() {
             break_offset(&mut self.s, n, off)
         } else {
@@ -599,7 +599,7 @@ pub fn break_offset_if_not_bol(&mut self, n: usize,
 
     // Synthesizes a comment that was not textually present in the original source
     // file.
-    pub fn synth_comment(&mut self, text: String) -> IoResult<()> {
+    pub fn synth_comment(&mut self, text: String) -> io::Result<()> {
         try!(word(&mut self.s, "/*"));
         try!(space(&mut self.s));
         try!(word(&mut self.s, &text[..]));
@@ -607,8 +607,8 @@ pub fn synth_comment(&mut self, text: String) -> IoResult<()> {
         word(&mut self.s, "*/")
     }
 
-    pub fn commasep<T, F>(&mut self, b: Breaks, elts: &[T], mut op: F) -> IoResult<()> where
-        F: FnMut(&mut State, &T) -> IoResult<()>,
+    pub fn commasep<T, F>(&mut self, b: Breaks, elts: &[T], mut op: F) -> io::Result<()> where
+        F: FnMut(&mut State, &T) -> io::Result<()>,
     {
         try!(self.rbox(0, b));
         let mut first = true;
@@ -624,8 +624,8 @@ pub fn commasep_cmnt<T, F, G>(&mut self,
                                   b: Breaks,
                                   elts: &[T],
                                   mut op: F,
-                                  mut get_span: G) -> IoResult<()> where
-        F: FnMut(&mut State, &T) -> IoResult<()>,
+                                  mut get_span: G) -> io::Result<()> where
+        F: FnMut(&mut State, &T) -> io::Result<()>,
         G: FnMut(&T) -> codemap::Span,
     {
         try!(self.rbox(0, b));
@@ -646,12 +646,12 @@ pub fn commasep_cmnt<T, F, G>(&mut self,
     }
 
     pub fn commasep_exprs(&mut self, b: Breaks,
-                          exprs: &[P<ast::Expr>]) -> IoResult<()> {
+                          exprs: &[P<ast::Expr>]) -> io::Result<()> {
         self.commasep_cmnt(b, exprs, |s, e| s.print_expr(&**e), |e| e.span)
     }
 
     pub fn print_mod(&mut self, _mod: &ast::Mod,
-                     attrs: &[ast::Attribute]) -> IoResult<()> {
+                     attrs: &[ast::Attribute]) -> io::Result<()> {
         try!(self.print_inner_attributes(attrs));
         for item in &_mod.items {
             try!(self.print_item(&**item));
@@ -660,7 +660,7 @@ pub fn print_mod(&mut self, _mod: &ast::Mod,
     }
 
     pub fn print_foreign_mod(&mut self, nmod: &ast::ForeignMod,
-                             attrs: &[ast::Attribute]) -> IoResult<()> {
+                             attrs: &[ast::Attribute]) -> io::Result<()> {
         try!(self.print_inner_attributes(attrs));
         for item in &nmod.items {
             try!(self.print_foreign_item(&**item));
@@ -669,7 +669,7 @@ pub fn print_foreign_mod(&mut self, nmod: &ast::ForeignMod,
     }
 
     pub fn print_opt_lifetime(&mut self,
-                              lifetime: &Option<ast::Lifetime>) -> IoResult<()> {
+                              lifetime: &Option<ast::Lifetime>) -> io::Result<()> {
         if let Some(l) = *lifetime {
             try!(self.print_lifetime(&l));
             try!(self.nbsp());
@@ -677,7 +677,7 @@ pub fn print_opt_lifetime(&mut self,
         Ok(())
     }
 
-    pub fn print_type(&mut self, ty: &ast::Ty) -> IoResult<()> {
+    pub fn print_type(&mut self, ty: &ast::Ty) -> io::Result<()> {
         try!(self.maybe_print_comment(ty.span.lo));
         try!(self.ibox(0));
         match ty.node {
@@ -762,7 +762,7 @@ pub fn print_type(&mut self, ty: &ast::Ty) -> IoResult<()> {
     }
 
     pub fn print_foreign_item(&mut self,
-                              item: &ast::ForeignItem) -> IoResult<()> {
+                              item: &ast::ForeignItem) -> io::Result<()> {
         try!(self.hardbreak_if_not_bol());
         try!(self.maybe_print_comment(item.span.lo));
         try!(self.print_outer_attributes(&item.attrs));
@@ -791,7 +791,7 @@ pub fn print_foreign_item(&mut self,
     }
 
     fn print_associated_type(&mut self, typedef: &ast::AssociatedType)
-                             -> IoResult<()>
+                             -> io::Result<()>
     {
         try!(self.print_outer_attributes(&typedef.attrs));
         try!(self.word_space("type"));
@@ -799,7 +799,7 @@ fn print_associated_type(&mut self, typedef: &ast::AssociatedType)
         word(&mut self.s, ";")
     }
 
-    fn print_typedef(&mut self, typedef: &ast::Typedef) -> IoResult<()> {
+    fn print_typedef(&mut self, typedef: &ast::Typedef) -> io::Result<()> {
         try!(self.word_space("type"));
         try!(self.print_ident(typedef.ident));
         try!(space(&mut self.s));
@@ -809,7 +809,7 @@ fn print_typedef(&mut self, typedef: &ast::Typedef) -> IoResult<()> {
     }
 
     /// Pretty-print an item
-    pub fn print_item(&mut self, item: &ast::Item) -> IoResult<()> {
+    pub fn print_item(&mut self, item: &ast::Item) -> io::Result<()> {
         try!(self.hardbreak_if_not_bol());
         try!(self.maybe_print_comment(item.span.lo));
         try!(self.print_outer_attributes(&item.attrs));
@@ -1032,11 +1032,11 @@ pub fn print_item(&mut self, item: &ast::Item) -> IoResult<()> {
         self.ann.post(self, NodeItem(item))
     }
 
-    fn print_trait_ref(&mut self, t: &ast::TraitRef) -> IoResult<()> {
+    fn print_trait_ref(&mut self, t: &ast::TraitRef) -> io::Result<()> {
         self.print_path(&t.path, false, 0)
     }
 
-    fn print_formal_lifetime_list(&mut self, lifetimes: &[ast::LifetimeDef]) -> IoResult<()> {
+    fn print_formal_lifetime_list(&mut self, lifetimes: &[ast::LifetimeDef]) -> io::Result<()> {
         if !lifetimes.is_empty() {
             try!(word(&mut self.s, "for<"));
             let mut comma = false;
@@ -1052,7 +1052,7 @@ fn print_formal_lifetime_list(&mut self, lifetimes: &[ast::LifetimeDef]) -> IoRe
         Ok(())
     }
 
-    fn print_poly_trait_ref(&mut self, t: &ast::PolyTraitRef) -> IoResult<()> {
+    fn print_poly_trait_ref(&mut self, t: &ast::PolyTraitRef) -> io::Result<()> {
         try!(self.print_formal_lifetime_list(&t.bound_lifetimes));
         self.print_trait_ref(&t.trait_ref)
     }
@@ -1060,7 +1060,7 @@ fn print_poly_trait_ref(&mut self, t: &ast::PolyTraitRef) -> IoResult<()> {
     pub fn print_enum_def(&mut self, enum_definition: &ast::EnumDef,
                           generics: &ast::Generics, ident: ast::Ident,
                           span: codemap::Span,
-                          visibility: ast::Visibility) -> IoResult<()> {
+                          visibility: ast::Visibility) -> io::Result<()> {
         try!(self.head(&visibility_qualified(visibility, "enum")));
         try!(self.print_ident(ident));
         try!(self.print_generics(generics));
@@ -1071,7 +1071,7 @@ pub fn print_enum_def(&mut self, enum_definition: &ast::EnumDef,
 
     pub fn print_variants(&mut self,
                           variants: &[P<ast::Variant>],
-                          span: codemap::Span) -> IoResult<()> {
+                          span: codemap::Span) -> io::Result<()> {
         try!(self.bopen());
         for v in variants {
             try!(self.space_if_not_bol());
@@ -1086,7 +1086,7 @@ pub fn print_variants(&mut self,
         self.bclose(span)
     }
 
-    pub fn print_visibility(&mut self, vis: ast::Visibility) -> IoResult<()> {
+    pub fn print_visibility(&mut self, vis: ast::Visibility) -> io::Result<()> {
         match vis {
             ast::Public => self.word_nbsp("pub"),
             ast::Inherited => Ok(())
@@ -1097,7 +1097,7 @@ pub fn print_struct(&mut self,
                         struct_def: &ast::StructDef,
                         generics: &ast::Generics,
                         ident: ast::Ident,
-                        span: codemap::Span) -> IoResult<()> {
+                        span: codemap::Span) -> io::Result<()> {
         try!(self.print_ident(ident));
         try!(self.print_generics(generics));
         if ast_util::struct_def_is_tuple_like(struct_def) {
@@ -1155,7 +1155,7 @@ pub fn print_struct(&mut self,
     /// appropriate macro, transcribe back into the grammar we just parsed from,
     /// and then pretty-print the resulting AST nodes (so, e.g., we print
     /// expression arguments as expressions). It can be done! I think.
-    pub fn print_tt(&mut self, tt: &ast::TokenTree) -> IoResult<()> {
+    pub fn print_tt(&mut self, tt: &ast::TokenTree) -> io::Result<()> {
         match *tt {
             ast::TtToken(_, ref tk) => {
                 try!(word(&mut self.s, &token_to_string(tk)));
@@ -1193,7 +1193,7 @@ pub fn print_tt(&mut self, tt: &ast::TokenTree) -> IoResult<()> {
         }
     }
 
-    pub fn print_tts(&mut self, tts: &[ast::TokenTree]) -> IoResult<()> {
+    pub fn print_tts(&mut self, tts: &[ast::TokenTree]) -> io::Result<()> {
         try!(self.ibox(0));
         let mut suppress_space = false;
         for (i, tt) in tts.iter().enumerate() {
@@ -1213,7 +1213,7 @@ pub fn print_tts(&mut self, tts: &[ast::TokenTree]) -> IoResult<()> {
         self.end()
     }
 
-    pub fn print_variant(&mut self, v: &ast::Variant) -> IoResult<()> {
+    pub fn print_variant(&mut self, v: &ast::Variant) -> io::Result<()> {
         try!(self.print_visibility(v.node.vis));
         match v.node.kind {
             ast::TupleVariantKind(ref args) => {
@@ -1242,7 +1242,7 @@ pub fn print_variant(&mut self, v: &ast::Variant) -> IoResult<()> {
         }
     }
 
-    pub fn print_ty_method(&mut self, m: &ast::TypeMethod) -> IoResult<()> {
+    pub fn print_ty_method(&mut self, m: &ast::TypeMethod) -> io::Result<()> {
         try!(self.hardbreak_if_not_bol());
         try!(self.maybe_print_comment(m.span.lo));
         try!(self.print_outer_attributes(&m.attrs));
@@ -1256,7 +1256,7 @@ pub fn print_ty_method(&mut self, m: &ast::TypeMethod) -> IoResult<()> {
     }
 
     pub fn print_trait_method(&mut self,
-                              m: &ast::TraitItem) -> IoResult<()> {
+                              m: &ast::TraitItem) -> io::Result<()> {
         match *m {
             RequiredMethod(ref ty_m) => self.print_ty_method(ty_m),
             ProvidedMethod(ref m) => self.print_method(&**m),
@@ -1264,14 +1264,14 @@ pub fn print_trait_method(&mut self,
         }
     }
 
-    pub fn print_impl_item(&mut self, ii: &ast::ImplItem) -> IoResult<()> {
+    pub fn print_impl_item(&mut self, ii: &ast::ImplItem) -> io::Result<()> {
         match *ii {
             MethodImplItem(ref m) => self.print_method(&**m),
             TypeImplItem(ref td) => self.print_typedef(&**td),
         }
     }
 
-    pub fn print_method(&mut self, meth: &ast::Method) -> IoResult<()> {
+    pub fn print_method(&mut self, meth: &ast::Method) -> io::Result<()> {
         try!(self.hardbreak_if_not_bol());
         try!(self.maybe_print_comment(meth.span.lo));
         try!(self.print_outer_attributes(&meth.attrs));
@@ -1310,7 +1310,7 @@ pub fn print_method(&mut self, meth: &ast::Method) -> IoResult<()> {
     }
 
     pub fn print_outer_attributes(&mut self,
-                                  attrs: &[ast::Attribute]) -> IoResult<()> {
+                                  attrs: &[ast::Attribute]) -> io::Result<()> {
         let mut count = 0;
         for attr in attrs {
             match attr.node.style {
@@ -1328,7 +1328,7 @@ pub fn print_outer_attributes(&mut self,
     }
 
     pub fn print_inner_attributes(&mut self,
-                                  attrs: &[ast::Attribute]) -> IoResult<()> {
+                                  attrs: &[ast::Attribute]) -> io::Result<()> {
         let mut count = 0;
         for attr in attrs {
             match attr.node.style {
@@ -1345,7 +1345,7 @@ pub fn print_inner_attributes(&mut self,
         Ok(())
     }
 
-    pub fn print_attribute(&mut self, attr: &ast::Attribute) -> IoResult<()> {
+    pub fn print_attribute(&mut self, attr: &ast::Attribute) -> io::Result<()> {
         try!(self.hardbreak_if_not_bol());
         try!(self.maybe_print_comment(attr.span.lo));
         if attr.node.is_sugared_doc {
@@ -1361,7 +1361,7 @@ pub fn print_attribute(&mut self, attr: &ast::Attribute) -> IoResult<()> {
     }
 
 
-    pub fn print_stmt(&mut self, st: &ast::Stmt) -> IoResult<()> {
+    pub fn print_stmt(&mut self, st: &ast::Stmt) -> io::Result<()> {
         try!(self.maybe_print_comment(st.span.lo));
         match st.node {
             ast::StmtDecl(ref decl, _) => {
@@ -1395,22 +1395,22 @@ pub fn print_stmt(&mut self, st: &ast::Stmt) -> IoResult<()> {
         self.maybe_print_trailing_comment(st.span, None)
     }
 
-    pub fn print_block(&mut self, blk: &ast::Block) -> IoResult<()> {
+    pub fn print_block(&mut self, blk: &ast::Block) -> io::Result<()> {
         self.print_block_with_attrs(blk, &[])
     }
 
-    pub fn print_block_unclosed(&mut self, blk: &ast::Block) -> IoResult<()> {
+    pub fn print_block_unclosed(&mut self, blk: &ast::Block) -> io::Result<()> {
         self.print_block_unclosed_indent(blk, indent_unit)
     }
 
     pub fn print_block_unclosed_indent(&mut self, blk: &ast::Block,
-                                       indented: usize) -> IoResult<()> {
+                                       indented: usize) -> io::Result<()> {
         self.print_block_maybe_unclosed(blk, indented, &[], false)
     }
 
     pub fn print_block_with_attrs(&mut self,
                                   blk: &ast::Block,
-                                  attrs: &[ast::Attribute]) -> IoResult<()> {
+                                  attrs: &[ast::Attribute]) -> io::Result<()> {
         self.print_block_maybe_unclosed(blk, indent_unit, attrs, true)
     }
 
@@ -1418,7 +1418,7 @@ pub fn print_block_maybe_unclosed(&mut self,
                                       blk: &ast::Block,
                                       indented: usize,
                                       attrs: &[ast::Attribute],
-                                      close_box: bool) -> IoResult<()> {
+                                      close_box: bool) -> io::Result<()> {
         match blk.rules {
             ast::UnsafeBlock(..) => try!(self.word_space("unsafe")),
             ast::DefaultBlock => ()
@@ -1444,7 +1444,7 @@ pub fn print_block_maybe_unclosed(&mut self,
         self.ann.post(self, NodeBlock(blk))
     }
 
-    fn print_else(&mut self, els: Option<&ast::Expr>) -> IoResult<()> {
+    fn print_else(&mut self, els: Option<&ast::Expr>) -> io::Result<()> {
         match els {
             Some(_else) => {
                 match _else.node {
@@ -1489,7 +1489,7 @@ fn print_else(&mut self, els: Option<&ast::Expr>) -> IoResult<()> {
     }
 
     pub fn print_if(&mut self, test: &ast::Expr, blk: &ast::Block,
-                    elseopt: Option<&ast::Expr>) -> IoResult<()> {
+                    elseopt: Option<&ast::Expr>) -> io::Result<()> {
         try!(self.head("if"));
         try!(self.print_expr(test));
         try!(space(&mut self.s));
@@ -1498,7 +1498,7 @@ pub fn print_if(&mut self, test: &ast::Expr, blk: &ast::Block,
     }
 
     pub fn print_if_let(&mut self, pat: &ast::Pat, expr: &ast::Expr, blk: &ast::Block,
-                        elseopt: Option<&ast::Expr>) -> IoResult<()> {
+                        elseopt: Option<&ast::Expr>) -> io::Result<()> {
         try!(self.head("if let"));
         try!(self.print_pat(pat));
         try!(space(&mut self.s));
@@ -1510,7 +1510,7 @@ pub fn print_if_let(&mut self, pat: &ast::Pat, expr: &ast::Expr, blk: &ast::Bloc
     }
 
     pub fn print_mac(&mut self, m: &ast::Mac, delim: token::DelimToken)
-                     -> IoResult<()> {
+                     -> io::Result<()> {
         match m.node {
             // I think it's reasonable to hide the ctxt here:
             ast::MacInvocTT(ref pth, ref tts, _) => {
@@ -1532,13 +1532,13 @@ pub fn print_mac(&mut self, m: &ast::Mac, delim: token::DelimToken)
     }
 
 
-    fn print_call_post(&mut self, args: &[P<ast::Expr>]) -> IoResult<()> {
+    fn print_call_post(&mut self, args: &[P<ast::Expr>]) -> io::Result<()> {
         try!(self.popen());
         try!(self.commasep_exprs(Inconsistent, args));
         self.pclose()
     }
 
-    pub fn print_expr_maybe_paren(&mut self, expr: &ast::Expr) -> IoResult<()> {
+    pub fn print_expr_maybe_paren(&mut self, expr: &ast::Expr) -> io::Result<()> {
         let needs_par = needs_parentheses(expr);
         if needs_par {
             try!(self.popen());
@@ -1552,7 +1552,7 @@ pub fn print_expr_maybe_paren(&mut self, expr: &ast::Expr) -> IoResult<()> {
 
     fn print_expr_box(&mut self,
                       place: &Option<P<ast::Expr>>,
-                      expr: &ast::Expr) -> IoResult<()> {
+                      expr: &ast::Expr) -> io::Result<()> {
         try!(word(&mut self.s, "box"));
         try!(word(&mut self.s, "("));
         try!(place.as_ref().map_or(Ok(()), |e|self.print_expr(&**e)));
@@ -1560,7 +1560,7 @@ fn print_expr_box(&mut self,
         self.print_expr(expr)
     }
 
-    fn print_expr_vec(&mut self, exprs: &[P<ast::Expr>]) -> IoResult<()> {
+    fn print_expr_vec(&mut self, exprs: &[P<ast::Expr>]) -> io::Result<()> {
         try!(self.ibox(indent_unit));
         try!(word(&mut self.s, "["));
         try!(self.commasep_exprs(Inconsistent, &exprs[..]));
@@ -1570,7 +1570,7 @@ fn print_expr_vec(&mut self, exprs: &[P<ast::Expr>]) -> IoResult<()> {
 
     fn print_expr_repeat(&mut self,
                          element: &ast::Expr,
-                         count: &ast::Expr) -> IoResult<()> {
+                         count: &ast::Expr) -> io::Result<()> {
         try!(self.ibox(indent_unit));
         try!(word(&mut self.s, "["));
         try!(self.print_expr(element));
@@ -1583,7 +1583,7 @@ fn print_expr_repeat(&mut self,
     fn print_expr_struct(&mut self,
                          path: &ast::Path,
                          fields: &[ast::Field],
-                         wth: &Option<P<ast::Expr>>) -> IoResult<()> {
+                         wth: &Option<P<ast::Expr>>) -> io::Result<()> {
         try!(self.print_path(path, true, 0));
         if !(fields.is_empty() && wth.is_none()) {
             try!(word(&mut self.s, "{"));
@@ -1616,7 +1616,7 @@ fn print_expr_struct(&mut self,
         Ok(())
     }
 
-    fn print_expr_tup(&mut self, exprs: &[P<ast::Expr>]) -> IoResult<()> {
+    fn print_expr_tup(&mut self, exprs: &[P<ast::Expr>]) -> io::Result<()> {
         try!(self.popen());
         try!(self.commasep_exprs(Inconsistent, &exprs[..]));
         if exprs.len() == 1 {
@@ -1627,7 +1627,7 @@ fn print_expr_tup(&mut self, exprs: &[P<ast::Expr>]) -> IoResult<()> {
 
     fn print_expr_call(&mut self,
                        func: &ast::Expr,
-                       args: &[P<ast::Expr>]) -> IoResult<()> {
+                       args: &[P<ast::Expr>]) -> io::Result<()> {
         try!(self.print_expr_maybe_paren(func));
         self.print_call_post(args)
     }
@@ -1635,7 +1635,7 @@ fn print_expr_call(&mut self,
     fn print_expr_method_call(&mut self,
                               ident: ast::SpannedIdent,
                               tys: &[P<ast::Ty>],
-                              args: &[P<ast::Expr>]) -> IoResult<()> {
+                              args: &[P<ast::Expr>]) -> io::Result<()> {
         let base_args = &args[1..];
         try!(self.print_expr(&*args[0]));
         try!(word(&mut self.s, "."));
@@ -1652,7 +1652,7 @@ fn print_expr_method_call(&mut self,
     fn print_expr_binary(&mut self,
                          op: ast::BinOp,
                          lhs: &ast::Expr,
-                         rhs: &ast::Expr) -> IoResult<()> {
+                         rhs: &ast::Expr) -> io::Result<()> {
         try!(self.print_expr(lhs));
         try!(space(&mut self.s));
         try!(self.word_space(ast_util::binop_to_string(op.node)));
@@ -1661,20 +1661,20 @@ fn print_expr_binary(&mut self,
 
     fn print_expr_unary(&mut self,
                         op: ast::UnOp,
-                        expr: &ast::Expr) -> IoResult<()> {
+                        expr: &ast::Expr) -> io::Result<()> {
         try!(word(&mut self.s, ast_util::unop_to_string(op)));
         self.print_expr_maybe_paren(expr)
     }
 
     fn print_expr_addr_of(&mut self,
                           mutability: ast::Mutability,
-                          expr: &ast::Expr) -> IoResult<()> {
+                          expr: &ast::Expr) -> io::Result<()> {
         try!(word(&mut self.s, "&"));
         try!(self.print_mutability(mutability));
         self.print_expr_maybe_paren(expr)
     }
 
-    pub fn print_expr(&mut self, expr: &ast::Expr) -> IoResult<()> {
+    pub fn print_expr(&mut self, expr: &ast::Expr) -> io::Result<()> {
         try!(self.maybe_print_comment(expr.span.lo));
         try!(self.ibox(indent_unit));
         try!(self.ann.pre(self, NodeExpr(expr)));
@@ -1958,7 +1958,7 @@ pub fn print_expr(&mut self, expr: &ast::Expr) -> IoResult<()> {
         self.end()
     }
 
-    pub fn print_local_decl(&mut self, loc: &ast::Local) -> IoResult<()> {
+    pub fn print_local_decl(&mut self, loc: &ast::Local) -> io::Result<()> {
         try!(self.print_pat(&*loc.pat));
         if let Some(ref ty) = loc.ty {
             try!(self.word_space(":"));
@@ -1967,7 +1967,7 @@ pub fn print_local_decl(&mut self, loc: &ast::Local) -> IoResult<()> {
         Ok(())
     }
 
-    pub fn print_decl(&mut self, decl: &ast::Decl) -> IoResult<()> {
+    pub fn print_decl(&mut self, decl: &ast::Decl) -> io::Result<()> {
         try!(self.maybe_print_comment(decl.span.lo));
         match decl.node {
             ast::DeclLocal(ref loc) => {
@@ -1989,7 +1989,7 @@ pub fn print_decl(&mut self, decl: &ast::Decl) -> IoResult<()> {
         }
     }
 
-    pub fn print_ident(&mut self, ident: ast::Ident) -> IoResult<()> {
+    pub fn print_ident(&mut self, ident: ast::Ident) -> io::Result<()> {
         if self.encode_idents_with_hygiene {
             let encoded = ident.encode_with_hygiene();
             try!(word(&mut self.s, &encoded[..]))
@@ -1999,17 +1999,17 @@ pub fn print_ident(&mut self, ident: ast::Ident) -> IoResult<()> {
         self.ann.post(self, NodeIdent(&ident))
     }
 
-    pub fn print_usize(&mut self, i: usize) -> IoResult<()> {
+    pub fn print_usize(&mut self, i: usize) -> io::Result<()> {
         word(&mut self.s, &i.to_string())
     }
 
-    pub fn print_name(&mut self, name: ast::Name) -> IoResult<()> {
+    pub fn print_name(&mut self, name: ast::Name) -> io::Result<()> {
         try!(word(&mut self.s, &token::get_name(name)));
         self.ann.post(self, NodeName(&name))
     }
 
     pub fn print_for_decl(&mut self, loc: &ast::Local,
-                          coll: &ast::Expr) -> IoResult<()> {
+                          coll: &ast::Expr) -> io::Result<()> {
         try!(self.print_local_decl(loc));
         try!(space(&mut self.s));
         try!(self.word_space("in"));
@@ -2020,7 +2020,7 @@ fn print_path(&mut self,
                   path: &ast::Path,
                   colons_before_params: bool,
                   depth: usize)
-                  -> IoResult<()>
+                  -> io::Result<()>
     {
         try!(self.maybe_print_comment(path.span.lo));
 
@@ -2044,7 +2044,7 @@ fn print_qpath(&mut self,
                    path: &ast::Path,
                    qself: &ast::QSelf,
                    colons_before_params: bool)
-                   -> IoResult<()>
+                   -> io::Result<()>
     {
         try!(word(&mut self.s, "<"));
         try!(self.print_type(&qself.ty));
@@ -2064,7 +2064,7 @@ fn print_qpath(&mut self,
     fn print_path_parameters(&mut self,
                              parameters: &ast::PathParameters,
                              colons_before_params: bool)
-                             -> IoResult<()>
+                             -> io::Result<()>
     {
         if parameters.is_empty() {
             return Ok(());
@@ -2134,7 +2134,7 @@ fn print_path_parameters(&mut self,
         Ok(())
     }
 
-    pub fn print_pat(&mut self, pat: &ast::Pat) -> IoResult<()> {
+    pub fn print_pat(&mut self, pat: &ast::Pat) -> io::Result<()> {
         try!(self.maybe_print_comment(pat.span.lo));
         try!(self.ann.pre(self, NodePat(pat)));
         /* Pat isn't normalized, but the beauty of it
@@ -2253,7 +2253,7 @@ pub fn print_pat(&mut self, pat: &ast::Pat) -> IoResult<()> {
         self.ann.post(self, NodePat(pat))
     }
 
-    fn print_arm(&mut self, arm: &ast::Arm) -> IoResult<()> {
+    fn print_arm(&mut self, arm: &ast::Arm) -> io::Result<()> {
         // I have no idea why this check is necessary, but here it
         // is :(
         if arm.attrs.is_empty() {
@@ -2302,7 +2302,7 @@ fn print_arm(&mut self, arm: &ast::Arm) -> IoResult<()> {
     // Returns whether it printed anything
     fn print_explicit_self(&mut self,
                            explicit_self: &ast::ExplicitSelf_,
-                           mutbl: ast::Mutability) -> IoResult<bool> {
+                           mutbl: ast::Mutability) -> io::Result<bool> {
         try!(self.print_mutability(mutbl));
         match *explicit_self {
             ast::SelfStatic => { return Ok(false); }
@@ -2331,7 +2331,7 @@ pub fn print_fn(&mut self,
                     name: ast::Ident,
                     generics: &ast::Generics,
                     opt_explicit_self: Option<&ast::ExplicitSelf_>,
-                    vis: ast::Visibility) -> IoResult<()> {
+                    vis: ast::Visibility) -> io::Result<()> {
         try!(self.head(""));
         try!(self.print_fn_header_info(unsafety, abi, vis));
         try!(self.nbsp());
@@ -2343,7 +2343,7 @@ pub fn print_fn(&mut self,
 
     pub fn print_fn_args(&mut self, decl: &ast::FnDecl,
                          opt_explicit_self: Option<&ast::ExplicitSelf_>)
-        -> IoResult<()> {
+        -> io::Result<()> {
         // It is unfortunate to duplicate the commasep logic, but we want the
         // self type and the args all in the same box.
         try!(self.rbox(0, Inconsistent));
@@ -2376,7 +2376,7 @@ pub fn print_fn_args(&mut self, decl: &ast::FnDecl,
 
     pub fn print_fn_args_and_ret(&mut self, decl: &ast::FnDecl,
                                  opt_explicit_self: Option<&ast::ExplicitSelf_>)
-        -> IoResult<()> {
+        -> io::Result<()> {
         try!(self.popen());
         try!(self.print_fn_args(decl, opt_explicit_self));
         if decl.variadic {
@@ -2390,7 +2390,7 @@ pub fn print_fn_args_and_ret(&mut self, decl: &ast::FnDecl,
     pub fn print_fn_block_args(
             &mut self,
             decl: &ast::FnDecl)
-            -> IoResult<()> {
+            -> io::Result<()> {
         try!(word(&mut self.s, "|"));
         try!(self.print_fn_args(decl, None));
         try!(word(&mut self.s, "|"));
@@ -2415,7 +2415,7 @@ pub fn print_fn_block_args(
     }
 
     pub fn print_capture_clause(&mut self, capture_clause: ast::CaptureClause)
-                                -> IoResult<()> {
+                                -> io::Result<()> {
         match capture_clause {
             ast::CaptureByValue => self.word_space("move"),
             ast::CaptureByRef => Ok(()),
@@ -2425,7 +2425,7 @@ pub fn print_capture_clause(&mut self, capture_clause: ast::CaptureClause)
     pub fn print_bounds(&mut self,
                         prefix: &str,
                         bounds: &[ast::TyParamBound])
-                        -> IoResult<()> {
+                        -> io::Result<()> {
         if !bounds.is_empty() {
             try!(word(&mut self.s, prefix));
             let mut first = true;
@@ -2458,14 +2458,14 @@ pub fn print_bounds(&mut self,
 
     pub fn print_lifetime(&mut self,
                           lifetime: &ast::Lifetime)
-                          -> IoResult<()>
+                          -> io::Result<()>
     {
         self.print_name(lifetime.name)
     }
 
     pub fn print_lifetime_def(&mut self,
                               lifetime: &ast::LifetimeDef)
-                              -> IoResult<()>
+                              -> io::Result<()>
     {
         try!(self.print_lifetime(&lifetime.lifetime));
         let mut sep = ":";
@@ -2479,7 +2479,7 @@ pub fn print_lifetime_def(&mut self,
 
     pub fn print_generics(&mut self,
                           generics: &ast::Generics)
-                          -> IoResult<()>
+                          -> io::Result<()>
     {
         let total = generics.lifetimes.len() + generics.ty_params.len();
         if total == 0 {
@@ -2508,7 +2508,7 @@ pub fn print_generics(&mut self,
         Ok(())
     }
 
-    pub fn print_ty_param(&mut self, param: &ast::TyParam) -> IoResult<()> {
+    pub fn print_ty_param(&mut self, param: &ast::TyParam) -> io::Result<()> {
         try!(self.print_ident(param.ident));
         try!(self.print_bounds(":", &param.bounds));
         match param.default {
@@ -2522,7 +2522,7 @@ pub fn print_ty_param(&mut self, param: &ast::TyParam) -> IoResult<()> {
     }
 
     pub fn print_where_clause(&mut self, generics: &ast::Generics)
-                              -> IoResult<()> {
+                              -> io::Result<()> {
         if generics.where_clause.predicates.len() == 0 {
             return Ok(())
         }
@@ -2573,7 +2573,7 @@ pub fn print_where_clause(&mut self, generics: &ast::Generics)
         Ok(())
     }
 
-    pub fn print_meta_item(&mut self, item: &ast::MetaItem) -> IoResult<()> {
+    pub fn print_meta_item(&mut self, item: &ast::MetaItem) -> io::Result<()> {
         try!(self.ibox(indent_unit));
         match item.node {
             ast::MetaWord(ref name) => {
@@ -2596,7 +2596,7 @@ pub fn print_meta_item(&mut self, item: &ast::MetaItem) -> IoResult<()> {
         self.end()
     }
 
-    pub fn print_view_path(&mut self, vp: &ast::ViewPath) -> IoResult<()> {
+    pub fn print_view_path(&mut self, vp: &ast::ViewPath) -> io::Result<()> {
         match vp.node {
             ast::ViewPathSimple(ident, ref path) => {
                 try!(self.print_path(path, false, 0));
@@ -2640,19 +2640,19 @@ pub fn print_view_path(&mut self, vp: &ast::ViewPath) -> IoResult<()> {
     }
 
     pub fn print_mutability(&mut self,
-                            mutbl: ast::Mutability) -> IoResult<()> {
+                            mutbl: ast::Mutability) -> io::Result<()> {
         match mutbl {
             ast::MutMutable => self.word_nbsp("mut"),
             ast::MutImmutable => Ok(()),
         }
     }
 
-    pub fn print_mt(&mut self, mt: &ast::MutTy) -> IoResult<()> {
+    pub fn print_mt(&mut self, mt: &ast::MutTy) -> io::Result<()> {
         try!(self.print_mutability(mt.mutbl));
         self.print_type(&*mt.ty)
     }
 
-    pub fn print_arg(&mut self, input: &ast::Arg) -> IoResult<()> {
+    pub fn print_arg(&mut self, input: &ast::Arg) -> io::Result<()> {
         try!(self.ibox(indent_unit));
         match input.ty.node {
             ast::TyInfer => try!(self.print_pat(&*input.pat)),
@@ -2675,7 +2675,7 @@ pub fn print_arg(&mut self, input: &ast::Arg) -> IoResult<()> {
         self.end()
     }
 
-    pub fn print_fn_output(&mut self, decl: &ast::FnDecl) -> IoResult<()> {
+    pub fn print_fn_output(&mut self, decl: &ast::FnDecl) -> io::Result<()> {
         if let ast::DefaultReturn(..) = decl.output {
             return Ok(());
         }
@@ -2705,7 +2705,7 @@ pub fn print_ty_fn(&mut self,
                        id: Option<ast::Ident>,
                        generics: &ast::Generics,
                        opt_explicit_self: Option<&ast::ExplicitSelf_>)
-                       -> IoResult<()> {
+                       -> io::Result<()> {
         try!(self.ibox(indent_unit));
         try!(self.print_fn_header_info(Some(unsafety), abi, ast::Inherited));
 
@@ -2726,7 +2726,7 @@ pub fn print_ty_fn(&mut self,
 
     pub fn maybe_print_trailing_comment(&mut self, span: codemap::Span,
                                         next_pos: Option<BytePos>)
-        -> IoResult<()> {
+        -> io::Result<()> {
         let cm = match self.cm {
             Some(cm) => cm,
             _ => return Ok(())
@@ -2749,7 +2749,7 @@ pub fn maybe_print_trailing_comment(&mut self, span: codemap::Span,
         Ok(())
     }
 
-    pub fn print_remaining_comments(&mut self) -> IoResult<()> {
+    pub fn print_remaining_comments(&mut self) -> io::Result<()> {
         // If there aren't any remaining comments, then we need to manually
         // make sure there is a line break at the end.
         if self.next_comment().is_none() {
@@ -2767,7 +2767,7 @@ pub fn print_remaining_comments(&mut self) -> IoResult<()> {
         Ok(())
     }
 
-    pub fn print_literal(&mut self, lit: &ast::Lit) -> IoResult<()> {
+    pub fn print_literal(&mut self, lit: &ast::Lit) -> io::Result<()> {
         try!(self.maybe_print_comment(lit.span.lo));
         match self.next_lit(lit.span.lo) {
             Some(ref ltrl) => {
@@ -2848,7 +2848,7 @@ pub fn next_lit(&mut self, pos: BytePos) -> Option<comments::Literal> {
         }
     }
 
-    pub fn maybe_print_comment(&mut self, pos: BytePos) -> IoResult<()> {
+    pub fn maybe_print_comment(&mut self, pos: BytePos) -> io::Result<()> {
         loop {
             match self.next_comment() {
                 Some(ref cmnt) => {
@@ -2864,7 +2864,7 @@ pub fn maybe_print_comment(&mut self, pos: BytePos) -> IoResult<()> {
     }
 
     pub fn print_comment(&mut self,
-                         cmnt: &comments::Comment) -> IoResult<()> {
+                         cmnt: &comments::Comment) -> io::Result<()> {
         match cmnt.style {
             comments::Mixed => {
                 assert_eq!(cmnt.lines.len(), 1);
@@ -2915,7 +2915,7 @@ pub fn print_comment(&mut self,
     }
 
     pub fn print_string(&mut self, st: &str,
-                        style: ast::StrStyle) -> IoResult<()> {
+                        style: ast::StrStyle) -> io::Result<()> {
         let st = match style {
             ast::CookedStr => {
                 (format!("\"{}\"", st.escape_default()))
@@ -2943,7 +2943,7 @@ pub fn next_comment(&mut self) -> Option<comments::Comment> {
     }
 
     pub fn print_opt_unsafety(&mut self,
-                            opt_unsafety: Option<ast::Unsafety>) -> IoResult<()> {
+                            opt_unsafety: Option<ast::Unsafety>) -> io::Result<()> {
         match opt_unsafety {
             Some(unsafety) => self.print_unsafety(unsafety),
             None => Ok(())
@@ -2952,7 +2952,7 @@ pub fn print_opt_unsafety(&mut self,
 
     pub fn print_opt_abi_and_extern_if_nondefault(&mut self,
                                                   opt_abi: Option<abi::Abi>)
-        -> IoResult<()> {
+        -> io::Result<()> {
         match opt_abi {
             Some(abi::Rust) => Ok(()),
             Some(abi) => {
@@ -2964,7 +2964,7 @@ pub fn print_opt_abi_and_extern_if_nondefault(&mut self,
     }
 
     pub fn print_extern_opt_abi(&mut self,
-                                opt_abi: Option<abi::Abi>) -> IoResult<()> {
+                                opt_abi: Option<abi::Abi>) -> io::Result<()> {
         match opt_abi {
             Some(abi) => {
                 try!(self.word_nbsp("extern"));
@@ -2977,7 +2977,7 @@ pub fn print_extern_opt_abi(&mut self,
     pub fn print_fn_header_info(&mut self,
                                 opt_unsafety: Option<ast::Unsafety>,
                                 abi: abi::Abi,
-                                vis: ast::Visibility) -> IoResult<()> {
+                                vis: ast::Visibility) -> io::Result<()> {
         try!(word(&mut self.s, &visibility_qualified(vis, "")));
         try!(self.print_opt_unsafety(opt_unsafety));
 
@@ -2989,7 +2989,7 @@ pub fn print_fn_header_info(&mut self,
         word(&mut self.s, "fn")
     }
 
-    pub fn print_unsafety(&mut self, s: ast::Unsafety) -> IoResult<()> {
+    pub fn print_unsafety(&mut self, s: ast::Unsafety) -> io::Result<()> {
         match s {
             ast::Unsafety::Normal => Ok(()),
             ast::Unsafety::Unsafe => self.word_nbsp("unsafe"),
index 5bada41badfd8077b4980f4bb79deb6c6fc4066a..5e858d8a79f766b3750fa6b1b4eaee7176d3c8d4 100644 (file)
@@ -37,7 +37,7 @@
 use ptr::P;
 use util::small_vector::SmallVector;
 
-enum ShouldFail {
+enum ShouldPanic {
     No,
     Yes(Option<InternedString>),
 }
@@ -47,7 +47,7 @@ struct Test {
     path: Vec<ast::Ident> ,
     bench: bool,
     ignore: bool,
-    should_fail: ShouldFail
+    should_panic: ShouldPanic
 }
 
 struct TestCtxt<'a> {
@@ -136,7 +136,7 @@ fn fold_item(&mut self, i: P<ast::Item>) -> SmallVector<P<ast::Item>> {
                         path: self.cx.path.clone(),
                         bench: is_bench_fn(&self.cx, &*i),
                         ignore: is_ignored(&*i),
-                        should_fail: should_fail(&*i)
+                        should_panic: should_panic(&*i, self.cx.span_diagnostic)
                     };
                     self.cx.testfns.push(test);
                     self.tests.push(i.ident);
@@ -256,7 +256,8 @@ fn generate_test_harness(sess: &ParseSess,
         callee: NameAndSpan {
             name: "test".to_string(),
             format: MacroAttribute,
-            span: None
+            span: None,
+            allow_internal_unstable: false,
         }
     });
 
@@ -288,7 +289,8 @@ fn ignored_span(cx: &TestCtxt, sp: Span) -> Span {
         callee: NameAndSpan {
             name: "test".to_string(),
             format: MacroAttribute,
-            span: None
+            span: None,
+            allow_internal_unstable: true,
         }
     };
     let expn_id = cx.sess.span_diagnostic.cm.record_expansion(info);
@@ -376,15 +378,23 @@ fn is_ignored(i: &ast::Item) -> bool {
     i.attrs.iter().any(|attr| attr.check_name("ignore"))
 }
 
-fn should_fail(i: &ast::Item) -> ShouldFail {
-    match i.attrs.iter().find(|attr| attr.check_name("should_fail")) {
+fn should_panic(i: &ast::Item, diag: &diagnostic::SpanHandler) -> ShouldPanic {
+    match i.attrs.iter().find(|attr| {
+        if attr.check_name("should_panic") { return true; }
+        if attr.check_name("should_fail") {
+            diag.span_warn(attr.span, "`#[should_fail]` is deprecated. Use `#[should_panic]` \
+                                       instead");
+            return true;
+        }
+        false
+    }) {
         Some(attr) => {
             let msg = attr.meta_item_list()
                 .and_then(|list| list.iter().find(|mi| mi.check_name("expected")))
                 .and_then(|mi| mi.value_str());
-            ShouldFail::Yes(msg)
+            ShouldPanic::Yes(msg)
         }
-        None => ShouldFail::No,
+        None => ShouldPanic::No,
     }
 }
 
@@ -615,13 +625,13 @@ fn mk_test_desc_and_fn_rec(cx: &TestCtxt, test: &Test) -> P<ast::Expr> {
                                   vec![name_expr]);
 
     let ignore_expr = ecx.expr_bool(span, test.ignore);
-    let should_fail_path = |name| {
-        ecx.path(span, vec![self_id, test_id, ecx.ident_of("ShouldFail"), ecx.ident_of(name)])
+    let should_panic_path = |name| {
+        ecx.path(span, vec![self_id, test_id, ecx.ident_of("ShouldPanic"), ecx.ident_of(name)])
     };
-    let fail_expr = match test.should_fail {
-        ShouldFail::No => ecx.expr_path(should_fail_path("No")),
-        ShouldFail::Yes(ref msg) => {
-            let path = should_fail_path("Yes");
+    let fail_expr = match test.should_panic {
+        ShouldPanic::No => ecx.expr_path(should_panic_path("No")),
+        ShouldPanic::Yes(ref msg) => {
+            let path = should_panic_path("Yes");
             let arg = match *msg {
                 Some(ref msg) => ecx.expr_some(span, ecx.expr_str(span, msg.clone())),
                 None => ecx.expr_none(span),
@@ -636,7 +646,7 @@ fn mk_test_desc_and_fn_rec(cx: &TestCtxt, test: &Test) -> P<ast::Expr> {
         test_path("TestDesc"),
         vec![field("name", name_expr),
              field("ignore", ignore_expr),
-             field("should_fail", fail_expr)]);
+             field("should_panic", fail_expr)]);
 
 
     let mut visible_path = match cx.toplevel_reexport {
index 5be45a2698f40ae34c295c3e2e892994d465fc2a..7ae9e4646e516b32bee9972485f904b3f974d2d6 100644 (file)
@@ -234,7 +234,7 @@ mod tests {
     use ast::Name;
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn i1 () {
         let i : Interner<RcStr> = Interner::new();
         i.get(Name(13));
index 90df23882a1d4bf53c790a36ed40dae5ac899696..5bd6591cfb097c770cf1aa658e8e495ad91f4e97 100644 (file)
@@ -236,13 +236,13 @@ fn test_move_iter() {
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_expect_one_zero() {
         let _: isize = SmallVector::zero().expect_one("");
     }
 
     #[test]
-    #[should_fail]
+    #[should_panic]
     fn test_expect_one_many() {
         SmallVector::many(vec!(1, 2)).expect_one("");
     }
index 756d67b5db1e1a37212ee04f4e0a133d80ba856a..d3be5b5683063aa7957124f34e5bf58edb8d3699 100644 (file)
@@ -38,6 +38,8 @@
 //! [win]: http://msdn.microsoft.com/en-us/library/windows/desktop/ms682010%28v=vs.85%29.aspx
 //! [ti]: https://en.wikipedia.org/wiki/Terminfo
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "term"]
 #![unstable(feature = "rustc_private",
             reason = "use the crates.io `term` library instead")]
 #![feature(box_syntax)]
 #![feature(collections)]
 #![feature(int_uint)]
+#![feature(io)]
 #![feature(old_io)]
-#![feature(old_path)]
+#![feature(path)]
 #![feature(rustc_private)]
 #![feature(staged_api)]
-#![feature(unicode)]
 #![feature(std_misc)]
-#![feature(os)]
+#![feature(path_ext)]
 #![cfg_attr(windows, feature(libc))]
 
 #[macro_use] extern crate log;
@@ -153,23 +155,23 @@ pub mod color {
     /// Number for a terminal color
     pub type Color = u16;
 
-    pub const BLACK:   Color = 0u16;
-    pub const RED:     Color = 1u16;
-    pub const GREEN:   Color = 2u16;
-    pub const YELLOW:  Color = 3u16;
-    pub const BLUE:    Color = 4u16;
-    pub const MAGENTA: Color = 5u16;
-    pub const CYAN:    Color = 6u16;
-    pub const WHITE:   Color = 7u16;
-
-    pub const BRIGHT_BLACK:   Color = 8u16;
-    pub const BRIGHT_RED:     Color = 9u16;
-    pub const BRIGHT_GREEN:   Color = 10u16;
-    pub const BRIGHT_YELLOW:  Color = 11u16;
-    pub const BRIGHT_BLUE:    Color = 12u16;
-    pub const BRIGHT_MAGENTA: Color = 13u16;
-    pub const BRIGHT_CYAN:    Color = 14u16;
-    pub const BRIGHT_WHITE:   Color = 15u16;
+    pub const BLACK:   Color = 0;
+    pub const RED:     Color = 1;
+    pub const GREEN:   Color = 2;
+    pub const YELLOW:  Color = 3;
+    pub const BLUE:    Color = 4;
+    pub const MAGENTA: Color = 5;
+    pub const CYAN:    Color = 6;
+    pub const WHITE:   Color = 7;
+
+    pub const BRIGHT_BLACK:   Color = 8;
+    pub const BRIGHT_RED:     Color = 9;
+    pub const BRIGHT_GREEN:   Color = 10;
+    pub const BRIGHT_YELLOW:  Color = 11;
+    pub const BRIGHT_BLUE:    Color = 12;
+    pub const BRIGHT_MAGENTA: Color = 13;
+    pub const BRIGHT_CYAN:    Color = 14;
+    pub const BRIGHT_WHITE:   Color = 15;
 }
 
 /// Terminal attributes
index 112525fcce96efe2a1762a6555f4ddee0a80daa5..30b732781db1cdead56be19d692d607036eaf62b 100644 (file)
@@ -128,7 +128,7 @@ pub fn expand(cap: &[u8], params: &[Param], vars: &mut Variables)
                             // if c is 0, use 0200 (128) for ncurses compatibility
                             Number(c) => {
                                 output.push(if c == 0 {
-                                    128u8
+                                    128
                                 } else {
                                     c as u8
                                 })
@@ -647,7 +647,7 @@ fn test_push_bad_param() {
 
     #[test]
     fn test_comparison_ops() {
-        let v = [('<', [1u8, 0u8, 0u8]), ('=', [0u8, 1u8, 0u8]), ('>', [0u8, 0u8, 1u8])];
+        let v = [('<', [1, 0, 0]), ('=', [0, 1, 0]), ('>', [0, 0, 1])];
         for &(op, bs) in &v {
             let s = format!("%{{1}}%{{2}}%{}%d", op);
             let res = expand(s.as_bytes(), &[], &mut Variables::new());
index c147e6aa056dd2a916402ab636ee7dcfadd6e268..cc9a2880b5d07d10b5f8502315b1f9e9951f0798 100644 (file)
@@ -13,7 +13,8 @@
 //! ncurses-compatible compiled terminfo format parsing (term(5))
 
 use std::collections::HashMap;
-use std::old_io;
+use std::io::prelude::*;
+use std::io;
 use super::super::TermInfo;
 
 // These are the orders ncurses uses in its compiled format (as of 5.9). Not sure if portable.
     "box1"];
 
 /// Parse a compiled terminfo entry, using long capability names if `longnames` is true
-pub fn parse(file: &mut old_io::Reader, longnames: bool)
+pub fn parse(file: &mut Read, longnames: bool)
              -> Result<Box<TermInfo>, String> {
     macro_rules! try { ($e:expr) => (
         match $e {
@@ -182,17 +183,17 @@ macro_rules! try { ($e:expr) => (
     }
 
     // Check magic number
-    let magic = try!(file.read_le_u16());
+    let magic = try!(read_le_u16(file));
     if magic != 0x011A {
         return Err(format!("invalid magic number: expected {:x}, found {:x}",
                            0x011A as usize, magic as usize));
     }
 
-    let names_bytes          = try!(file.read_le_i16()) as int;
-    let bools_bytes          = try!(file.read_le_i16()) as int;
-    let numbers_count        = try!(file.read_le_i16()) as int;
-    let string_offsets_count = try!(file.read_le_i16()) as int;
-    let string_table_bytes   = try!(file.read_le_i16()) as int;
+    let names_bytes          = try!(read_le_u16(file)) as int;
+    let bools_bytes          = try!(read_le_u16(file)) as int;
+    let numbers_count        = try!(read_le_u16(file)) as int;
+    let string_offsets_count = try!(read_le_u16(file)) as int;
+    let string_table_bytes   = try!(read_le_u16(file)) as int;
 
     assert!(names_bytes          > 0);
 
@@ -212,7 +213,7 @@ macro_rules! try { ($e:expr) => (
     }
 
     // don't read NUL
-    let bytes = try!(file.read_exact(names_bytes as uint - 1));
+    let bytes = try!(read_exact(file, names_bytes as uint - 1));
     let names_str = match String::from_utf8(bytes) {
         Ok(s)  => s,
         Err(_) => return Err("input not utf-8".to_string()),
@@ -222,12 +223,12 @@ macro_rules! try { ($e:expr) => (
                                            .map(|s| s.to_string())
                                            .collect();
 
-    try!(file.read_byte()); // consume NUL
+    try!(read_byte(file)); // consume NUL
 
     let mut bools_map = HashMap::new();
     if bools_bytes != 0 {
         for i in 0..bools_bytes {
-            let b = try!(file.read_byte());
+            let b = try!(read_byte(file));
             if b == 1 {
                 bools_map.insert(bnames[i as uint].to_string(), true);
             }
@@ -235,13 +236,13 @@ macro_rules! try { ($e:expr) => (
     }
 
     if (bools_bytes + names_bytes) % 2 == 1 {
-        try!(file.read_byte()); // compensate for padding
+        try!(read_byte(file)); // compensate for padding
     }
 
     let mut numbers_map = HashMap::new();
     if numbers_count != 0 {
         for i in 0..numbers_count {
-            let n = try!(file.read_le_u16());
+            let n = try!(read_le_u16(file));
             if n != 0xFFFF {
                 numbers_map.insert(nnames[i as uint].to_string(), n);
             }
@@ -253,10 +254,10 @@ macro_rules! try { ($e:expr) => (
     if string_offsets_count != 0 {
         let mut string_offsets = Vec::with_capacity(10);
         for _ in 0..string_offsets_count {
-            string_offsets.push(try!(file.read_le_u16()));
+            string_offsets.push(try!(read_le_u16(file)));
         }
 
-        let string_table = try!(file.read_exact(string_table_bytes as uint));
+        let string_table = try!(read_exact(file, string_table_bytes as usize));
 
         if string_table.len() != string_table_bytes as uint {
             return Err("error: hit EOF before end of string \
@@ -309,6 +310,25 @@ macro_rules! try { ($e:expr) => (
     })
 }
 
+fn read_le_u16<R: Read + ?Sized>(r: &mut R) -> io::Result<u16> {
+    let mut b = [0; 2];
+    assert_eq!(try!(r.read(&mut b)), 2);
+    Ok((b[0] as u16) | ((b[1] as u16) << 8))
+}
+
+fn read_byte<R: Read + ?Sized>(r: &mut R) -> io::Result<u8> {
+    let mut b = [0; 1];
+    assert_eq!(try!(r.read(&mut b)), 1);
+    Ok(b[0])
+}
+
+fn read_exact<R: Read + ?Sized>(r: &mut R, sz: usize) -> io::Result<Vec<u8>> {
+    let mut v = Vec::with_capacity(sz);
+    try!(r.take(sz as u64).read_to_end(&mut v));
+    assert_eq!(v.len(), sz);
+    Ok(v)
+}
+
 /// Create a dummy TermInfo struct for msys terminals
 pub fn msys_terminfo() -> Box<TermInfo> {
     let mut strings = HashMap::new();
index a0cd78420700187e78aa2ef451e5ff81f0bf2a3a..f47921cbf5e6acc3e921dd04ea36b1b373a33b2e 100644 (file)
 //!
 //! Does not support hashed database, only filesystem!
 
-use std::old_io::File;
-use std::old_io::fs::PathExtensions;
 use std::env;
+use std::fs::File;
+use std::io::prelude::*;
+use std::path::PathBuf;
 
 /// Return path to database entry for `term`
 #[allow(deprecated)]
-pub fn get_dbpath_for_term(term: &str) -> Option<Box<Path>> {
+pub fn get_dbpath_for_term(term: &str) -> Option<Box<PathBuf>> {
     if term.len() == 0 {
         return None;
     }
 
-    let homedir = ::std::os::homedir();
+    let homedir = env::home_dir();
 
     let mut dirs_to_search = Vec::new();
     let first_char = term.char_at(0);
 
     // Find search directory
-    match env::var("TERMINFO") {
-        Ok(dir) => dirs_to_search.push(Path::new(dir)),
-        Err(..) => {
+    match env::var_os("TERMINFO") {
+        Some(dir) => dirs_to_search.push(PathBuf::new(&dir)),
+        None => {
             if homedir.is_some() {
                 // ncurses compatibility;
                 dirs_to_search.push(homedir.unwrap().join(".terminfo"))
@@ -39,9 +40,9 @@ pub fn get_dbpath_for_term(term: &str) -> Option<Box<Path>> {
             match env::var("TERMINFO_DIRS") {
                 Ok(dirs) => for i in dirs.split(':') {
                     if i == "" {
-                        dirs_to_search.push(Path::new("/usr/share/terminfo"));
+                        dirs_to_search.push(PathBuf::new("/usr/share/terminfo"));
                     } else {
-                        dirs_to_search.push(Path::new(i));
+                        dirs_to_search.push(PathBuf::new(i));
                     }
                 },
                 // Found nothing in TERMINFO_DIRS, use the default paths:
@@ -49,9 +50,9 @@ pub fn get_dbpath_for_term(term: &str) -> Option<Box<Path>> {
                 // ~/.terminfo, ncurses will search /etc/terminfo, then
                 // /lib/terminfo, and eventually /usr/share/terminfo.
                 Err(..) => {
-                    dirs_to_search.push(Path::new("/etc/terminfo"));
-                    dirs_to_search.push(Path::new("/lib/terminfo"));
-                    dirs_to_search.push(Path::new("/usr/share/terminfo"));
+                    dirs_to_search.push(PathBuf::new("/etc/terminfo"));
+                    dirs_to_search.push(PathBuf::new("/lib/terminfo"));
+                    dirs_to_search.push(PathBuf::new("/usr/share/terminfo"));
                 }
             }
         }
@@ -61,13 +62,13 @@ pub fn get_dbpath_for_term(term: &str) -> Option<Box<Path>> {
     for p in &dirs_to_search {
         if p.exists() {
             let f = first_char.to_string();
-            let newp = p.join_many(&[&f[..], term]);
+            let newp = p.join(&f).join(term);
             if newp.exists() {
                 return Some(box newp);
             }
             // on some installations the dir is named after the hex of the char (e.g. OS X)
             let f = format!("{:x}", first_char as uint);
-            let newp = p.join_many(&[&f[..], term]);
+            let newp = p.join(&f).join(term);
             if newp.exists() {
                 return Some(box newp);
             }
@@ -96,17 +97,17 @@ pub fn open(term: &str) -> Result<File, String> {
 fn test_get_dbpath_for_term() {
     // woefully inadequate test coverage
     // note: current tests won't work with non-standard terminfo hierarchies (e.g. OS X's)
-    use std::os::{setenv, unsetenv};
+    use std::env;
     // FIXME (#9639): This needs to handle non-utf8 paths
     fn x(t: &str) -> String {
         let p = get_dbpath_for_term(t).expect("no terminfo entry found");
-        p.as_str().unwrap().to_string()
+        p.to_str().unwrap().to_string()
     };
     assert!(x("screen") == "/usr/share/terminfo/s/screen");
     assert!(get_dbpath_for_term("") == None);
-    setenv("TERMINFO_DIRS", ":");
+    env::set_var("TERMINFO_DIRS", ":");
     assert!(x("screen") == "/usr/share/terminfo/s/screen");
-    unsetenv("TERMINFO_DIRS");
+    env::remove_var("TERMINFO_DIRS");
 }
 
 #[test]
index a144904903e58e8f7ca2d7dfcdd3da4e3926288e..1590291c88c16336a492d4a00341f77511f90231 100644 (file)
@@ -23,6 +23,8 @@
 // running tests while providing a base that other test frameworks may
 // build off of.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "test"]
 #![unstable(feature = "test")]
 #![staged_api]
 #![feature(core)]
 #![feature(int_uint)]
 #![feature(old_io)]
-#![feature(old_path)]
+#![feature(path)]
 #![feature(rustc_private)]
 #![feature(staged_api)]
 #![feature(std_misc)]
+#![feature(io)]
 
 extern crate getopts;
 extern crate serialize;
 use std::any::Any;
 use std::cmp;
 use std::collections::BTreeMap;
+use std::env;
 use std::fmt;
-use std::old_io::stdio::StdWriter;
-use std::old_io::{File, ChanReader, ChanWriter};
-use std::old_io;
+use std::fs::File;
+use std::io::{self, Write};
 use std::iter::repeat;
 use std::num::{Float, Int};
-use std::env;
+use std::old_io::stdio::StdWriter;
+use std::old_io::{ChanReader, ChanWriter};
+use std::old_io;
+use std::path::{PathBuf};
 use std::sync::mpsc::{channel, Sender};
 use std::thread;
 use std::thunk::{Thunk, Invoke};
@@ -84,7 +90,7 @@ pub mod test {
              Metric, MetricMap,
              StaticTestFn, StaticTestName, DynTestName, DynTestFn,
              run_test, test_main, test_main_static, filter_tests,
-             parse_opts, StaticBenchFn, ShouldFail};
+             parse_opts, StaticBenchFn, ShouldPanic};
 }
 
 pub mod stats;
@@ -196,7 +202,7 @@ pub struct Bencher {
 }
 
 #[derive(Copy, Clone, Debug, PartialEq, Eq, Hash)]
-pub enum ShouldFail {
+pub enum ShouldPanic {
     No,
     Yes(Option<&'static str>)
 }
@@ -207,7 +213,7 @@ pub enum ShouldFail {
 pub struct TestDesc {
     pub name: TestName,
     pub ignore: bool,
-    pub should_fail: ShouldFail,
+    pub should_panic: ShouldPanic,
 }
 
 unsafe impl Send for TestDesc {}
@@ -287,7 +293,7 @@ pub struct TestOpts {
     pub run_ignored: bool,
     pub run_tests: bool,
     pub run_benchmarks: bool,
-    pub logfile: Option<Path>,
+    pub logfile: Option<PathBuf>,
     pub nocapture: bool,
     pub color: ColorConfig,
 }
@@ -345,10 +351,10 @@ fn usage(binary: &str) {
                      takes no arguments.
     #[bench]       - Indicates a function is a benchmark to be run. This
                      function takes one argument (test::Bencher).
-    #[should_fail] - This function (also labeled with #[test]) will only pass if
-                     the code causes a failure (an assertion failure or panic!)
+    #[should_panic] - This function (also labeled with #[test]) will only pass if
+                     the code causes a panic (an assertion failure or panic!)
                      A message may be provided, which the failure string must
-                     contain: #[should_fail(expected = "foo")].
+                     contain: #[should_panic(expected = "foo")].
     #[ignore]      - When applied to a function which is already attributed as a
                      test, then the test runner will ignore these tests during
                      normal test runs. Running with --ignored will run these
@@ -376,7 +382,7 @@ pub fn parse_opts(args: &[String]) -> Option<OptRes> {
     let run_ignored = matches.opt_present("ignored");
 
     let logfile = matches.opt_str("logfile");
-    let logfile = logfile.map(|s| Path::new(s));
+    let logfile = logfile.map(|s| PathBuf::new(&s));
 
     let run_benchmarks = matches.opt_present("bench");
     let run_tests = ! run_benchmarks ||
@@ -446,11 +452,19 @@ struct ConsoleTestState<T> {
     max_name_len: uint, // number of columns to fill when aligning names
 }
 
+fn new2old(new: io::Error) -> old_io::IoError {
+    old_io::IoError {
+        kind: old_io::OtherIoError,
+        desc: "other error",
+        detail: Some(new.to_string()),
+    }
+}
+
 impl<T: Writer> ConsoleTestState<T> {
     pub fn new(opts: &TestOpts,
                _: Option<T>) -> old_io::IoResult<ConsoleTestState<StdWriter>> {
         let log_out = match opts.logfile {
-            Some(ref path) => Some(try!(File::create(path))),
+            Some(ref path) => Some(try!(File::create(path).map_err(new2old))),
             None => None
         };
         let out = match term::stdout() {
@@ -560,7 +574,7 @@ pub fn write_result(&mut self, result: &TestResult) -> old_io::IoResult<()> {
     }
 
     pub fn write_log(&mut self, test: &TestDesc,
-                     result: &TestResult) -> old_io::IoResult<()> {
+                     result: &TestResult) -> io::Result<()> {
         match self.log_out {
             None => Ok(()),
             Some(ref mut o) => {
@@ -646,7 +660,7 @@ fn callback<T: Writer>(event: &TestEvent,
             TeFiltered(ref filtered_tests) => st.write_run_start(filtered_tests.len()),
             TeWait(ref test, padding) => st.write_test_start(test, padding),
             TeResult(test, result, stdout) => {
-                try!(st.write_log(&test, &result));
+                try!(st.write_log(&test, &result).map_err(new2old));
                 try!(st.write_result(&result));
                 match result {
                     TrOk => st.passed += 1,
@@ -703,13 +717,13 @@ fn should_sort_failures_before_printing_them() {
     let test_a = TestDesc {
         name: StaticTestName("a"),
         ignore: false,
-        should_fail: ShouldFail::No
+        should_panic: ShouldPanic::No
     };
 
     let test_b = TestDesc {
         name: StaticTestName("b"),
         ignore: false,
-        should_fail: ShouldFail::No
+        should_panic: ShouldPanic::No
     };
 
     let mut st = ConsoleTestState {
@@ -732,8 +746,8 @@ fn should_sort_failures_before_printing_them() {
         Pretty(_) => unreachable!()
     };
 
-    let apos = s.find_str("a").unwrap();
-    let bpos = s.find_str("b").unwrap();
+    let apos = s.find("a").unwrap();
+    let bpos = s.find("b").unwrap();
     assert!(apos < bpos);
 }
 
@@ -939,10 +953,10 @@ fn run_test_inner(desc: TestDesc,
 }
 
 fn calc_result(desc: &TestDesc, task_result: Result<(), Box<Any+Send>>) -> TestResult {
-    match (&desc.should_fail, task_result) {
-        (&ShouldFail::No, Ok(())) |
-        (&ShouldFail::Yes(None), Err(_)) => TrOk,
-        (&ShouldFail::Yes(Some(msg)), Err(ref err))
+    match (&desc.should_panic, task_result) {
+        (&ShouldPanic::No, Ok(())) |
+        (&ShouldPanic::Yes(None), Err(_)) => TrOk,
+        (&ShouldPanic::Yes(Some(msg)), Err(ref err))
             if err.downcast_ref::<String>()
                 .map(|e| &**e)
                 .or_else(|| err.downcast_ref::<&'static str>().map(|e| *e))
@@ -1011,7 +1025,7 @@ impl Bencher {
     pub fn iter<T, F>(&mut self, mut inner: F) where F: FnMut() -> T {
         self.dur = Duration::span(|| {
             let k = self.iterations;
-            for _ in 0u64..k {
+            for _ in 0..k {
                 black_box(inner());
             }
         });
@@ -1037,7 +1051,7 @@ pub fn bench_n<F>(&mut self, n: u64, f: F) where F: FnOnce(&mut Bencher) {
     // This is a more statistics-driven benchmark algorithm
     pub fn auto_bench<F>(&mut self, mut f: F) -> stats::Summary<f64> where F: FnMut(&mut Bencher) {
         // Initial bench run to get ballpark figure.
-        let mut n = 1_u64;
+        let mut n = 1;
         self.bench_n(n, |x| f(x));
 
         // Try to estimate iter count for 1ms falling back to 1m
@@ -1095,7 +1109,14 @@ pub fn auto_bench<F>(&mut self, mut f: F) -> stats::Summary<f64> where F: FnMut(
                 return summ5;
             }
 
-            n *= 2;
+            // If we overflow here just return the results so far. We check a
+            // multiplier of 10 because we're about to multiply by 2 and the
+            // next iteration of the loop will also multiply by 5 (to calculate
+            // the summ5 result)
+            n = match n.checked_mul(10) {
+                Some(_) => n * 2,
+                None => return summ5,
+            };
         }
     }
 }
@@ -1130,7 +1151,7 @@ mod tests {
     use test::{TrFailed, TrIgnored, TrOk, filter_tests, parse_opts,
                TestDesc, TestDescAndFn, TestOpts, run_test,
                MetricMap,
-               StaticTestName, DynTestName, DynTestFn, ShouldFail};
+               StaticTestName, DynTestName, DynTestFn, ShouldPanic};
     use std::thunk::Thunk;
     use std::sync::mpsc::channel;
 
@@ -1141,7 +1162,7 @@ pub fn do_not_run_ignored_tests() {
             desc: TestDesc {
                 name: StaticTestName("whatever"),
                 ignore: true,
-                should_fail: ShouldFail::No,
+                should_panic: ShouldPanic::No,
             },
             testfn: DynTestFn(Thunk::new(move|| f())),
         };
@@ -1158,7 +1179,7 @@ fn f() { }
             desc: TestDesc {
                 name: StaticTestName("whatever"),
                 ignore: true,
-                should_fail: ShouldFail::No,
+                should_panic: ShouldPanic::No,
             },
             testfn: DynTestFn(Thunk::new(move|| f())),
         };
@@ -1169,13 +1190,13 @@ fn f() { }
     }
 
     #[test]
-    fn test_should_fail() {
+    fn test_should_panic() {
         fn f() { panic!(); }
         let desc = TestDescAndFn {
             desc: TestDesc {
                 name: StaticTestName("whatever"),
                 ignore: false,
-                should_fail: ShouldFail::Yes(None)
+                should_panic: ShouldPanic::Yes(None)
             },
             testfn: DynTestFn(Thunk::new(move|| f())),
         };
@@ -1186,13 +1207,13 @@ fn test_should_fail() {
     }
 
     #[test]
-    fn test_should_fail_good_message() {
+    fn test_should_panic_good_message() {
         fn f() { panic!("an error message"); }
         let desc = TestDescAndFn {
             desc: TestDesc {
                 name: StaticTestName("whatever"),
                 ignore: false,
-                should_fail: ShouldFail::Yes(Some("error message"))
+                should_panic: ShouldPanic::Yes(Some("error message"))
             },
             testfn: DynTestFn(Thunk::new(move|| f())),
         };
@@ -1203,13 +1224,13 @@ fn test_should_fail_good_message() {
     }
 
     #[test]
-    fn test_should_fail_bad_message() {
+    fn test_should_panic_bad_message() {
         fn f() { panic!("an error message"); }
         let desc = TestDescAndFn {
             desc: TestDesc {
                 name: StaticTestName("whatever"),
                 ignore: false,
-                should_fail: ShouldFail::Yes(Some("foobar"))
+                should_panic: ShouldPanic::Yes(Some("foobar"))
             },
             testfn: DynTestFn(Thunk::new(move|| f())),
         };
@@ -1220,13 +1241,13 @@ fn test_should_fail_bad_message() {
     }
 
     #[test]
-    fn test_should_fail_but_succeeds() {
+    fn test_should_panic_but_succeeds() {
         fn f() { }
         let desc = TestDescAndFn {
             desc: TestDesc {
                 name: StaticTestName("whatever"),
                 ignore: false,
-                should_fail: ShouldFail::Yes(None)
+                should_panic: ShouldPanic::Yes(None)
             },
             testfn: DynTestFn(Thunk::new(move|| f())),
         };
@@ -1262,7 +1283,7 @@ pub fn filter_for_ignored_option() {
                 desc: TestDesc {
                     name: StaticTestName("1"),
                     ignore: true,
-                    should_fail: ShouldFail::No,
+                    should_panic: ShouldPanic::No,
                 },
                 testfn: DynTestFn(Thunk::new(move|| {})),
             },
@@ -1270,7 +1291,7 @@ pub fn filter_for_ignored_option() {
                 desc: TestDesc {
                     name: StaticTestName("2"),
                     ignore: false,
-                    should_fail: ShouldFail::No,
+                    should_panic: ShouldPanic::No,
                 },
                 testfn: DynTestFn(Thunk::new(move|| {})),
             });
@@ -1306,7 +1327,7 @@ fn testfn() { }
                     desc: TestDesc {
                         name: DynTestName((*name).clone()),
                         ignore: false,
-                        should_fail: ShouldFail::No,
+                        should_panic: ShouldPanic::No,
                     },
                     testfn: DynTestFn(Thunk::new(testfn)),
                 };
index 7cc07e926b267b4b27b97c82e2f7c2adfd47b046..42812e1e597bccdf64514b733bb19852f01b2a1a 100644 (file)
@@ -210,11 +210,11 @@ fn max(&self) -> T {
 
     fn mean(&self) -> T {
         assert!(self.len() != 0);
-        self.sum() / FromPrimitive::from_uint(self.len()).unwrap()
+        self.sum() / FromPrimitive::from_usize(self.len()).unwrap()
     }
 
     fn median(&self) -> T {
-        self.percentile(FromPrimitive::from_uint(50).unwrap())
+        self.percentile(FromPrimitive::from_usize(50).unwrap())
     }
 
     fn var(&self) -> T {
@@ -230,7 +230,7 @@ fn var(&self) -> T {
             // NB: this is _supposed to be_ len-1, not len. If you
             // change it back to len, you will be calculating a
             // population variance, not a sample variance.
-            let denom = FromPrimitive::from_uint(self.len()-1).unwrap();
+            let denom = FromPrimitive::from_usize(self.len()-1).unwrap();
             v/denom
         }
     }
@@ -240,7 +240,7 @@ fn std_dev(&self) -> T {
     }
 
     fn std_dev_pct(&self) -> T {
-        let hundred = FromPrimitive::from_uint(100).unwrap();
+        let hundred = FromPrimitive::from_usize(100).unwrap();
         (self.std_dev() / self.mean()) * hundred
     }
 
@@ -254,7 +254,7 @@ fn median_abs_dev(&self) -> T {
     }
 
     fn median_abs_dev_pct(&self) -> T {
-        let hundred = FromPrimitive::from_uint(100).unwrap();
+        let hundred = FromPrimitive::from_usize(100).unwrap();
         (self.median_abs_dev() / self.median()) * hundred
     }
 
@@ -267,11 +267,11 @@ fn percentile(&self, pct: T) -> T {
     fn quartiles(&self) -> (T,T,T) {
         let mut tmp = self.to_vec();
         local_sort(&mut tmp);
-        let first = FromPrimitive::from_uint(25).unwrap();
+        let first = FromPrimitive::from_usize(25).unwrap();
         let a = percentile_of_sorted(&tmp, first);
-        let secound = FromPrimitive::from_uint(50).unwrap();
+        let secound = FromPrimitive::from_usize(50).unwrap();
         let b = percentile_of_sorted(&tmp, secound);
-        let third = FromPrimitive::from_uint(75).unwrap();
+        let third = FromPrimitive::from_usize(75).unwrap();
         let c = percentile_of_sorted(&tmp, third);
         (a,b,c)
     }
@@ -293,16 +293,16 @@ fn percentile_of_sorted<T: Float + FromPrimitive>(sorted_samples: &[T],
     }
     let zero: T = Float::zero();
     assert!(zero <= pct);
-    let hundred = FromPrimitive::from_uint(100).unwrap();
+    let hundred = FromPrimitive::from_usize(100).unwrap();
     assert!(pct <= hundred);
     if pct == hundred {
         return sorted_samples[sorted_samples.len() - 1];
     }
-    let length = FromPrimitive::from_uint(sorted_samples.len() - 1).unwrap();
+    let length = FromPrimitive::from_usize(sorted_samples.len() - 1).unwrap();
     let rank = (pct / hundred) * length;
     let lrank = rank.floor();
     let d = rank - lrank;
-    let n = lrank.to_uint().unwrap();
+    let n = lrank.to_usize().unwrap();
     let lo = sorted_samples[n];
     let hi = sorted_samples[n+1];
     lo + (hi - lo) * d
@@ -319,7 +319,7 @@ pub fn winsorize<T: Float + FromPrimitive>(samples: &mut [T], pct: T) {
     let mut tmp = samples.to_vec();
     local_sort(&mut tmp);
     let lo = percentile_of_sorted(&tmp, pct);
-    let hundred: T = FromPrimitive::from_uint(100).unwrap();
+    let hundred: T = FromPrimitive::from_usize(100).unwrap();
     let hi = percentile_of_sorted(&tmp, hundred-pct);
     for samp in samples {
         if *samp > hi {
diff --git a/src/libunicode/char.rs b/src/libunicode/char.rs
new file mode 100644 (file)
index 0000000..bcc2820
--- /dev/null
@@ -0,0 +1,469 @@
+// 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.
+
+//! Character manipulation (`char` type, Unicode Scalar Value)
+//!
+//! This module provides the `CharExt` trait, as well as its
+//! implementation for the primitive `char` type, in order to allow
+//! basic character manipulation.
+//!
+//! A `char` actually represents a
+//! *[Unicode Scalar
+//! Value](http://www.unicode.org/glossary/#unicode_scalar_value)*, as it can
+//! contain any Unicode code point except high-surrogate and low-surrogate code
+//! points.
+//!
+//! As such, only values in the ranges \[0x0,0xD7FF\] and \[0xE000,0x10FFFF\]
+//! (inclusive) are allowed. A `char` can always be safely cast to a `u32`;
+//! however the converse is not always true due to the above range limits
+//! and, as such, should be performed via the `from_u32` function.
+
+#![stable(feature = "rust1", since = "1.0.0")]
+#![doc(primitive = "char")]
+
+use core::char::CharExt as C;
+use core::option::Option::{self, Some};
+use core::iter::Iterator;
+use tables::{derived_property, property, general_category, conversions, charwidth};
+
+// stable reexports
+pub use core::char::{MAX, from_u32, from_digit, EscapeUnicode, EscapeDefault};
+
+// unstable reexports
+pub use normalize::{decompose_canonical, decompose_compatible, compose};
+pub use tables::normalization::canonical_combining_class;
+pub use tables::UNICODE_VERSION;
+
+/// Functionality for manipulating `char`.
+#[stable(feature = "rust1", since = "1.0.0")]
+pub trait CharExt {
+    /// Checks if a `char` parses as a numeric digit in the given radix.
+    ///
+    /// Compared to `is_numeric()`, this function only recognizes the characters
+    /// `0-9`, `a-z` and `A-Z`.
+    ///
+    /// # Return value
+    ///
+    /// Returns `true` if `c` is a valid digit under `radix`, and `false`
+    /// otherwise.
+    ///
+    /// # Panics
+    ///
+    /// Panics if given a radix > 36.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// let c = '1';
+    ///
+    /// assert!(c.is_digit(10));
+    ///
+    /// assert!('f'.is_digit(16));
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_digit(self, radix: u32) -> bool;
+
+    /// Converts a character to the corresponding digit.
+    ///
+    /// # Return value
+    ///
+    /// If `c` is between '0' and '9', the corresponding value between 0 and
+    /// 9. If `c` is 'a' or 'A', 10. If `c` is 'b' or 'B', 11, etc. Returns
+    /// none if the character does not refer to a digit in the given radix.
+    ///
+    /// # Panics
+    ///
+    /// Panics if given a radix outside the range [0..36].
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// let c = '1';
+    ///
+    /// assert_eq!(c.to_digit(10), Some(1));
+    ///
+    /// assert_eq!('f'.to_digit(16), Some(15));
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn to_digit(self, radix: u32) -> Option<u32>;
+
+    /// Returns an iterator that yields the hexadecimal Unicode escape of a
+    /// character, as `char`s.
+    ///
+    /// All characters are escaped with Rust syntax of the form `\\u{NNNN}`
+    /// where `NNNN` is the shortest hexadecimal representation of the code
+    /// point.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// for i in '❤'.escape_unicode() {
+    ///     println!("{}", i);
+    /// }
+    /// ```
+    ///
+    /// This prints:
+    ///
+    /// ```text
+    /// \
+    /// u
+    /// {
+    /// 2
+    /// 7
+    /// 6
+    /// 4
+    /// }
+    /// ```
+    ///
+    /// Collecting into a `String`:
+    ///
+    /// ```
+    /// let heart: String = '❤'.escape_unicode().collect();
+    ///
+    /// assert_eq!(heart, r"\u{2764}");
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn escape_unicode(self) -> EscapeUnicode;
+
+    /// Returns an iterator that yields the 'default' ASCII and
+    /// C++11-like literal escape of a character, as `char`s.
+    ///
+    /// The default is chosen with a bias toward producing literals that are
+    /// legal in a variety of languages, including C++11 and similar C-family
+    /// languages. The exact rules are:
+    ///
+    /// * Tab, CR and LF are escaped as '\t', '\r' and '\n' respectively.
+    /// * Single-quote, double-quote and backslash chars are backslash-
+    ///   escaped.
+    /// * Any other chars in the range [0x20,0x7e] are not escaped.
+    /// * Any other chars are given hex Unicode escapes; see `escape_unicode`.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// for i in '"'.escape_default() {
+    ///     println!("{}", i);
+    /// }
+    /// ```
+    ///
+    /// This prints:
+    ///
+    /// ```text
+    /// \
+    /// "
+    /// ```
+    ///
+    /// Collecting into a `String`:
+    ///
+    /// ```
+    /// let quote: String = '"'.escape_default().collect();
+    ///
+    /// assert_eq!(quote, "\\\"");
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn escape_default(self) -> EscapeDefault;
+
+    /// Returns the number of bytes this character would need if encoded in
+    /// UTF-8.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// let n = 'ß'.len_utf8();
+    ///
+    /// assert_eq!(n, 2);
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn len_utf8(self) -> usize;
+
+    /// Returns the number of 16-bit code units this character would need if
+    /// encoded in UTF-16.
+    ///
+    /// # Examples
+    ///
+    /// ```
+    /// let n = 'ß'.len_utf16();
+    ///
+    /// assert_eq!(n, 1);
+    /// ```
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn len_utf16(self) -> usize;
+
+    /// Encodes this character as UTF-8 into the provided byte buffer, and then
+    /// returns the number of bytes written.
+    ///
+    /// If the buffer is not large enough, nothing will be written into it and a
+    /// `None` will be returned. A buffer of length four is large enough to
+    /// encode any `char`.
+    ///
+    /// # Examples
+    ///
+    /// In both of these examples, 'ß' takes two bytes to encode.
+    ///
+    /// ```
+    /// let mut b = [0; 2];
+    ///
+    /// let result = 'ß'.encode_utf8(&mut b);
+    ///
+    /// assert_eq!(result, Some(2));
+    /// ```
+    ///
+    /// A buffer that's too small:
+    ///
+    /// ```
+    /// let mut b = [0; 1];
+    ///
+    /// let result = 'ß'.encode_utf8(&mut b);
+    ///
+    /// assert_eq!(result, None);
+    /// ```
+    #[unstable(feature = "unicode",
+               reason = "pending decision about Iterator/Writer/Reader")]
+    fn encode_utf8(self, dst: &mut [u8]) -> Option<usize>;
+
+    /// Encodes this character as UTF-16 into the provided `u16` buffer, and
+    /// then returns the number of `u16`s written.
+    ///
+    /// If the buffer is not large enough, nothing will be written into it and a
+    /// `None` will be returned. A buffer of length 2 is large enough to encode
+    /// any `char`.
+    ///
+    /// # Examples
+    ///
+    /// In both of these examples, 'ß' takes one `u16` to encode.
+    ///
+    /// ```
+    /// let mut b = [0; 1];
+    ///
+    /// let result = 'ß'.encode_utf16(&mut b);
+    ///
+    /// assert_eq!(result, Some(1));
+    /// ```
+    ///
+    /// A buffer that's too small:
+    ///
+    /// ```
+    /// let mut b = [0; 0];
+    ///
+    /// let result = 'ß'.encode_utf8(&mut b);
+    ///
+    /// assert_eq!(result, None);
+    /// ```
+    #[unstable(feature = "unicode",
+               reason = "pending decision about Iterator/Writer/Reader")]
+    fn encode_utf16(self, dst: &mut [u16]) -> Option<usize>;
+
+    /// Returns whether the specified character is considered a Unicode
+    /// alphabetic code point.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_alphabetic(self) -> bool;
+
+    /// Returns whether the specified character satisfies the 'XID_Start'
+    /// Unicode property.
+    ///
+    /// 'XID_Start' is a Unicode Derived Property specified in
+    /// [UAX #31](http://unicode.org/reports/tr31/#NFKC_Modifications),
+    /// mostly similar to ID_Start but modified for closure under NFKx.
+    #[unstable(feature = "unicode",
+               reason = "mainly needed for compiler internals")]
+    fn is_xid_start(self) -> bool;
+
+    /// Returns whether the specified `char` satisfies the 'XID_Continue'
+    /// Unicode property.
+    ///
+    /// 'XID_Continue' is a Unicode Derived Property specified in
+    /// [UAX #31](http://unicode.org/reports/tr31/#NFKC_Modifications),
+    /// mostly similar to 'ID_Continue' but modified for closure under NFKx.
+    #[unstable(feature = "unicode",
+               reason = "mainly needed for compiler internals")]
+    fn is_xid_continue(self) -> bool;
+
+    /// Indicates whether a character is in lowercase.
+    ///
+    /// This is defined according to the terms of the Unicode Derived Core
+    /// Property `Lowercase`.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_lowercase(self) -> bool;
+
+    /// Indicates whether a character is in uppercase.
+    ///
+    /// This is defined according to the terms of the Unicode Derived Core
+    /// Property `Uppercase`.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_uppercase(self) -> bool;
+
+    /// Indicates whether a character is whitespace.
+    ///
+    /// Whitespace is defined in terms of the Unicode Property `White_Space`.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_whitespace(self) -> bool;
+
+    /// Indicates whether a character is alphanumeric.
+    ///
+    /// Alphanumericness is defined in terms of the Unicode General Categories
+    /// 'Nd', 'Nl', 'No' and the Derived Core Property 'Alphabetic'.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_alphanumeric(self) -> bool;
+
+    /// Indicates whether a character is a control code point.
+    ///
+    /// Control code points are defined in terms of the Unicode General
+    /// Category `Cc`.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_control(self) -> bool;
+
+    /// Indicates whether the character is numeric (Nd, Nl, or No).
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn is_numeric(self) -> bool;
+
+    /// Converts a character to its lowercase equivalent.
+    ///
+    /// The case-folding performed is the common or simple mapping. See
+    /// `to_uppercase()` for references and more information.
+    ///
+    /// # Return value
+    ///
+    /// Returns an iterator which yields the characters corresponding to the
+    /// lowercase equivalent of the character. If no conversion is possible then
+    /// the input character is returned.
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn to_lowercase(self) -> ToLowercase;
+
+    /// Converts a character to its uppercase equivalent.
+    ///
+    /// The case-folding performed is the common or simple mapping: it maps
+    /// one Unicode codepoint to its uppercase equivalent according to the
+    /// Unicode database [1]. The additional [`SpecialCasing.txt`] is not yet
+    /// considered here, but the iterator returned will soon support this form
+    /// of case folding.
+    ///
+    /// A full reference can be found here [2].
+    ///
+    /// # Return value
+    ///
+    /// Returns an iterator which yields the characters corresponding to the
+    /// uppercase equivalent of the character. If no conversion is possible then
+    /// the input character is returned.
+    ///
+    /// [1]: ftp://ftp.unicode.org/Public/UNIDATA/UnicodeData.txt
+    ///
+    /// [`SpecialCasing`.txt`]: ftp://ftp.unicode.org/Public/UNIDATA/SpecialCasing.txt
+    ///
+    /// [2]: http://www.unicode.org/versions/Unicode4.0.0/ch03.pdf#G33992
+    #[stable(feature = "rust1", since = "1.0.0")]
+    fn to_uppercase(self) -> ToUppercase;
+
+    /// Returns this character's displayed width in columns, or `None` if it is a
+    /// control character other than `'\x00'`.
+    ///
+    /// `is_cjk` determines behavior for characters in the Ambiguous category:
+    /// if `is_cjk` is `true`, these are 2 columns wide; otherwise, they are 1.
+    /// In CJK contexts, `is_cjk` should be `true`, else it should be `false`.
+    /// [Unicode Standard Annex #11](http://www.unicode.org/reports/tr11/)
+    /// recommends that these characters be treated as 1 column (i.e.,
+    /// `is_cjk` = `false`) if the context cannot be reliably determined.
+    #[unstable(feature = "unicode",
+               reason = "needs expert opinion. is_cjk flag stands out as ugly")]
+    fn width(self, is_cjk: bool) -> Option<usize>;
+}
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl CharExt for char {
+    fn is_digit(self, radix: u32) -> bool { C::is_digit(self, radix) }
+    fn to_digit(self, radix: u32) -> Option<u32> { C::to_digit(self, radix) }
+    fn escape_unicode(self) -> EscapeUnicode { C::escape_unicode(self) }
+    fn escape_default(self) -> EscapeDefault { C::escape_default(self) }
+    fn len_utf8(self) -> usize { C::len_utf8(self) }
+    fn len_utf16(self) -> usize { C::len_utf16(self) }
+    fn encode_utf8(self, dst: &mut [u8]) -> Option<usize> { C::encode_utf8(self, dst) }
+    fn encode_utf16(self, dst: &mut [u16]) -> Option<usize> { C::encode_utf16(self, dst) }
+
+    fn is_alphabetic(self) -> bool {
+        match self {
+            'a' ... 'z' | 'A' ... 'Z' => true,
+            c if c > '\x7f' => derived_property::Alphabetic(c),
+            _ => false
+        }
+    }
+
+    fn is_xid_start(self) -> bool { derived_property::XID_Start(self) }
+
+    fn is_xid_continue(self) -> bool { derived_property::XID_Continue(self) }
+
+    fn is_lowercase(self) -> bool {
+        match self {
+            'a' ... 'z' => true,
+            c if c > '\x7f' => derived_property::Lowercase(c),
+            _ => false
+        }
+    }
+
+    fn is_uppercase(self) -> bool {
+        match self {
+            'A' ... 'Z' => true,
+            c if c > '\x7f' => derived_property::Uppercase(c),
+            _ => false
+        }
+    }
+
+    fn is_whitespace(self) -> bool {
+        match self {
+            ' ' | '\x09' ... '\x0d' => true,
+            c if c > '\x7f' => property::White_Space(c),
+            _ => false
+        }
+    }
+
+    fn is_alphanumeric(self) -> bool {
+        self.is_alphabetic() || self.is_numeric()
+    }
+
+    fn is_control(self) -> bool { general_category::Cc(self) }
+
+    fn is_numeric(self) -> bool {
+        match self {
+            '0' ... '9' => true,
+            c if c > '\x7f' => general_category::N(c),
+            _ => false
+        }
+    }
+
+    fn to_lowercase(self) -> ToLowercase {
+        ToLowercase(Some(conversions::to_lower(self)))
+    }
+
+    fn to_uppercase(self) -> ToUppercase {
+        ToUppercase(Some(conversions::to_upper(self)))
+    }
+
+    fn width(self, is_cjk: bool) -> Option<usize> { charwidth::width(self, is_cjk) }
+}
+
+/// An iterator over the lowercase mapping of a given character, returned from
+/// the `lowercase` method on characters.
+#[stable(feature = "rust1", since = "1.0.0")]
+pub struct ToLowercase(Option<char>);
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl Iterator for ToLowercase {
+    type Item = char;
+    fn next(&mut self) -> Option<char> { self.0.take() }
+}
+
+/// An iterator over the uppercase mapping of a given character, returned from
+/// the `uppercase` method on characters.
+#[stable(feature = "rust1", since = "1.0.0")]
+pub struct ToUppercase(Option<char>);
+
+#[stable(feature = "rust1", since = "1.0.0")]
+impl Iterator for ToUppercase {
+    type Item = char;
+    fn next(&mut self) -> Option<char> { self.0.take() }
+}
index 791886be1ce5b6a6de76889ca83bc7d7f53a3f7e..fadf91f33bce83a3a6d667b3266ddb08ddfb27c0 100644 (file)
@@ -20,6 +20,8 @@
 //! provide for basic string-related manipulations. This crate does not
 //! (yet) aim to provide a full set of Unicode tables.
 
+// Do not remove on snapshot creation. Needed for bootstrap. (Issue #22364)
+#![cfg_attr(stage0, feature(custom_attribute))]
 #![crate_name = "unicode"]
 #![unstable(feature = "unicode")]
 #![feature(staged_api)]
 
 mod normalize;
 mod tables;
-mod u_char;
 mod u_str;
-
-// re-export char so that std et al see it correctly
-/// Character manipulation (`char` type, Unicode Scalar Value)
-///
-/// This module provides the `CharExt` trait, as well as its
-/// implementation for the primitive `char` type, in order to allow
-/// basic character manipulation.
-///
-/// A `char` actually represents a
-/// *[Unicode Scalar Value](http://www.unicode.org/glossary/#unicode_scalar_value)*,
-/// as it can contain any Unicode code point except high-surrogate and
-/// low-surrogate code points.
-///
-/// As such, only values in the ranges \[0x0,0xD7FF\] and \[0xE000,0x10FFFF\]
-/// (inclusive) are allowed. A `char` can always be safely cast to a `u32`;
-/// however the converse is not always true due to the above range limits
-/// and, as such, should be performed via the `from_u32` function.
-#[stable(feature = "rust1", since = "1.0.0")]
-#[doc(primitive = "char")]
-pub mod char {
-    pub use core::char::{MAX, from_u32, from_digit};
-
-    pub use normalize::{decompose_canonical, decompose_compatible, compose};
-
-    pub use tables::normalization::canonical_combining_class;
-    pub use tables::UNICODE_VERSION;
-
-    pub use u_char::CharExt;
-}
+pub mod char;
 
 pub mod str {
     pub use u_str::{UnicodeStr, Words, Graphemes, GraphemeIndices};
index 61f447a3dd3b687a836c4f17f308aabd76ab41ca..1fb6ee7bc7ce1952c59d0f0dd579b6b6e86413e3 100644 (file)
@@ -27,7 +27,7 @@ fn bsearch_range_table(c: char, r: &'static [(char,char)]) -> bool {
 }
 
 pub mod general_category {
-    pub static C_table: &'static [(char, char)] = &[
+    pub const C_table: &'static [(char, char)] = &[
         ('\u{0}', '\u{1f}'), ('\u{7f}', '\u{9f}'), ('\u{ad}', '\u{ad}'), ('\u{378}', '\u{379}'),
         ('\u{380}', '\u{383}'), ('\u{38b}', '\u{38b}'), ('\u{38d}', '\u{38d}'), ('\u{3a2}',
         '\u{3a2}'), ('\u{530}', '\u{530}'), ('\u{557}', '\u{558}'), ('\u{560}', '\u{560}'),
@@ -115,27 +115,26 @@ pub mod general_category {
         '\u{2eff}'), ('\u{2fd6}', '\u{2fef}'), ('\u{2ffc}', '\u{2fff}'), ('\u{3040}', '\u{3040}'),
         ('\u{3097}', '\u{3098}'), ('\u{3100}', '\u{3104}'), ('\u{312e}', '\u{3130}'), ('\u{318f}',
         '\u{318f}'), ('\u{31bb}', '\u{31bf}'), ('\u{31e4}', '\u{31ef}'), ('\u{321f}', '\u{321f}'),
-        ('\u{32ff}', '\u{32ff}'), ('\u{3401}', '\u{4db4}'), ('\u{4db6}', '\u{4dbf}'), ('\u{4e01}',
-        '\u{9fcb}'), ('\u{9fcd}', '\u{9fff}'), ('\u{a48d}', '\u{a48f}'), ('\u{a4c7}', '\u{a4cf}'),
-        ('\u{a62c}', '\u{a63f}'), ('\u{a69e}', '\u{a69e}'), ('\u{a6f8}', '\u{a6ff}'), ('\u{a78f}',
-        '\u{a78f}'), ('\u{a7ae}', '\u{a7af}'), ('\u{a7b2}', '\u{a7f6}'), ('\u{a82c}', '\u{a82f}'),
-        ('\u{a83a}', '\u{a83f}'), ('\u{a878}', '\u{a87f}'), ('\u{a8c5}', '\u{a8cd}'), ('\u{a8da}',
-        '\u{a8df}'), ('\u{a8fc}', '\u{a8ff}'), ('\u{a954}', '\u{a95e}'), ('\u{a97d}', '\u{a97f}'),
-        ('\u{a9ce}', '\u{a9ce}'), ('\u{a9da}', '\u{a9dd}'), ('\u{a9ff}', '\u{a9ff}'), ('\u{aa37}',
-        '\u{aa3f}'), ('\u{aa4e}', '\u{aa4f}'), ('\u{aa5a}', '\u{aa5b}'), ('\u{aac3}', '\u{aada}'),
-        ('\u{aaf7}', '\u{ab00}'), ('\u{ab07}', '\u{ab08}'), ('\u{ab0f}', '\u{ab10}'), ('\u{ab17}',
-        '\u{ab1f}'), ('\u{ab27}', '\u{ab27}'), ('\u{ab2f}', '\u{ab2f}'), ('\u{ab60}', '\u{ab63}'),
-        ('\u{ab66}', '\u{abbf}'), ('\u{abee}', '\u{abef}'), ('\u{abfa}', '\u{abff}'), ('\u{ac01}',
-        '\u{d7a2}'), ('\u{d7a4}', '\u{d7af}'), ('\u{d7c7}', '\u{d7ca}'), ('\u{d7fc}', '\u{d7ff}'),
-        ('\u{e000}', '\u{f8ff}'), ('\u{fa6e}', '\u{fa6f}'), ('\u{fada}', '\u{faff}'), ('\u{fb07}',
-        '\u{fb12}'), ('\u{fb18}', '\u{fb1c}'), ('\u{fb37}', '\u{fb37}'), ('\u{fb3d}', '\u{fb3d}'),
-        ('\u{fb3f}', '\u{fb3f}'), ('\u{fb42}', '\u{fb42}'), ('\u{fb45}', '\u{fb45}'), ('\u{fbc2}',
-        '\u{fbd2}'), ('\u{fd40}', '\u{fd4f}'), ('\u{fd90}', '\u{fd91}'), ('\u{fdc8}', '\u{fdef}'),
-        ('\u{fdfe}', '\u{fdff}'), ('\u{fe1a}', '\u{fe1f}'), ('\u{fe2e}', '\u{fe2f}'), ('\u{fe53}',
-        '\u{fe53}'), ('\u{fe67}', '\u{fe67}'), ('\u{fe6c}', '\u{fe6f}'), ('\u{fe75}', '\u{fe75}'),
-        ('\u{fefd}', '\u{ff00}'), ('\u{ffbf}', '\u{ffc1}'), ('\u{ffc8}', '\u{ffc9}'), ('\u{ffd0}',
-        '\u{ffd1}'), ('\u{ffd8}', '\u{ffd9}'), ('\u{ffdd}', '\u{ffdf}'), ('\u{ffe7}', '\u{ffe7}'),
-        ('\u{ffef}', '\u{fffb}'), ('\u{fffe}', '\u{ffff}'), ('\u{1000c}', '\u{1000c}'),
+        ('\u{32ff}', '\u{32ff}'), ('\u{4db6}', '\u{4dbf}'), ('\u{9fcd}', '\u{9fff}'), ('\u{a48d}',
+        '\u{a48f}'), ('\u{a4c7}', '\u{a4cf}'), ('\u{a62c}', '\u{a63f}'), ('\u{a69e}', '\u{a69e}'),
+        ('\u{a6f8}', '\u{a6ff}'), ('\u{a78f}', '\u{a78f}'), ('\u{a7ae}', '\u{a7af}'), ('\u{a7b2}',
+        '\u{a7f6}'), ('\u{a82c}', '\u{a82f}'), ('\u{a83a}', '\u{a83f}'), ('\u{a878}', '\u{a87f}'),
+        ('\u{a8c5}', '\u{a8cd}'), ('\u{a8da}', '\u{a8df}'), ('\u{a8fc}', '\u{a8ff}'), ('\u{a954}',
+        '\u{a95e}'), ('\u{a97d}', '\u{a97f}'), ('\u{a9ce}', '\u{a9ce}'), ('\u{a9da}', '\u{a9dd}'),
+        ('\u{a9ff}', '\u{a9ff}'), ('\u{aa37}', '\u{aa3f}'), ('\u{aa4e}', '\u{aa4f}'), ('\u{aa5a}',
+        '\u{aa5b}'), ('\u{aac3}', '\u{aada}'), ('\u{aaf7}', '\u{ab00}'), ('\u{ab07}', '\u{ab08}'),
+        ('\u{ab0f}', '\u{ab10}'), ('\u{ab17}', '\u{ab1f}'), ('\u{ab27}', '\u{ab27}'), ('\u{ab2f}',
+        '\u{ab2f}'), ('\u{ab60}', '\u{ab63}'), ('\u{ab66}', '\u{abbf}'), ('\u{abee}', '\u{abef}'),
+        ('\u{abfa}', '\u{abff}'), ('\u{d7a4}', '\u{d7af}'), ('\u{d7c7}', '\u{d7ca}'), ('\u{d7fc}',
+        '\u{d7ff}'), ('\u{e000}', '\u{f8ff}'), ('\u{fa6e}', '\u{fa6f}'), ('\u{fada}', '\u{faff}'),
+        ('\u{fb07}', '\u{fb12}'), ('\u{fb18}', '\u{fb1c}'), ('\u{fb37}', '\u{fb37}'), ('\u{fb3d}',
+        '\u{fb3d}'), ('\u{fb3f}', '\u{fb3f}'), ('\u{fb42}', '\u{fb42}'), ('\u{fb45}', '\u{fb45}'),
+        ('\u{fbc2}', '\u{fbd2}'), ('\u{fd40}', '\u{fd4f}'), ('\u{fd90}', '\u{fd91}'), ('\u{fdc8}',
+        '\u{fdef}'), ('\u{fdfe}', '\u{fdff}'), ('\u{fe1a}', '\u{fe1f}'), ('\u{fe2e}', '\u{fe2f}'),
+        ('\u{fe53}', '\u{fe53}'), ('\u{fe67}', '\u{fe67}'), ('\u{fe6c}', '\u{fe6f}'), ('\u{fe75}',
+        '\u{fe75}'), ('\u{fefd}', '\u{ff00}'), ('\u{ffbf}', '\u{ffc1}'), ('\u{ffc8}', '\u{ffc9}'),
+        ('\u{ffd0}', '\u{ffd1}'), ('\u{ffd8}', '\u{ffd9}'), ('\u{ffdd}', '\u{ffdf}'), ('\u{ffe7}',
+        '\u{ffe7}'), ('\u{ffef}', '\u{fffb}'), ('\u{fffe}', '\u{ffff}'), ('\u{1000c}', '\u{1000c}'),
         ('\u{10027}', '\u{10027}'), ('\u{1003b}', '\u{1003b}'), ('\u{1003e}', '\u{1003e}'),
         ('\u{1004e}', '\u{1004f}'), ('\u{1005e}', '\u{1007f}'), ('\u{100fb}', '\u{100ff}'),
         ('\u{10103}', '\u{10106}'), ('\u{10134}', '\u{10136}'), ('\u{1018d}', '\u{1018f}'),
@@ -210,13 +209,12 @@ pub mod general_category {
         ('\u{1f643}', '\u{1f644}'), ('\u{1f6d0}', '\u{1f6df}'), ('\u{1f6ed}', '\u{1f6ef}'),
         ('\u{1f6f4}', '\u{1f6ff}'), ('\u{1f774}', '\u{1f77f}'), ('\u{1f7d5}', '\u{1f7ff}'),
         ('\u{1f80c}', '\u{1f80f}'), ('\u{1f848}', '\u{1f84f}'), ('\u{1f85a}', '\u{1f85f}'),
-        ('\u{1f888}', '\u{1f88f}'), ('\u{1f8ae}', '\u{1ffff}'), ('\u{20001}', '\u{2a6d5}'),
-        ('\u{2a6d7}', '\u{2a6ff}'), ('\u{2a701}', '\u{2b733}'), ('\u{2b735}', '\u{2b73f}'),
-        ('\u{2b741}', '\u{2b81c}'), ('\u{2b81e}', '\u{2f7ff}'), ('\u{2fa1e}', '\u{e00ff}'),
+        ('\u{1f888}', '\u{1f88f}'), ('\u{1f8ae}', '\u{1ffff}'), ('\u{2a6d7}', '\u{2a6ff}'),
+        ('\u{2b735}', '\u{2b73f}'), ('\u{2b81e}', '\u{2f7ff}'), ('\u{2fa1e}', '\u{e00ff}'),
         ('\u{e01f0}', '\u{10ffff}')
     ];
 
-    pub static Cc_table: &'static [(char, char)] = &[
+    pub const Cc_table: &'static [(char, char)] = &[
         ('\u{0}', '\u{1f}'), ('\u{7f}', '\u{9f}')
     ];
 
@@ -224,7 +222,7 @@ pub fn Cc(c: char) -> bool {
         super::bsearch_range_table(c, Cc_table)
     }
 
-    pub static Cf_table: &'static [(char, char)] = &[
+    pub const Cf_table: &'static [(char, char)] = &[
         ('\u{ad}', '\u{ad}'), ('\u{600}', '\u{605}'), ('\u{61c}', '\u{61c}'), ('\u{6dd}',
         '\u{6dd}'), ('\u{70f}', '\u{70f}'), ('\u{180e}', '\u{180e}'), ('\u{200b}', '\u{200f}'),
         ('\u{202a}', '\u{202e}'), ('\u{2060}', '\u{2064}'), ('\u{2066}', '\u{206f}'), ('\u{feff}',
@@ -233,7 +231,7 @@ pub fn Cc(c: char) -> bool {
         '\u{e007f}')
     ];
 
-    pub static Cn_table: &'static [(char, char)] = &[
+    pub const Cn_table: &'static [(char, char)] = &[
         ('\u{378}', '\u{379}'), ('\u{380}', '\u{383}'), ('\u{38b}', '\u{38b}'), ('\u{38d}',
         '\u{38d}'), ('\u{3a2}', '\u{3a2}'), ('\u{530}', '\u{530}'), ('\u{557}', '\u{558}'),
         ('\u{560}', '\u{560}'), ('\u{588}', '\u{588}'), ('\u{58b}', '\u{58c}'), ('\u{590}',
@@ -319,115 +317,111 @@ pub fn Cc(c: char) -> bool {
         ('\u{2e9a}', '\u{2e9a}'), ('\u{2ef4}', '\u{2eff}'), ('\u{2fd6}', '\u{2fef}'), ('\u{2ffc}',
         '\u{2fff}'), ('\u{3040}', '\u{3040}'), ('\u{3097}', '\u{3098}'), ('\u{3100}', '\u{3104}'),
         ('\u{312e}', '\u{3130}'), ('\u{318f}', '\u{318f}'), ('\u{31bb}', '\u{31bf}'), ('\u{31e4}',
-        '\u{31ef}'), ('\u{321f}', '\u{321f}'), ('\u{32ff}', '\u{32ff}'), ('\u{3401}', '\u{4db4}'),
-        ('\u{4db6}', '\u{4dbf}'), ('\u{4e01}', '\u{9fcb}'), ('\u{9fcd}', '\u{9fff}'), ('\u{a48d}',
-        '\u{a48f}'), ('\u{a4c7}', '\u{a4cf}'), ('\u{a62c}', '\u{a63f}'), ('\u{a69e}', '\u{a69e}'),
-        ('\u{a6f8}', '\u{a6ff}'), ('\u{a78f}', '\u{a78f}'), ('\u{a7ae}', '\u{a7af}'), ('\u{a7b2}',
-        '\u{a7f6}'), ('\u{a82c}', '\u{a82f}'), ('\u{a83a}', '\u{a83f}'), ('\u{a878}', '\u{a87f}'),
-        ('\u{a8c5}', '\u{a8cd}'), ('\u{a8da}', '\u{a8df}'), ('\u{a8fc}', '\u{a8ff}'), ('\u{a954}',
-        '\u{a95e}'), ('\u{a97d}', '\u{a97f}'), ('\u{a9ce}', '\u{a9ce}'), ('\u{a9da}', '\u{a9dd}'),
-        ('\u{a9ff}', '\u{a9ff}'), ('\u{aa37}', '\u{aa3f}'), ('\u{aa4e}', '\u{aa4f}'), ('\u{aa5a}',
-        '\u{aa5b}'), ('\u{aac3}', '\u{aada}'), ('\u{aaf7}', '\u{ab00}'), ('\u{ab07}', '\u{ab08}'),
-        ('\u{ab0f}', '\u{ab10}'), ('\u{ab17}', '\u{ab1f}'), ('\u{ab27}', '\u{ab27}'), ('\u{ab2f}',
-        '\u{ab2f}'), ('\u{ab60}', '\u{ab63}'), ('\u{ab66}', '\u{abbf}'), ('\u{abee}', '\u{abef}'),
-        ('\u{abfa}', '\u{abff}'), ('\u{ac01}', '\u{d7a2}'), ('\u{d7a4}', '\u{d7af}'), ('\u{d7c7}',
-        '\u{d7ca}'), ('\u{d7fc}', '\u{d7ff}'), ('\u{e001}', '\u{f8fe}'), ('\u{fa6e}', '\u{fa6f}'),
-        ('\u{fada}', '\u{faff}'), ('\u{fb07}', '\u{fb12}'), ('\u{fb18}', '\u{fb1c}'), ('\u{fb37}',
-        '\u{fb37}'), ('\u{fb3d}', '\u{fb3d}'), ('\u{fb3f}', '\u{fb3f}'), ('\u{fb42}', '\u{fb42}'),
-        ('\u{fb45}', '\u{fb45}'), ('\u{fbc2}', '\u{fbd2}'), ('\u{fd40}', '\u{fd4f}'), ('\u{fd90}',
-        '\u{fd91}'), ('\u{fdc8}', '\u{fdef}'), ('\u{fdfe}', '\u{fdff}'), ('\u{fe1a}', '\u{fe1f}'),
-        ('\u{fe2e}', '\u{fe2f}'), ('\u{fe53}', '\u{fe53}'), ('\u{fe67}', '\u{fe67}'), ('\u{fe6c}',
-        '\u{fe6f}'), ('\u{fe75}', '\u{fe75}'), ('\u{fefd}', '\u{fefe}'), ('\u{ff00}', '\u{ff00}'),
-        ('\u{ffbf}', '\u{ffc1}'), ('\u{ffc8}', '\u{ffc9}'), ('\u{ffd0}', '\u{ffd1}'), ('\u{ffd8}',
-        '\u{ffd9}'), ('\u{ffdd}', '\u{ffdf}'), ('\u{ffe7}', '\u{ffe7}'), ('\u{ffef}', '\u{fff8}'),
-        ('\u{fffe}', '\u{ffff}'), ('\u{1000c}', '\u{1000c}'), ('\u{10027}', '\u{10027}'),
-        ('\u{1003b}', '\u{1003b}'), ('\u{1003e}', '\u{1003e}'), ('\u{1004e}', '\u{1004f}'),
-        ('\u{1005e}', '\u{1007f}'), ('\u{100fb}', '\u{100ff}'), ('\u{10103}', '\u{10106}'),
-        ('\u{10134}', '\u{10136}'), ('\u{1018d}', '\u{1018f}'), ('\u{1019c}', '\u{1019f}'),
-        ('\u{101a1}', '\u{101cf}'), ('\u{101fe}', '\u{1027f}'), ('\u{1029d}', '\u{1029f}'),
-        ('\u{102d1}', '\u{102df}'), ('\u{102fc}', '\u{102ff}'), ('\u{10324}', '\u{1032f}'),
-        ('\u{1034b}', '\u{1034f}'), ('\u{1037b}', '\u{1037f}'), ('\u{1039e}', '\u{1039e}'),
-        ('\u{103c4}', '\u{103c7}'), ('\u{103d6}', '\u{103ff}'), ('\u{1049e}', '\u{1049f}'),
-        ('\u{104aa}', '\u{104ff}'), ('\u{10528}', '\u{1052f}'), ('\u{10564}', '\u{1056e}'),
-        ('\u{10570}', '\u{105ff}'), ('\u{10737}', '\u{1073f}'), ('\u{10756}', '\u{1075f}'),
-        ('\u{10768}', '\u{107ff}'), ('\u{10806}', '\u{10807}'), ('\u{10809}', '\u{10809}'),
-        ('\u{10836}', '\u{10836}'), ('\u{10839}', '\u{1083b}'), ('\u{1083d}', '\u{1083e}'),
-        ('\u{10856}', '\u{10856}'), ('\u{1089f}', '\u{108a6}'), ('\u{108b0}', '\u{108ff}'),
-        ('\u{1091c}', '\u{1091e}'), ('\u{1093a}', '\u{1093e}'), ('\u{10940}', '\u{1097f}'),
-        ('\u{109b8}', '\u{109bd}'), ('\u{109c0}', '\u{109ff}'), ('\u{10a04}', '\u{10a04}'),
-        ('\u{10a07}', '\u{10a0b}'), ('\u{10a14}', '\u{10a14}'), ('\u{10a18}', '\u{10a18}'),
-        ('\u{10a34}', '\u{10a37}'), ('\u{10a3b}', '\u{10a3e}'), ('\u{10a48}', '\u{10a4f}'),
-        ('\u{10a59}', '\u{10a5f}'), ('\u{10aa0}', '\u{10abf}'), ('\u{10ae7}', '\u{10aea}'),
-        ('\u{10af7}', '\u{10aff}'), ('\u{10b36}', '\u{10b38}'), ('\u{10b56}', '\u{10b57}'),
-        ('\u{10b73}', '\u{10b77}'), ('\u{10b92}', '\u{10b98}'), ('\u{10b9d}', '\u{10ba8}'),
-        ('\u{10bb0}', '\u{10bff}'), ('\u{10c49}', '\u{10e5f}'), ('\u{10e7f}', '\u{10fff}'),
-        ('\u{1104e}', '\u{11051}'), ('\u{11070}', '\u{1107e}'), ('\u{110c2}', '\u{110cf}'),
-        ('\u{110e9}', '\u{110ef}'), ('\u{110fa}', '\u{110ff}'), ('\u{11135}', '\u{11135}'),
-        ('\u{11144}', '\u{1114f}'), ('\u{11177}', '\u{1117f}'), ('\u{111c9}', '\u{111cc}'),
-        ('\u{111ce}', '\u{111cf}'), ('\u{111db}', '\u{111e0}'), ('\u{111f5}', '\u{111ff}'),
-        ('\u{11212}', '\u{11212}'), ('\u{1123e}', '\u{112af}'), ('\u{112eb}', '\u{112ef}'),
-        ('\u{112fa}', '\u{11300}'), ('\u{11304}', '\u{11304}'), ('\u{1130d}', '\u{1130e}'),
-        ('\u{11311}', '\u{11312}'), ('\u{11329}', '\u{11329}'), ('\u{11331}', '\u{11331}'),
-        ('\u{11334}', '\u{11334}'), ('\u{1133a}', '\u{1133b}'), ('\u{11345}', '\u{11346}'),
-        ('\u{11349}', '\u{1134a}'), ('\u{1134e}', '\u{11356}'), ('\u{11358}', '\u{1135c}'),
-        ('\u{11364}', '\u{11365}'), ('\u{1136d}', '\u{1136f}'), ('\u{11375}', '\u{1147f}'),
-        ('\u{114c8}', '\u{114cf}'), ('\u{114da}', '\u{1157f}'), ('\u{115b6}', '\u{115b7}'),
-        ('\u{115ca}', '\u{115ff}'), ('\u{11645}', '\u{1164f}'), ('\u{1165a}', '\u{1167f}'),
-        ('\u{116b8}', '\u{116bf}'), ('\u{116ca}', '\u{1189f}'), ('\u{118f3}', '\u{118fe}'),
-        ('\u{11900}', '\u{11abf}'), ('\u{11af9}', '\u{11fff}'), ('\u{12399}', '\u{123ff}'),
-        ('\u{1246f}', '\u{1246f}'), ('\u{12475}', '\u{12fff}'), ('\u{1342f}', '\u{167ff}'),
-        ('\u{16a39}', '\u{16a3f}'), ('\u{16a5f}', '\u{16a5f}'), ('\u{16a6a}', '\u{16a6d}'),
-        ('\u{16a70}', '\u{16acf}'), ('\u{16aee}', '\u{16aef}'), ('\u{16af6}', '\u{16aff}'),
-        ('\u{16b46}', '\u{16b4f}'), ('\u{16b5a}', '\u{16b5a}'), ('\u{16b62}', '\u{16b62}'),
-        ('\u{16b78}', '\u{16b7c}'), ('\u{16b90}', '\u{16eff}'), ('\u{16f45}', '\u{16f4f}'),
-        ('\u{16f7f}', '\u{16f8e}'), ('\u{16fa0}', '\u{1afff}'), ('\u{1b002}', '\u{1bbff}'),
-        ('\u{1bc6b}', '\u{1bc6f}'), ('\u{1bc7d}', '\u{1bc7f}'), ('\u{1bc89}', '\u{1bc8f}'),
-        ('\u{1bc9a}', '\u{1bc9b}'), ('\u{1bca4}', '\u{1cfff}'), ('\u{1d0f6}', '\u{1d0ff}'),
-        ('\u{1d127}', '\u{1d128}'), ('\u{1d1de}', '\u{1d1ff}'), ('\u{1d246}', '\u{1d2ff}'),
-        ('\u{1d357}', '\u{1d35f}'), ('\u{1d372}', '\u{1d3ff}'), ('\u{1d455}', '\u{1d455}'),
-        ('\u{1d49d}', '\u{1d49d}'), ('\u{1d4a0}', '\u{1d4a1}'), ('\u{1d4a3}', '\u{1d4a4}'),
-        ('\u{1d4a7}', '\u{1d4a8}'), ('\u{1d4ad}', '\u{1d4ad}'), ('\u{1d4ba}', '\u{1d4ba}'),
-        ('\u{1d4bc}', '\u{1d4bc}'), ('\u{1d4c4}', '\u{1d4c4}'), ('\u{1d506}', '\u{1d506}'),
-        ('\u{1d50b}', '\u{1d50c}'), ('\u{1d515}', '\u{1d515}'), ('\u{1d51d}', '\u{1d51d}'),
-        ('\u{1d53a}', '\u{1d53a}'), ('\u{1d53f}', '\u{1d53f}'), ('\u{1d545}', '\u{1d545}'),
-        ('\u{1d547}', '\u{1d549}'), ('\u{1d551}', '\u{1d551}'), ('\u{1d6a6}', '\u{1d6a7}'),
-        ('\u{1d7cc}', '\u{1d7cd}'), ('\u{1d800}', '\u{1e7ff}'), ('\u{1e8c5}', '\u{1e8c6}'),
-        ('\u{1e8d7}', '\u{1edff}'), ('\u{1ee04}', '\u{1ee04}'), ('\u{1ee20}', '\u{1ee20}'),
-        ('\u{1ee23}', '\u{1ee23}'), ('\u{1ee25}', '\u{1ee26}'), ('\u{1ee28}', '\u{1ee28}'),
-        ('\u{1ee33}', '\u{1ee33}'), ('\u{1ee38}', '\u{1ee38}'), ('\u{1ee3a}', '\u{1ee3a}'),
-        ('\u{1ee3c}', '\u{1ee41}'), ('\u{1ee43}', '\u{1ee46}'), ('\u{1ee48}', '\u{1ee48}'),
-        ('\u{1ee4a}', '\u{1ee4a}'), ('\u{1ee4c}', '\u{1ee4c}'), ('\u{1ee50}', '\u{1ee50}'),
-        ('\u{1ee53}', '\u{1ee53}'), ('\u{1ee55}', '\u{1ee56}'), ('\u{1ee58}', '\u{1ee58}'),
-        ('\u{1ee5a}', '\u{1ee5a}'), ('\u{1ee5c}', '\u{1ee5c}'), ('\u{1ee5e}', '\u{1ee5e}'),
-        ('\u{1ee60}', '\u{1ee60}'), ('\u{1ee63}', '\u{1ee63}'), ('\u{1ee65}', '\u{1ee66}'),
-        ('\u{1ee6b}', '\u{1ee6b}'), ('\u{1ee73}', '\u{1ee73}'), ('\u{1ee78}', '\u{1ee78}'),
-        ('\u{1ee7d}', '\u{1ee7d}'), ('\u{1ee7f}', '\u{1ee7f}'), ('\u{1ee8a}', '\u{1ee8a}'),
-        ('\u{1ee9c}', '\u{1eea0}'), ('\u{1eea4}', '\u{1eea4}'), ('\u{1eeaa}', '\u{1eeaa}'),
-        ('\u{1eebc}', '\u{1eeef}'), ('\u{1eef2}', '\u{1efff}'), ('\u{1f02c}', '\u{1f02f}'),
-        ('\u{1f094}', '\u{1f09f}'), ('\u{1f0af}', '\u{1f0b0}'), ('\u{1f0c0}', '\u{1f0c0}'),
-        ('\u{1f0d0}', '\u{1f0d0}'), ('\u{1f0f6}', '\u{1f0ff}'), ('\u{1f10d}', '\u{1f10f}'),
-        ('\u{1f12f}', '\u{1f12f}'), ('\u{1f16c}', '\u{1f16f}'), ('\u{1f19b}', '\u{1f1e5}'),
-        ('\u{1f203}', '\u{1f20f}'), ('\u{1f23b}', '\u{1f23f}'), ('\u{1f249}', '\u{1f24f}'),
-        ('\u{1f252}', '\u{1f2ff}'), ('\u{1f32d}', '\u{1f32f}'), ('\u{1f37e}', '\u{1f37f}'),
-        ('\u{1f3cf}', '\u{1f3d3}'), ('\u{1f3f8}', '\u{1f3ff}'), ('\u{1f4ff}', '\u{1f4ff}'),
-        ('\u{1f54b}', '\u{1f54f}'), ('\u{1f57a}', '\u{1f57a}'), ('\u{1f5a4}', '\u{1f5a4}'),
-        ('\u{1f643}', '\u{1f644}'), ('\u{1f6d0}', '\u{1f6df}'), ('\u{1f6ed}', '\u{1f6ef}'),
-        ('\u{1f6f4}', '\u{1f6ff}'), ('\u{1f774}', '\u{1f77f}'), ('\u{1f7d5}', '\u{1f7ff}'),
-        ('\u{1f80c}', '\u{1f80f}'), ('\u{1f848}', '\u{1f84f}'), ('\u{1f85a}', '\u{1f85f}'),
-        ('\u{1f888}', '\u{1f88f}'), ('\u{1f8ae}', '\u{1ffff}'), ('\u{20001}', '\u{2a6d5}'),
-        ('\u{2a6d7}', '\u{2a6ff}'), ('\u{2a701}', '\u{2b733}'), ('\u{2b735}', '\u{2b73f}'),
-        ('\u{2b741}', '\u{2b81c}'), ('\u{2b81e}', '\u{2f7ff}'), ('\u{2fa1e}', '\u{e0000}'),
-        ('\u{e0002}', '\u{e001f}'), ('\u{e0080}', '\u{e00ff}'), ('\u{e01f0}', '\u{effff}'),
-        ('\u{f0001}', '\u{ffffc}'), ('\u{ffffe}', '\u{fffff}'), ('\u{100001}', '\u{10fffc}'),
-        ('\u{10fffe}', '\u{10ffff}')
-    ];
-
-    pub static Co_table: &'static [(char, char)] = &[
-        ('\u{e000}', '\u{e000}'), ('\u{f8ff}', '\u{f8ff}'), ('\u{f0000}', '\u{f0000}'),
-        ('\u{ffffd}', '\u{ffffd}'), ('\u{100000}', '\u{100000}'), ('\u{10fffd}', '\u{10fffd}')
-    ];
-
-    pub static L_table: &'static [(char, char)] = &[
+        '\u{31ef}'), ('\u{321f}', '\u{321f}'), ('\u{32ff}', '\u{32ff}'), ('\u{4db6}', '\u{4dbf}'),
+        ('\u{9fcd}', '\u{9fff}'), ('\u{a48d}', '\u{a48f}'), ('\u{a4c7}', '\u{a4cf}'), ('\u{a62c}',
+        '\u{a63f}'), ('\u{a69e}', '\u{a69e}'), ('\u{a6f8}', '\u{a6ff}'), ('\u{a78f}', '\u{a78f}'),
+        ('\u{a7ae}', '\u{a7af}'), ('\u{a7b2}', '\u{a7f6}'), ('\u{a82c}', '\u{a82f}'), ('\u{a83a}',
+        '\u{a83f}'), ('\u{a878}', '\u{a87f}'), ('\u{a8c5}', '\u{a8cd}'), ('\u{a8da}', '\u{a8df}'),
+        ('\u{a8fc}', '\u{a8ff}'), ('\u{a954}', '\u{a95e}'), ('\u{a97d}', '\u{a97f}'), ('\u{a9ce}',
+        '\u{a9ce}'), ('\u{a9da}', '\u{a9dd}'), ('\u{a9ff}', '\u{a9ff}'), ('\u{aa37}', '\u{aa3f}'),
+        ('\u{aa4e}', '\u{aa4f}'), ('\u{aa5a}', '\u{aa5b}'), ('\u{aac3}', '\u{aada}'), ('\u{aaf7}',
+        '\u{ab00}'), ('\u{ab07}', '\u{ab08}'), ('\u{ab0f}', '\u{ab10}'), ('\u{ab17}', '\u{ab1f}'),
+        ('\u{ab27}', '\u{ab27}'), ('\u{ab2f}', '\u{ab2f}'), ('\u{ab60}', '\u{ab63}'), ('\u{ab66}',
+        '\u{abbf}'), ('\u{abee}', '\u{abef}'), ('\u{abfa}', '\u{abff}'), ('\u{d7a4}', '\u{d7af}'),
+        ('\u{d7c7}', '\u{d7ca}'), ('\u{d7fc}', '\u{d7ff}'), ('\u{fa6e}', '\u{fa6f}'), ('\u{fada}',
+        '\u{faff}'), ('\u{fb07}', '\u{fb12}'), ('\u{fb18}', '\u{fb1c}'), ('\u{fb37}', '\u{fb37}'),
+        ('\u{fb3d}', '\u{fb3d}'), ('\u{fb3f}', '\u{fb3f}'), ('\u{fb42}', '\u{fb42}'), ('\u{fb45}',
+        '\u{fb45}'), ('\u{fbc2}', '\u{fbd2}'), ('\u{fd40}', '\u{fd4f}'), ('\u{fd90}', '\u{fd91}'),
+        ('\u{fdc8}', '\u{fdef}'), ('\u{fdfe}', '\u{fdff}'), ('\u{fe1a}', '\u{fe1f}'), ('\u{fe2e}',
+        '\u{fe2f}'), ('\u{fe53}', '\u{fe53}'), ('\u{fe67}', '\u{fe67}'), ('\u{fe6c}', '\u{fe6f}'),
+        ('\u{fe75}', '\u{fe75}'), ('\u{fefd}', '\u{fefe}'), ('\u{ff00}', '\u{ff00}'), ('\u{ffbf}',
+        '\u{ffc1}'), ('\u{ffc8}', '\u{ffc9}'), ('\u{ffd0}', '\u{ffd1}'), ('\u{ffd8}', '\u{ffd9}'),
+        ('\u{ffdd}', '\u{ffdf}'), ('\u{ffe7}', '\u{ffe7}'), ('\u{ffef}', '\u{fff8}'), ('\u{fffe}',
+        '\u{ffff}'), ('\u{1000c}', '\u{1000c}'), ('\u{10027}', '\u{10027}'), ('\u{1003b}',
+        '\u{1003b}'), ('\u{1003e}', '\u{1003e}'), ('\u{1004e}', '\u{1004f}'), ('\u{1005e}',
+        '\u{1007f}'), ('\u{100fb}', '\u{100ff}'), ('\u{10103}', '\u{10106}'), ('\u{10134}',
+        '\u{10136}'), ('\u{1018d}', '\u{1018f}'), ('\u{1019c}', '\u{1019f}'), ('\u{101a1}',
+        '\u{101cf}'), ('\u{101fe}', '\u{1027f}'), ('\u{1029d}', '\u{1029f}'), ('\u{102d1}',
+        '\u{102df}'), ('\u{102fc}', '\u{102ff}'), ('\u{10324}', '\u{1032f}'), ('\u{1034b}',
+        '\u{1034f}'), ('\u{1037b}', '\u{1037f}'), ('\u{1039e}', '\u{1039e}'), ('\u{103c4}',
+        '\u{103c7}'), ('\u{103d6}', '\u{103ff}'), ('\u{1049e}', '\u{1049f}'), ('\u{104aa}',
+        '\u{104ff}'), ('\u{10528}', '\u{1052f}'), ('\u{10564}', '\u{1056e}'), ('\u{10570}',
+        '\u{105ff}'), ('\u{10737}', '\u{1073f}'), ('\u{10756}', '\u{1075f}'), ('\u{10768}',
+        '\u{107ff}'), ('\u{10806}', '\u{10807}'), ('\u{10809}', '\u{10809}'), ('\u{10836}',
+        '\u{10836}'), ('\u{10839}', '\u{1083b}'), ('\u{1083d}', '\u{1083e}'), ('\u{10856}',
+        '\u{10856}'), ('\u{1089f}', '\u{108a6}'), ('\u{108b0}', '\u{108ff}'), ('\u{1091c}',
+        '\u{1091e}'), ('\u{1093a}', '\u{1093e}'), ('\u{10940}', '\u{1097f}'), ('\u{109b8}',
+        '\u{109bd}'), ('\u{109c0}', '\u{109ff}'), ('\u{10a04}', '\u{10a04}'), ('\u{10a07}',
+        '\u{10a0b}'), ('\u{10a14}', '\u{10a14}'), ('\u{10a18}', '\u{10a18}'), ('\u{10a34}',
+        '\u{10a37}'), ('\u{10a3b}', '\u{10a3e}'), ('\u{10a48}', '\u{10a4f}'), ('\u{10a59}',
+        '\u{10a5f}'), ('\u{10aa0}', '\u{10abf}'), ('\u{10ae7}', '\u{10aea}'), ('\u{10af7}',
+        '\u{10aff}'), ('\u{10b36}', '\u{10b38}'), ('\u{10b56}', '\u{10b57}'), ('\u{10b73}',
+        '\u{10b77}'), ('\u{10b92}', '\u{10b98}'), ('\u{10b9d}', '\u{10ba8}'), ('\u{10bb0}',
+        '\u{10bff}'), ('\u{10c49}', '\u{10e5f}'), ('\u{10e7f}', '\u{10fff}'), ('\u{1104e}',
+        '\u{11051}'), ('\u{11070}', '\u{1107e}'), ('\u{110c2}', '\u{110cf}'), ('\u{110e9}',
+        '\u{110ef}'), ('\u{110fa}', '\u{110ff}'), ('\u{11135}', '\u{11135}'), ('\u{11144}',
+        '\u{1114f}'), ('\u{11177}', '\u{1117f}'), ('\u{111c9}', '\u{111cc}'), ('\u{111ce}',
+        '\u{111cf}'), ('\u{111db}', '\u{111e0}'), ('\u{111f5}', '\u{111ff}'), ('\u{11212}',
+        '\u{11212}'), ('\u{1123e}', '\u{112af}'), ('\u{112eb}', '\u{112ef}'), ('\u{112fa}',
+        '\u{11300}'), ('\u{11304}', '\u{11304}'), ('\u{1130d}', '\u{1130e}'), ('\u{11311}',
+        '\u{11312}'), ('\u{11329}', '\u{11329}'), ('\u{11331}', '\u{11331}'), ('\u{11334}',
+        '\u{11334}'), ('\u{1133a}', '\u{1133b}'), ('\u{11345}', '\u{11346}'), ('\u{11349}',
+        '\u{1134a}'), ('\u{1134e}', '\u{11356}'), ('\u{11358}', '\u{1135c}'), ('\u{11364}',
+        '\u{11365}'), ('\u{1136d}', '\u{1136f}'), ('\u{11375}', '\u{1147f}'), ('\u{114c8}',
+        '\u{114cf}'), ('\u{114da}', '\u{1157f}'), ('\u{115b6}', '\u{115b7}'), ('\u{115ca}',
+        '\u{115ff}'), ('\u{11645}', '\u{1164f}'), ('\u{1165a}', '\u{1167f}'), ('\u{116b8}',
+        '\u{116bf}'), ('\u{116ca}', '\u{1189f}'), ('\u{118f3}', '\u{118fe}'), ('\u{11900}',
+        '\u{11abf}'), ('\u{11af9}', '\u{11fff}'), ('\u{12399}', '\u{123ff}'), ('\u{1246f}',
+        '\u{1246f}'), ('\u{12475}', '\u{12fff}'), ('\u{1342f}', '\u{167ff}'), ('\u{16a39}',
+        '\u{16a3f}'), ('\u{16a5f}', '\u{16a5f}'), ('\u{16a6a}', '\u{16a6d}'), ('\u{16a70}',
+        '\u{16acf}'), ('\u{16aee}', '\u{16aef}'), ('\u{16af6}', '\u{16aff}'), ('\u{16b46}',
+        '\u{16b4f}'), ('\u{16b5a}', '\u{16b5a}'), ('\u{16b62}', '\u{16b62}'), ('\u{16b78}',
+        '\u{16b7c}'), ('\u{16b90}', '\u{16eff}'), ('\u{16f45}', '\u{16f4f}'), ('\u{16f7f}',
+        '\u{16f8e}'), ('\u{16fa0}', '\u{1afff}'), ('\u{1b002}', '\u{1bbff}'), ('\u{1bc6b}',
+        '\u{1bc6f}'), ('\u{1bc7d}', '\u{1bc7f}'), ('\u{1bc89}', '\u{1bc8f}'), ('\u{1bc9a}',
+        '\u{1bc9b}'), ('\u{1bca4}', '\u{1cfff}'), ('\u{1d0f6}', '\u{1d0ff}'), ('\u{1d127}',
+        '\u{1d128}'), ('\u{1d1de}', '\u{1d1ff}'), ('\u{1d246}', '\u{1d2ff}'), ('\u{1d357}',
+        '\u{1d35f}'), ('\u{1d372}', '\u{1d3ff}'), ('\u{1d455}', '\u{1d455}'), ('\u{1d49d}',
+        '\u{1d49d}'), ('\u{1d4a0}', '\u{1d4a1}'), ('\u{1d4a3}', '\u{1d4a4}'), ('\u{1d4a7}',
+        '\u{1d4a8}'), ('\u{1d4ad}', '\u{1d4ad}'), ('\u{1d4ba}', '\u{1d4ba}'), ('\u{1d4bc}',
+        '\u{1d4bc}'), ('\u{1d4c4}', '\u{1d4c4}'), ('\u{1d506}', '\u{1d506}'), ('\u{1d50b}',
+        '\u{1d50c}'), ('\u{1d515}', '\u{1d515}'), ('\u{1d51d}', '\u{1d51d}'), ('\u{1d53a}',
+        '\u{1d53a}'), ('\u{1d53f}', '\u{1d53f}'), ('\u{1d545}', '\u{1d545}'), ('\u{1d547}',
+        '\u{1d549}'), ('\u{1d551}', '\u{1d551}'), ('\u{1d6a6}', '\u{1d6a7}'), ('\u{1d7cc}',
+        '\u{1d7cd}'), ('\u{1d800}', '\u{1e7ff}'), ('\u{1e8c5}', '\u{1e8c6}'), ('\u{1e8d7}',
+        '\u{1edff}'), ('\u{1ee04}', '\u{1ee04}'), ('\u{1ee20}', '\u{1ee20}'), ('\u{1ee23}',
+        '\u{1ee23}'), ('\u{1ee25}', '\u{1ee26}'), ('\u{1ee28}', '\u{1ee28}'), ('\u{1ee33}',
+        '\u{1ee33}'), ('\u{1ee38}', '\u{1ee38}'), ('\u{1ee3a}', '\u{1ee3a}'), ('\u{1ee3c}',
+        '\u{1ee41}'), ('\u{1ee43}', '\u{1ee46}'), ('\u{1ee48}', '\u{1ee48}'), ('\u{1ee4a}',
+        '\u{1ee4a}'), ('\u{1ee4c}', '\u{1ee4c}'), ('\u{1ee50}', '\u{1ee50}'), ('\u{1ee53}',
+        '\u{1ee53}'), ('\u{1ee55}', '\u{1ee56}'), ('\u{1ee58}', '\u{1ee58}'), ('\u{1ee5a}',
+        '\u{1ee5a}'), ('\u{1ee5c}', '\u{1ee5c}'), ('\u{1ee5e}', '\u{1ee5e}'), ('\u{1ee60}',
+        '\u{1ee60}'), ('\u{1ee63}', '\u{1ee63}'), ('\u{1ee65}', '\u{1ee66}'), ('\u{1ee6b}',
+        '\u{1ee6b}'), ('\u{1ee73}', '\u{1ee73}'), ('\u{1ee78}', '\u{1ee78}'), ('\u{1ee7d}',
+        '\u{1ee7d}'), ('\u{1ee7f}', '\u{1ee7f}'), ('\u{1ee8a}', '\u{1ee8a}'), ('\u{1ee9c}',
+        '\u{1eea0}'), ('\u{1eea4}', '\u{1eea4}'), ('\u{1eeaa}', '\u{1eeaa}'), ('\u{1eebc}',
+        '\u{1eeef}'), ('\u{1eef2}', '\u{1efff}'), ('\u{1f02c}', '\u{1f02f}'), ('\u{1f094}',
+        '\u{1f09f}'), ('\u{1f0af}', '\u{1f0b0}'), ('\u{1f0c0}', '\u{1f0c0}'), ('\u{1f0d0}',
+        '\u{1f0d0}'), ('\u{1f0f6}', '\u{1f0ff}'), ('\u{1f10d}', '\u{1f10f}'), ('\u{1f12f}',
+        '\u{1f12f}'), ('\u{1f16c}', '\u{1f16f}'), ('\u{1f19b}', '\u{1f1e5}'), ('\u{1f203}',
+        '\u{1f20f}'), ('\u{1f23b}', '\u{1f23f}'), ('\u{1f249}', '\u{1f24f}'), ('\u{1f252}',
+        '\u{1f2ff}'), ('\u{1f32d}', '\u{1f32f}'), ('\u{1f37e}', '\u{1f37f}'), ('\u{1f3cf}',
+        '\u{1f3d3}'), ('\u{1f3f8}', '\u{1f3ff}'), ('\u{1f4ff}', '\u{1f4ff}'), ('\u{1f54b}',
+        '\u{1f54f}'), ('\u{1f57a}', '\u{1f57a}'), ('\u{1f5a4}', '\u{1f5a4}'), ('\u{1f643}',
+        '\u{1f644}'), ('\u{1f6d0}', '\u{1f6df}'), ('\u{1f6ed}', '\u{1f6ef}'), ('\u{1f6f4}',
+        '\u{1f6ff}'), ('\u{1f774}', '\u{1f77f}'), ('\u{1f7d5}', '\u{1f7ff}'), ('\u{1f80c}',
+        '\u{1f80f}'), ('\u{1f848}', '\u{1f84f}'), ('\u{1f85a}', '\u{1f85f}'), ('\u{1f888}',
+        '\u{1f88f}'), ('\u{1f8ae}', '\u{1ffff}'), ('\u{2a6d7}', '\u{2a6ff}'), ('\u{2b735}',
+        '\u{2b73f}'), ('\u{2b81e}', '\u{2f7ff}'), ('\u{2fa1e}', '\u{e0000}'), ('\u{e0002}',
+        '\u{e001f}'), ('\u{e0080}', '\u{e00ff}'), ('\u{e01f0}', '\u{effff}'), ('\u{ffffe}',
+        '\u{fffff}'), ('\u{10fffe}', '\u{10ffff}')
+    ];
+
+    pub const Co_table: &'static [(char, char)] = &[
+        ('\u{e000}', '\u{f8ff}'), ('\u{f0000}', '\u{ffffd}'), ('\u{100000}', '\u{10fffd}')
+    ];
+
+    pub const L_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{5a}'), ('\u{61}', '\u{7a}'), ('\u{aa}', '\u{aa}'), ('\u{b5}', '\u{b5}'),
         ('\u{ba}', '\u{ba}'), ('\u{c0}', '\u{d6}'), ('\u{d8}', '\u{f6}'), ('\u{f8}', '\u{2c1}'),
         ('\u{2c6}', '\u{2d1}'), ('\u{2e0}', '\u{2e4}'), ('\u{2ec}', '\u{2ec}'), ('\u{2ee}',
@@ -511,89 +505,87 @@ pub fn Cc(c: char) -> bool {
         ('\u{2e2f}', '\u{2e2f}'), ('\u{3005}', '\u{3006}'), ('\u{3031}', '\u{3035}'), ('\u{303b}',
         '\u{303c}'), ('\u{3041}', '\u{3096}'), ('\u{309d}', '\u{309f}'), ('\u{30a1}', '\u{30fa}'),
         ('\u{30fc}', '\u{30ff}'), ('\u{3105}', '\u{312d}'), ('\u{3131}', '\u{318e}'), ('\u{31a0}',
-        '\u{31ba}'), ('\u{31f0}', '\u{31ff}'), ('\u{3400}', '\u{3400}'), ('\u{4db5}', '\u{4db5}'),
-        ('\u{4e00}', '\u{4e00}'), ('\u{9fcc}', '\u{9fcc}'), ('\u{a000}', '\u{a48c}'), ('\u{a4d0}',
-        '\u{a4fd}'), ('\u{a500}', '\u{a60c}'), ('\u{a610}', '\u{a61f}'), ('\u{a62a}', '\u{a62b}'),
-        ('\u{a640}', '\u{a66e}'), ('\u{a67f}', '\u{a69d}'), ('\u{a6a0}', '\u{a6e5}'), ('\u{a717}',
-        '\u{a71f}'), ('\u{a722}', '\u{a788}'), ('\u{a78b}', '\u{a78e}'), ('\u{a790}', '\u{a7ad}'),
-        ('\u{a7b0}', '\u{a7b1}'), ('\u{a7f7}', '\u{a801}'), ('\u{a803}', '\u{a805}'), ('\u{a807}',
-        '\u{a80a}'), ('\u{a80c}', '\u{a822}'), ('\u{a840}', '\u{a873}'), ('\u{a882}', '\u{a8b3}'),
-        ('\u{a8f2}', '\u{a8f7}'), ('\u{a8fb}', '\u{a8fb}'), ('\u{a90a}', '\u{a925}'), ('\u{a930}',
-        '\u{a946}'), ('\u{a960}', '\u{a97c}'), ('\u{a984}', '\u{a9b2}'), ('\u{a9cf}', '\u{a9cf}'),
-        ('\u{a9e0}', '\u{a9e4}'), ('\u{a9e6}', '\u{a9ef}'), ('\u{a9fa}', '\u{a9fe}'), ('\u{aa00}',
-        '\u{aa28}'), ('\u{aa40}', '\u{aa42}'), ('\u{aa44}', '\u{aa4b}'), ('\u{aa60}', '\u{aa76}'),
-        ('\u{aa7a}', '\u{aa7a}'), ('\u{aa7e}', '\u{aaaf}'), ('\u{aab1}', '\u{aab1}'), ('\u{aab5}',
-        '\u{aab6}'), ('\u{aab9}', '\u{aabd}'), ('\u{aac0}', '\u{aac0}'), ('\u{aac2}', '\u{aac2}'),
-        ('\u{aadb}', '\u{aadd}'), ('\u{aae0}', '\u{aaea}'), ('\u{aaf2}', '\u{aaf4}'), ('\u{ab01}',
-        '\u{ab06}'), ('\u{ab09}', '\u{ab0e}'), ('\u{ab11}', '\u{ab16}'), ('\u{ab20}', '\u{ab26}'),
-        ('\u{ab28}', '\u{ab2e}'), ('\u{ab30}', '\u{ab5a}'), ('\u{ab5c}', '\u{ab5f}'), ('\u{ab64}',
-        '\u{ab65}'), ('\u{abc0}', '\u{abe2}'), ('\u{ac00}', '\u{ac00}'), ('\u{d7a3}', '\u{d7a3}'),
-        ('\u{d7b0}', '\u{d7c6}'), ('\u{d7cb}', '\u{d7fb}'), ('\u{f900}', '\u{fa6d}'), ('\u{fa70}',
-        '\u{fad9}'), ('\u{fb00}', '\u{fb06}'), ('\u{fb13}', '\u{fb17}'), ('\u{fb1d}', '\u{fb1d}'),
-        ('\u{fb1f}', '\u{fb28}'), ('\u{fb2a}', '\u{fb36}'), ('\u{fb38}', '\u{fb3c}'), ('\u{fb3e}',
-        '\u{fb3e}'), ('\u{fb40}', '\u{fb41}'), ('\u{fb43}', '\u{fb44}'), ('\u{fb46}', '\u{fbb1}'),
-        ('\u{fbd3}', '\u{fd3d}'), ('\u{fd50}', '\u{fd8f}'), ('\u{fd92}', '\u{fdc7}'), ('\u{fdf0}',
-        '\u{fdfb}'), ('\u{fe70}', '\u{fe74}'), ('\u{fe76}', '\u{fefc}'), ('\u{ff21}', '\u{ff3a}'),
-        ('\u{ff41}', '\u{ff5a}'), ('\u{ff66}', '\u{ffbe}'), ('\u{ffc2}', '\u{ffc7}'), ('\u{ffca}',
-        '\u{ffcf}'), ('\u{ffd2}', '\u{ffd7}'), ('\u{ffda}', '\u{ffdc}'), ('\u{10000}', '\u{1000b}'),
-        ('\u{1000d}', '\u{10026}'), ('\u{10028}', '\u{1003a}'), ('\u{1003c}', '\u{1003d}'),
-        ('\u{1003f}', '\u{1004d}'), ('\u{10050}', '\u{1005d}'), ('\u{10080}', '\u{100fa}'),
-        ('\u{10280}', '\u{1029c}'), ('\u{102a0}', '\u{102d0}'), ('\u{10300}', '\u{1031f}'),
-        ('\u{10330}', '\u{10340}'), ('\u{10342}', '\u{10349}'), ('\u{10350}', '\u{10375}'),
-        ('\u{10380}', '\u{1039d}'), ('\u{103a0}', '\u{103c3}'), ('\u{103c8}', '\u{103cf}'),
-        ('\u{10400}', '\u{1049d}'), ('\u{10500}', '\u{10527}'), ('\u{10530}', '\u{10563}'),
-        ('\u{10600}', '\u{10736}'), ('\u{10740}', '\u{10755}'), ('\u{10760}', '\u{10767}'),
-        ('\u{10800}', '\u{10805}'), ('\u{10808}', '\u{10808}'), ('\u{1080a}', '\u{10835}'),
-        ('\u{10837}', '\u{10838}'), ('\u{1083c}', '\u{1083c}'), ('\u{1083f}', '\u{10855}'),
-        ('\u{10860}', '\u{10876}'), ('\u{10880}', '\u{1089e}'), ('\u{10900}', '\u{10915}'),
-        ('\u{10920}', '\u{10939}'), ('\u{10980}', '\u{109b7}'), ('\u{109be}', '\u{109bf}'),
-        ('\u{10a00}', '\u{10a00}'), ('\u{10a10}', '\u{10a13}'), ('\u{10a15}', '\u{10a17}'),
-        ('\u{10a19}', '\u{10a33}'), ('\u{10a60}', '\u{10a7c}'), ('\u{10a80}', '\u{10a9c}'),
-        ('\u{10ac0}', '\u{10ac7}'), ('\u{10ac9}', '\u{10ae4}'), ('\u{10b00}', '\u{10b35}'),
-        ('\u{10b40}', '\u{10b55}'), ('\u{10b60}', '\u{10b72}'), ('\u{10b80}', '\u{10b91}'),
-        ('\u{10c00}', '\u{10c48}'), ('\u{11003}', '\u{11037}'), ('\u{11083}', '\u{110af}'),
-        ('\u{110d0}', '\u{110e8}'), ('\u{11103}', '\u{11126}'), ('\u{11150}', '\u{11172}'),
-        ('\u{11176}', '\u{11176}'), ('\u{11183}', '\u{111b2}'), ('\u{111c1}', '\u{111c4}'),
-        ('\u{111da}', '\u{111da}'), ('\u{11200}', '\u{11211}'), ('\u{11213}', '\u{1122b}'),
-        ('\u{112b0}', '\u{112de}'), ('\u{11305}', '\u{1130c}'), ('\u{1130f}', '\u{11310}'),
-        ('\u{11313}', '\u{11328}'), ('\u{1132a}', '\u{11330}'), ('\u{11332}', '\u{11333}'),
-        ('\u{11335}', '\u{11339}'), ('\u{1133d}', '\u{1133d}'), ('\u{1135d}', '\u{11361}'),
-        ('\u{11480}', '\u{114af}'), ('\u{114c4}', '\u{114c5}'), ('\u{114c7}', '\u{114c7}'),
-        ('\u{11580}', '\u{115ae}'), ('\u{11600}', '\u{1162f}'), ('\u{11644}', '\u{11644}'),
-        ('\u{11680}', '\u{116aa}'), ('\u{118a0}', '\u{118df}'), ('\u{118ff}', '\u{118ff}'),
-        ('\u{11ac0}', '\u{11af8}'), ('\u{12000}', '\u{12398}'), ('\u{13000}', '\u{1342e}'),
-        ('\u{16800}', '\u{16a38}'), ('\u{16a40}', '\u{16a5e}'), ('\u{16ad0}', '\u{16aed}'),
-        ('\u{16b00}', '\u{16b2f}'), ('\u{16b40}', '\u{16b43}'), ('\u{16b63}', '\u{16b77}'),
-        ('\u{16b7d}', '\u{16b8f}'), ('\u{16f00}', '\u{16f44}'), ('\u{16f50}', '\u{16f50}'),
-        ('\u{16f93}', '\u{16f9f}'), ('\u{1b000}', '\u{1b001}'), ('\u{1bc00}', '\u{1bc6a}'),
-        ('\u{1bc70}', '\u{1bc7c}'), ('\u{1bc80}', '\u{1bc88}'), ('\u{1bc90}', '\u{1bc99}'),
-        ('\u{1d400}', '\u{1d454}'), ('\u{1d456}', '\u{1d49c}'), ('\u{1d49e}', '\u{1d49f}'),
-        ('\u{1d4a2}', '\u{1d4a2}'), ('\u{1d4a5}', '\u{1d4a6}'), ('\u{1d4a9}', '\u{1d4ac}'),
-        ('\u{1d4ae}', '\u{1d4b9}'), ('\u{1d4bb}', '\u{1d4bb}'), ('\u{1d4bd}', '\u{1d4c3}'),
-        ('\u{1d4c5}', '\u{1d505}'), ('\u{1d507}', '\u{1d50a}'), ('\u{1d50d}', '\u{1d514}'),
-        ('\u{1d516}', '\u{1d51c}'), ('\u{1d51e}', '\u{1d539}'), ('\u{1d53b}', '\u{1d53e}'),
-        ('\u{1d540}', '\u{1d544}'), ('\u{1d546}', '\u{1d546}'), ('\u{1d54a}', '\u{1d550}'),
-        ('\u{1d552}', '\u{1d6a5}'), ('\u{1d6a8}', '\u{1d6c0}'), ('\u{1d6c2}', '\u{1d6da}'),
-        ('\u{1d6dc}', '\u{1d6fa}'), ('\u{1d6fc}', '\u{1d714}'), ('\u{1d716}', '\u{1d734}'),
-        ('\u{1d736}', '\u{1d74e}'), ('\u{1d750}', '\u{1d76e}'), ('\u{1d770}', '\u{1d788}'),
-        ('\u{1d78a}', '\u{1d7a8}'), ('\u{1d7aa}', '\u{1d7c2}'), ('\u{1d7c4}', '\u{1d7cb}'),
-        ('\u{1e800}', '\u{1e8c4}'), ('\u{1ee00}', '\u{1ee03}'), ('\u{1ee05}', '\u{1ee1f}'),
-        ('\u{1ee21}', '\u{1ee22}'), ('\u{1ee24}', '\u{1ee24}'), ('\u{1ee27}', '\u{1ee27}'),
-        ('\u{1ee29}', '\u{1ee32}'), ('\u{1ee34}', '\u{1ee37}'), ('\u{1ee39}', '\u{1ee39}'),
-        ('\u{1ee3b}', '\u{1ee3b}'), ('\u{1ee42}', '\u{1ee42}'), ('\u{1ee47}', '\u{1ee47}'),
-        ('\u{1ee49}', '\u{1ee49}'), ('\u{1ee4b}', '\u{1ee4b}'), ('\u{1ee4d}', '\u{1ee4f}'),
-        ('\u{1ee51}', '\u{1ee52}'), ('\u{1ee54}', '\u{1ee54}'), ('\u{1ee57}', '\u{1ee57}'),
-        ('\u{1ee59}', '\u{1ee59}'), ('\u{1ee5b}', '\u{1ee5b}'), ('\u{1ee5d}', '\u{1ee5d}'),
-        ('\u{1ee5f}', '\u{1ee5f}'), ('\u{1ee61}', '\u{1ee62}'), ('\u{1ee64}', '\u{1ee64}'),
-        ('\u{1ee67}', '\u{1ee6a}'), ('\u{1ee6c}', '\u{1ee72}'), ('\u{1ee74}', '\u{1ee77}'),
-        ('\u{1ee79}', '\u{1ee7c}'), ('\u{1ee7e}', '\u{1ee7e}'), ('\u{1ee80}', '\u{1ee89}'),
-        ('\u{1ee8b}', '\u{1ee9b}'), ('\u{1eea1}', '\u{1eea3}'), ('\u{1eea5}', '\u{1eea9}'),
-        ('\u{1eeab}', '\u{1eebb}'), ('\u{20000}', '\u{20000}'), ('\u{2a6d6}', '\u{2a6d6}'),
-        ('\u{2a700}', '\u{2a700}'), ('\u{2b734}', '\u{2b734}'), ('\u{2b740}', '\u{2b740}'),
-        ('\u{2b81d}', '\u{2b81d}'), ('\u{2f800}', '\u{2fa1d}')
+        '\u{31ba}'), ('\u{31f0}', '\u{31ff}'), ('\u{3400}', '\u{4db5}'), ('\u{4e00}', '\u{9fcc}'),
+        ('\u{a000}', '\u{a48c}'), ('\u{a4d0}', '\u{a4fd}'), ('\u{a500}', '\u{a60c}'), ('\u{a610}',
+        '\u{a61f}'), ('\u{a62a}', '\u{a62b}'), ('\u{a640}', '\u{a66e}'), ('\u{a67f}', '\u{a69d}'),
+        ('\u{a6a0}', '\u{a6e5}'), ('\u{a717}', '\u{a71f}'), ('\u{a722}', '\u{a788}'), ('\u{a78b}',
+        '\u{a78e}'), ('\u{a790}', '\u{a7ad}'), ('\u{a7b0}', '\u{a7b1}'), ('\u{a7f7}', '\u{a801}'),
+        ('\u{a803}', '\u{a805}'), ('\u{a807}', '\u{a80a}'), ('\u{a80c}', '\u{a822}'), ('\u{a840}',
+        '\u{a873}'), ('\u{a882}', '\u{a8b3}'), ('\u{a8f2}', '\u{a8f7}'), ('\u{a8fb}', '\u{a8fb}'),
+        ('\u{a90a}', '\u{a925}'), ('\u{a930}', '\u{a946}'), ('\u{a960}', '\u{a97c}'), ('\u{a984}',
+        '\u{a9b2}'), ('\u{a9cf}', '\u{a9cf}'), ('\u{a9e0}', '\u{a9e4}'), ('\u{a9e6}', '\u{a9ef}'),
+        ('\u{a9fa}', '\u{a9fe}'), ('\u{aa00}', '\u{aa28}'), ('\u{aa40}', '\u{aa42}'), ('\u{aa44}',
+        '\u{aa4b}'), ('\u{aa60}', '\u{aa76}'), ('\u{aa7a}', '\u{aa7a}'), ('\u{aa7e}', '\u{aaaf}'),
+        ('\u{aab1}', '\u{aab1}'), ('\u{aab5}', '\u{aab6}'), ('\u{aab9}', '\u{aabd}'), ('\u{aac0}',
+        '\u{aac0}'), ('\u{aac2}', '\u{aac2}'), ('\u{aadb}', '\u{aadd}'), ('\u{aae0}', '\u{aaea}'),
+        ('\u{aaf2}', '\u{aaf4}'), ('\u{ab01}', '\u{ab06}'), ('\u{ab09}', '\u{ab0e}'), ('\u{ab11}',
+        '\u{ab16}'), ('\u{ab20}', '\u{ab26}'), ('\u{ab28}', '\u{ab2e}'), ('\u{ab30}', '\u{ab5a}'),
+        ('\u{ab5c}', '\u{ab5f}'), ('\u{ab64}', '\u{ab65}'), ('\u{abc0}', '\u{abe2}'), ('\u{ac00}',
+        '\u{d7a3}'), ('\u{d7b0}', '\u{d7c6}'), ('\u{d7cb}', '\u{d7fb}'), ('\u{f900}', '\u{fa6d}'),
+        ('\u{fa70}', '\u{fad9}'), ('\u{fb00}', '\u{fb06}'), ('\u{fb13}', '\u{fb17}'), ('\u{fb1d}',
+        '\u{fb1d}'), ('\u{fb1f}', '\u{fb28}'), ('\u{fb2a}', '\u{fb36}'), ('\u{fb38}', '\u{fb3c}'),
+        ('\u{fb3e}', '\u{fb3e}'), ('\u{fb40}', '\u{fb41}'), ('\u{fb43}', '\u{fb44}'), ('\u{fb46}',
+        '\u{fbb1}'), ('\u{fbd3}', '\u{fd3d}'), ('\u{fd50}', '\u{fd8f}'), ('\u{fd92}', '\u{fdc7}'),
+        ('\u{fdf0}', '\u{fdfb}'), ('\u{fe70}', '\u{fe74}'), ('\u{fe76}', '\u{fefc}'), ('\u{ff21}',
+        '\u{ff3a}'), ('\u{ff41}', '\u{ff5a}'), ('\u{ff66}', '\u{ffbe}'), ('\u{ffc2}', '\u{ffc7}'),
+        ('\u{ffca}', '\u{ffcf}'), ('\u{ffd2}', '\u{ffd7}'), ('\u{ffda}', '\u{ffdc}'), ('\u{10000}',
+        '\u{1000b}'), ('\u{1000d}', '\u{10026}'), ('\u{10028}', '\u{1003a}'), ('\u{1003c}',
+        '\u{1003d}'), ('\u{1003f}', '\u{1004d}'), ('\u{10050}', '\u{1005d}'), ('\u{10080}',
+        '\u{100fa}'), ('\u{10280}', '\u{1029c}'), ('\u{102a0}', '\u{102d0}'), ('\u{10300}',
+        '\u{1031f}'), ('\u{10330}', '\u{10340}'), ('\u{10342}', '\u{10349}'), ('\u{10350}',
+        '\u{10375}'), ('\u{10380}', '\u{1039d}'), ('\u{103a0}', '\u{103c3}'), ('\u{103c8}',
+        '\u{103cf}'), ('\u{10400}', '\u{1049d}'), ('\u{10500}', '\u{10527}'), ('\u{10530}',
+        '\u{10563}'), ('\u{10600}', '\u{10736}'), ('\u{10740}', '\u{10755}'), ('\u{10760}',
+        '\u{10767}'), ('\u{10800}', '\u{10805}'), ('\u{10808}', '\u{10808}'), ('\u{1080a}',
+        '\u{10835}'), ('\u{10837}', '\u{10838}'), ('\u{1083c}', '\u{1083c}'), ('\u{1083f}',
+        '\u{10855}'), ('\u{10860}', '\u{10876}'), ('\u{10880}', '\u{1089e}'), ('\u{10900}',
+        '\u{10915}'), ('\u{10920}', '\u{10939}'), ('\u{10980}', '\u{109b7}'), ('\u{109be}',
+        '\u{109bf}'), ('\u{10a00}', '\u{10a00}'), ('\u{10a10}', '\u{10a13}'), ('\u{10a15}',
+        '\u{10a17}'), ('\u{10a19}', '\u{10a33}'), ('\u{10a60}', '\u{10a7c}'), ('\u{10a80}',
+        '\u{10a9c}'), ('\u{10ac0}', '\u{10ac7}'), ('\u{10ac9}', '\u{10ae4}'), ('\u{10b00}',
+        '\u{10b35}'), ('\u{10b40}', '\u{10b55}'), ('\u{10b60}', '\u{10b72}'), ('\u{10b80}',
+        '\u{10b91}'), ('\u{10c00}', '\u{10c48}'), ('\u{11003}', '\u{11037}'), ('\u{11083}',
+        '\u{110af}'), ('\u{110d0}', '\u{110e8}'), ('\u{11103}', '\u{11126}'), ('\u{11150}',
+        '\u{11172}'), ('\u{11176}', '\u{11176}'), ('\u{11183}', '\u{111b2}'), ('\u{111c1}',
+        '\u{111c4}'), ('\u{111da}', '\u{111da}'), ('\u{11200}', '\u{11211}'), ('\u{11213}',
+        '\u{1122b}'), ('\u{112b0}', '\u{112de}'), ('\u{11305}', '\u{1130c}'), ('\u{1130f}',
+        '\u{11310}'), ('\u{11313}', '\u{11328}'), ('\u{1132a}', '\u{11330}'), ('\u{11332}',
+        '\u{11333}'), ('\u{11335}', '\u{11339}'), ('\u{1133d}', '\u{1133d}'), ('\u{1135d}',
+        '\u{11361}'), ('\u{11480}', '\u{114af}'), ('\u{114c4}', '\u{114c5}'), ('\u{114c7}',
+        '\u{114c7}'), ('\u{11580}', '\u{115ae}'), ('\u{11600}', '\u{1162f}'), ('\u{11644}',
+        '\u{11644}'), ('\u{11680}', '\u{116aa}'), ('\u{118a0}', '\u{118df}'), ('\u{118ff}',
+        '\u{118ff}'), ('\u{11ac0}', '\u{11af8}'), ('\u{12000}', '\u{12398}'), ('\u{13000}',
+        '\u{1342e}'), ('\u{16800}', '\u{16a38}'), ('\u{16a40}', '\u{16a5e}'), ('\u{16ad0}',
+        '\u{16aed}'), ('\u{16b00}', '\u{16b2f}'), ('\u{16b40}', '\u{16b43}'), ('\u{16b63}',
+        '\u{16b77}'), ('\u{16b7d}', '\u{16b8f}'), ('\u{16f00}', '\u{16f44}'), ('\u{16f50}',
+        '\u{16f50}'), ('\u{16f93}', '\u{16f9f}'), ('\u{1b000}', '\u{1b001}'), ('\u{1bc00}',
+        '\u{1bc6a}'), ('\u{1bc70}', '\u{1bc7c}'), ('\u{1bc80}', '\u{1bc88}'), ('\u{1bc90}',
+        '\u{1bc99}'), ('\u{1d400}', '\u{1d454}'), ('\u{1d456}', '\u{1d49c}'), ('\u{1d49e}',
+        '\u{1d49f}'), ('\u{1d4a2}', '\u{1d4a2}'), ('\u{1d4a5}', '\u{1d4a6}'), ('\u{1d4a9}',
+        '\u{1d4ac}'), ('\u{1d4ae}', '\u{1d4b9}'), ('\u{1d4bb}', '\u{1d4bb}'), ('\u{1d4bd}',
+        '\u{1d4c3}'), ('\u{1d4c5}', '\u{1d505}'), ('\u{1d507}', '\u{1d50a}'), ('\u{1d50d}',
+        '\u{1d514}'), ('\u{1d516}', '\u{1d51c}'), ('\u{1d51e}', '\u{1d539}'), ('\u{1d53b}',
+        '\u{1d53e}'), ('\u{1d540}', '\u{1d544}'), ('\u{1d546}', '\u{1d546}'), ('\u{1d54a}',
+        '\u{1d550}'), ('\u{1d552}', '\u{1d6a5}'), ('\u{1d6a8}', '\u{1d6c0}'), ('\u{1d6c2}',
+        '\u{1d6da}'), ('\u{1d6dc}', '\u{1d6fa}'), ('\u{1d6fc}', '\u{1d714}'), ('\u{1d716}',
+        '\u{1d734}'), ('\u{1d736}', '\u{1d74e}'), ('\u{1d750}', '\u{1d76e}'), ('\u{1d770}',
+        '\u{1d788}'), ('\u{1d78a}', '\u{1d7a8}'), ('\u{1d7aa}', '\u{1d7c2}'), ('\u{1d7c4}',
+        '\u{1d7cb}'), ('\u{1e800}', '\u{1e8c4}'), ('\u{1ee00}', '\u{1ee03}'), ('\u{1ee05}',
+        '\u{1ee1f}'), ('\u{1ee21}', '\u{1ee22}'), ('\u{1ee24}', '\u{1ee24}'), ('\u{1ee27}',
+        '\u{1ee27}'), ('\u{1ee29}', '\u{1ee32}'), ('\u{1ee34}', '\u{1ee37}'), ('\u{1ee39}',
+        '\u{1ee39}'), ('\u{1ee3b}', '\u{1ee3b}'), ('\u{1ee42}', '\u{1ee42}'), ('\u{1ee47}',
+        '\u{1ee47}'), ('\u{1ee49}', '\u{1ee49}'), ('\u{1ee4b}', '\u{1ee4b}'), ('\u{1ee4d}',
+        '\u{1ee4f}'), ('\u{1ee51}', '\u{1ee52}'), ('\u{1ee54}', '\u{1ee54}'), ('\u{1ee57}',
+        '\u{1ee57}'), ('\u{1ee59}', '\u{1ee59}'), ('\u{1ee5b}', '\u{1ee5b}'), ('\u{1ee5d}',
+        '\u{1ee5d}'), ('\u{1ee5f}', '\u{1ee5f}'), ('\u{1ee61}', '\u{1ee62}'), ('\u{1ee64}',
+        '\u{1ee64}'), ('\u{1ee67}', '\u{1ee6a}'), ('\u{1ee6c}', '\u{1ee72}'), ('\u{1ee74}',
+        '\u{1ee77}'), ('\u{1ee79}', '\u{1ee7c}'), ('\u{1ee7e}', '\u{1ee7e}'), ('\u{1ee80}',
+        '\u{1ee89}'), ('\u{1ee8b}', '\u{1ee9b}'), ('\u{1eea1}', '\u{1eea3}'), ('\u{1eea5}',
+        '\u{1eea9}'), ('\u{1eeab}', '\u{1eebb}'), ('\u{20000}', '\u{2a6d6}'), ('\u{2a700}',
+        '\u{2b734}'), ('\u{2b740}', '\u{2b81d}'), ('\u{2f800}', '\u{2fa1d}')
     ];
 
-    pub static LC_table: &'static [(char, char)] = &[
+    pub const LC_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{5a}'), ('\u{61}', '\u{7a}'), ('\u{b5}', '\u{b5}'), ('\u{c0}', '\u{d6}'),
         ('\u{d8}', '\u{f6}'), ('\u{f8}', '\u{1ba}'), ('\u{1bc}', '\u{1bf}'), ('\u{1c4}', '\u{293}'),
         ('\u{295}', '\u{2af}'), ('\u{370}', '\u{373}'), ('\u{376}', '\u{377}'), ('\u{37b}',
@@ -631,7 +623,7 @@ pub fn Cc(c: char) -> bool {
         ('\u{1d7aa}', '\u{1d7c2}'), ('\u{1d7c4}', '\u{1d7cb}')
     ];
 
-    pub static Ll_table: &'static [(char, char)] = &[
+    pub const Ll_table: &'static [(char, char)] = &[
         ('\u{61}', '\u{7a}'), ('\u{b5}', '\u{b5}'), ('\u{df}', '\u{f6}'), ('\u{f8}', '\u{ff}'),
         ('\u{101}', '\u{101}'), ('\u{103}', '\u{103}'), ('\u{105}', '\u{105}'), ('\u{107}',
         '\u{107}'), ('\u{109}', '\u{109}'), ('\u{10b}', '\u{10b}'), ('\u{10d}', '\u{10d}'),
@@ -814,7 +806,7 @@ pub fn Cc(c: char) -> bool {
         '\u{1d7c2}'), ('\u{1d7c4}', '\u{1d7c9}'), ('\u{1d7cb}', '\u{1d7cb}')
     ];
 
-    pub static Lm_table: &'static [(char, char)] = &[
+    pub const Lm_table: &'static [(char, char)] = &[
         ('\u{2b0}', '\u{2c1}'), ('\u{2c6}', '\u{2d1}'), ('\u{2e0}', '\u{2e4}'), ('\u{2ec}',
         '\u{2ec}'), ('\u{2ee}', '\u{2ee}'), ('\u{374}', '\u{374}'), ('\u{37a}', '\u{37a}'),
         ('\u{559}', '\u{559}'), ('\u{640}', '\u{640}'), ('\u{6e5}', '\u{6e6}'), ('\u{7f4}',
@@ -834,7 +826,7 @@ pub fn Cc(c: char) -> bool {
         '\u{16f9f}')
     ];
 
-    pub static Lo_table: &'static [(char, char)] = &[
+    pub const Lo_table: &'static [(char, char)] = &[
         ('\u{aa}', '\u{aa}'), ('\u{ba}', '\u{ba}'), ('\u{1bb}', '\u{1bb}'), ('\u{1c0}', '\u{1c3}'),
         ('\u{294}', '\u{294}'), ('\u{5d0}', '\u{5ea}'), ('\u{5f0}', '\u{5f2}'), ('\u{620}',
         '\u{63f}'), ('\u{641}', '\u{64a}'), ('\u{66e}', '\u{66f}'), ('\u{671}', '\u{6d3}'),
@@ -896,81 +888,80 @@ pub fn Cc(c: char) -> bool {
         '\u{2dd6}'), ('\u{2dd8}', '\u{2dde}'), ('\u{3006}', '\u{3006}'), ('\u{303c}', '\u{303c}'),
         ('\u{3041}', '\u{3096}'), ('\u{309f}', '\u{309f}'), ('\u{30a1}', '\u{30fa}'), ('\u{30ff}',
         '\u{30ff}'), ('\u{3105}', '\u{312d}'), ('\u{3131}', '\u{318e}'), ('\u{31a0}', '\u{31ba}'),
-        ('\u{31f0}', '\u{31ff}'), ('\u{3400}', '\u{3400}'), ('\u{4db5}', '\u{4db5}'), ('\u{4e00}',
-        '\u{4e00}'), ('\u{9fcc}', '\u{9fcc}'), ('\u{a000}', '\u{a014}'), ('\u{a016}', '\u{a48c}'),
-        ('\u{a4d0}', '\u{a4f7}'), ('\u{a500}', '\u{a60b}'), ('\u{a610}', '\u{a61f}'), ('\u{a62a}',
-        '\u{a62b}'), ('\u{a66e}', '\u{a66e}'), ('\u{a6a0}', '\u{a6e5}'), ('\u{a7f7}', '\u{a7f7}'),
-        ('\u{a7fb}', '\u{a801}'), ('\u{a803}', '\u{a805}'), ('\u{a807}', '\u{a80a}'), ('\u{a80c}',
-        '\u{a822}'), ('\u{a840}', '\u{a873}'), ('\u{a882}', '\u{a8b3}'), ('\u{a8f2}', '\u{a8f7}'),
-        ('\u{a8fb}', '\u{a8fb}'), ('\u{a90a}', '\u{a925}'), ('\u{a930}', '\u{a946}'), ('\u{a960}',
-        '\u{a97c}'), ('\u{a984}', '\u{a9b2}'), ('\u{a9e0}', '\u{a9e4}'), ('\u{a9e7}', '\u{a9ef}'),
-        ('\u{a9fa}', '\u{a9fe}'), ('\u{aa00}', '\u{aa28}'), ('\u{aa40}', '\u{aa42}'), ('\u{aa44}',
-        '\u{aa4b}'), ('\u{aa60}', '\u{aa6f}'), ('\u{aa71}', '\u{aa76}'), ('\u{aa7a}', '\u{aa7a}'),
-        ('\u{aa7e}', '\u{aaaf}'), ('\u{aab1}', '\u{aab1}'), ('\u{aab5}', '\u{aab6}'), ('\u{aab9}',
-        '\u{aabd}'), ('\u{aac0}', '\u{aac0}'), ('\u{aac2}', '\u{aac2}'), ('\u{aadb}', '\u{aadc}'),
-        ('\u{aae0}', '\u{aaea}'), ('\u{aaf2}', '\u{aaf2}'), ('\u{ab01}', '\u{ab06}'), ('\u{ab09}',
-        '\u{ab0e}'), ('\u{ab11}', '\u{ab16}'), ('\u{ab20}', '\u{ab26}'), ('\u{ab28}', '\u{ab2e}'),
-        ('\u{abc0}', '\u{abe2}'), ('\u{ac00}', '\u{ac00}'), ('\u{d7a3}', '\u{d7a3}'), ('\u{d7b0}',
-        '\u{d7c6}'), ('\u{d7cb}', '\u{d7fb}'), ('\u{f900}', '\u{fa6d}'), ('\u{fa70}', '\u{fad9}'),
-        ('\u{fb1d}', '\u{fb1d}'), ('\u{fb1f}', '\u{fb28}'), ('\u{fb2a}', '\u{fb36}'), ('\u{fb38}',
-        '\u{fb3c}'), ('\u{fb3e}', '\u{fb3e}'), ('\u{fb40}', '\u{fb41}'), ('\u{fb43}', '\u{fb44}'),
-        ('\u{fb46}', '\u{fbb1}'), ('\u{fbd3}', '\u{fd3d}'), ('\u{fd50}', '\u{fd8f}'), ('\u{fd92}',
-        '\u{fdc7}'), ('\u{fdf0}', '\u{fdfb}'), ('\u{fe70}', '\u{fe74}'), ('\u{fe76}', '\u{fefc}'),
-        ('\u{ff66}', '\u{ff6f}'), ('\u{ff71}', '\u{ff9d}'), ('\u{ffa0}', '\u{ffbe}'), ('\u{ffc2}',
-        '\u{ffc7}'), ('\u{ffca}', '\u{ffcf}'), ('\u{ffd2}', '\u{ffd7}'), ('\u{ffda}', '\u{ffdc}'),
-        ('\u{10000}', '\u{1000b}'), ('\u{1000d}', '\u{10026}'), ('\u{10028}', '\u{1003a}'),
-        ('\u{1003c}', '\u{1003d}'), ('\u{1003f}', '\u{1004d}'), ('\u{10050}', '\u{1005d}'),
-        ('\u{10080}', '\u{100fa}'), ('\u{10280}', '\u{1029c}'), ('\u{102a0}', '\u{102d0}'),
-        ('\u{10300}', '\u{1031f}'), ('\u{10330}', '\u{10340}'), ('\u{10342}', '\u{10349}'),
-        ('\u{10350}', '\u{10375}'), ('\u{10380}', '\u{1039d}'), ('\u{103a0}', '\u{103c3}'),
-        ('\u{103c8}', '\u{103cf}'), ('\u{10450}', '\u{1049d}'), ('\u{10500}', '\u{10527}'),
-        ('\u{10530}', '\u{10563}'), ('\u{10600}', '\u{10736}'), ('\u{10740}', '\u{10755}'),
-        ('\u{10760}', '\u{10767}'), ('\u{10800}', '\u{10805}'), ('\u{10808}', '\u{10808}'),
-        ('\u{1080a}', '\u{10835}'), ('\u{10837}', '\u{10838}'), ('\u{1083c}', '\u{1083c}'),
-        ('\u{1083f}', '\u{10855}'), ('\u{10860}', '\u{10876}'), ('\u{10880}', '\u{1089e}'),
-        ('\u{10900}', '\u{10915}'), ('\u{10920}', '\u{10939}'), ('\u{10980}', '\u{109b7}'),
-        ('\u{109be}', '\u{109bf}'), ('\u{10a00}', '\u{10a00}'), ('\u{10a10}', '\u{10a13}'),
-        ('\u{10a15}', '\u{10a17}'), ('\u{10a19}', '\u{10a33}'), ('\u{10a60}', '\u{10a7c}'),
-        ('\u{10a80}', '\u{10a9c}'), ('\u{10ac0}', '\u{10ac7}'), ('\u{10ac9}', '\u{10ae4}'),
-        ('\u{10b00}', '\u{10b35}'), ('\u{10b40}', '\u{10b55}'), ('\u{10b60}', '\u{10b72}'),
-        ('\u{10b80}', '\u{10b91}'), ('\u{10c00}', '\u{10c48}'), ('\u{11003}', '\u{11037}'),
-        ('\u{11083}', '\u{110af}'), ('\u{110d0}', '\u{110e8}'), ('\u{11103}', '\u{11126}'),
-        ('\u{11150}', '\u{11172}'), ('\u{11176}', '\u{11176}'), ('\u{11183}', '\u{111b2}'),
-        ('\u{111c1}', '\u{111c4}'), ('\u{111da}', '\u{111da}'), ('\u{11200}', '\u{11211}'),
-        ('\u{11213}', '\u{1122b}'), ('\u{112b0}', '\u{112de}'), ('\u{11305}', '\u{1130c}'),
-        ('\u{1130f}', '\u{11310}'), ('\u{11313}', '\u{11328}'), ('\u{1132a}', '\u{11330}'),
-        ('\u{11332}', '\u{11333}'), ('\u{11335}', '\u{11339}'), ('\u{1133d}', '\u{1133d}'),
-        ('\u{1135d}', '\u{11361}'), ('\u{11480}', '\u{114af}'), ('\u{114c4}', '\u{114c5}'),
-        ('\u{114c7}', '\u{114c7}'), ('\u{11580}', '\u{115ae}'), ('\u{11600}', '\u{1162f}'),
-        ('\u{11644}', '\u{11644}'), ('\u{11680}', '\u{116aa}'), ('\u{118ff}', '\u{118ff}'),
-        ('\u{11ac0}', '\u{11af8}'), ('\u{12000}', '\u{12398}'), ('\u{13000}', '\u{1342e}'),
-        ('\u{16800}', '\u{16a38}'), ('\u{16a40}', '\u{16a5e}'), ('\u{16ad0}', '\u{16aed}'),
-        ('\u{16b00}', '\u{16b2f}'), ('\u{16b63}', '\u{16b77}'), ('\u{16b7d}', '\u{16b8f}'),
-        ('\u{16f00}', '\u{16f44}'), ('\u{16f50}', '\u{16f50}'), ('\u{1b000}', '\u{1b001}'),
-        ('\u{1bc00}', '\u{1bc6a}'), ('\u{1bc70}', '\u{1bc7c}'), ('\u{1bc80}', '\u{1bc88}'),
-        ('\u{1bc90}', '\u{1bc99}'), ('\u{1e800}', '\u{1e8c4}'), ('\u{1ee00}', '\u{1ee03}'),
-        ('\u{1ee05}', '\u{1ee1f}'), ('\u{1ee21}', '\u{1ee22}'), ('\u{1ee24}', '\u{1ee24}'),
-        ('\u{1ee27}', '\u{1ee27}'), ('\u{1ee29}', '\u{1ee32}'), ('\u{1ee34}', '\u{1ee37}'),
-        ('\u{1ee39}', '\u{1ee39}'), ('\u{1ee3b}', '\u{1ee3b}'), ('\u{1ee42}', '\u{1ee42}'),
-        ('\u{1ee47}', '\u{1ee47}'), ('\u{1ee49}', '\u{1ee49}'), ('\u{1ee4b}', '\u{1ee4b}'),
-        ('\u{1ee4d}', '\u{1ee4f}'), ('\u{1ee51}', '\u{1ee52}'), ('\u{1ee54}', '\u{1ee54}'),
-        ('\u{1ee57}', '\u{1ee57}'), ('\u{1ee59}', '\u{1ee59}'), ('\u{1ee5b}', '\u{1ee5b}'),
-        ('\u{1ee5d}', '\u{1ee5d}'), ('\u{1ee5f}', '\u{1ee5f}'), ('\u{1ee61}', '\u{1ee62}'),
-        ('\u{1ee64}', '\u{1ee64}'), ('\u{1ee67}', '\u{1ee6a}'), ('\u{1ee6c}', '\u{1ee72}'),
-        ('\u{1ee74}', '\u{1ee77}'), ('\u{1ee79}', '\u{1ee7c}'), ('\u{1ee7e}', '\u{1ee7e}'),
-        ('\u{1ee80}', '\u{1ee89}'), ('\u{1ee8b}', '\u{1ee9b}'), ('\u{1eea1}', '\u{1eea3}'),
-        ('\u{1eea5}', '\u{1eea9}'), ('\u{1eeab}', '\u{1eebb}'), ('\u{20000}', '\u{20000}'),
-        ('\u{2a6d6}', '\u{2a6d6}'), ('\u{2a700}', '\u{2a700}'), ('\u{2b734}', '\u{2b734}'),
-        ('\u{2b740}', '\u{2b740}'), ('\u{2b81d}', '\u{2b81d}'), ('\u{2f800}', '\u{2fa1d}')
+        ('\u{31f0}', '\u{31ff}'), ('\u{3400}', '\u{4db5}'), ('\u{4e00}', '\u{9fcc}'), ('\u{a000}',
+        '\u{a014}'), ('\u{a016}', '\u{a48c}'), ('\u{a4d0}', '\u{a4f7}'), ('\u{a500}', '\u{a60b}'),
+        ('\u{a610}', '\u{a61f}'), ('\u{a62a}', '\u{a62b}'), ('\u{a66e}', '\u{a66e}'), ('\u{a6a0}',
+        '\u{a6e5}'), ('\u{a7f7}', '\u{a7f7}'), ('\u{a7fb}', '\u{a801}'), ('\u{a803}', '\u{a805}'),
+        ('\u{a807}', '\u{a80a}'), ('\u{a80c}', '\u{a822}'), ('\u{a840}', '\u{a873}'), ('\u{a882}',
+        '\u{a8b3}'), ('\u{a8f2}', '\u{a8f7}'), ('\u{a8fb}', '\u{a8fb}'), ('\u{a90a}', '\u{a925}'),
+        ('\u{a930}', '\u{a946}'), ('\u{a960}', '\u{a97c}'), ('\u{a984}', '\u{a9b2}'), ('\u{a9e0}',
+        '\u{a9e4}'), ('\u{a9e7}', '\u{a9ef}'), ('\u{a9fa}', '\u{a9fe}'), ('\u{aa00}', '\u{aa28}'),
+        ('\u{aa40}', '\u{aa42}'), ('\u{aa44}', '\u{aa4b}'), ('\u{aa60}', '\u{aa6f}'), ('\u{aa71}',
+        '\u{aa76}'), ('\u{aa7a}', '\u{aa7a}'), ('\u{aa7e}', '\u{aaaf}'), ('\u{aab1}', '\u{aab1}'),
+        ('\u{aab5}', '\u{aab6}'), ('\u{aab9}', '\u{aabd}'), ('\u{aac0}', '\u{aac0}'), ('\u{aac2}',
+        '\u{aac2}'), ('\u{aadb}', '\u{aadc}'), ('\u{aae0}', '\u{aaea}'), ('\u{aaf2}', '\u{aaf2}'),
+        ('\u{ab01}', '\u{ab06}'), ('\u{ab09}', '\u{ab0e}'), ('\u{ab11}', '\u{ab16}'), ('\u{ab20}',
+        '\u{ab26}'), ('\u{ab28}', '\u{ab2e}'), ('\u{abc0}', '\u{abe2}'), ('\u{ac00}', '\u{d7a3}'),
+        ('\u{d7b0}', '\u{d7c6}'), ('\u{d7cb}', '\u{d7fb}'), ('\u{f900}', '\u{fa6d}'), ('\u{fa70}',
+        '\u{fad9}'), ('\u{fb1d}', '\u{fb1d}'), ('\u{fb1f}', '\u{fb28}'), ('\u{fb2a}', '\u{fb36}'),
+        ('\u{fb38}', '\u{fb3c}'), ('\u{fb3e}', '\u{fb3e}'), ('\u{fb40}', '\u{fb41}'), ('\u{fb43}',
+        '\u{fb44}'), ('\u{fb46}', '\u{fbb1}'), ('\u{fbd3}', '\u{fd3d}'), ('\u{fd50}', '\u{fd8f}'),
+        ('\u{fd92}', '\u{fdc7}'), ('\u{fdf0}', '\u{fdfb}'), ('\u{fe70}', '\u{fe74}'), ('\u{fe76}',
+        '\u{fefc}'), ('\u{ff66}', '\u{ff6f}'), ('\u{ff71}', '\u{ff9d}'), ('\u{ffa0}', '\u{ffbe}'),
+        ('\u{ffc2}', '\u{ffc7}'), ('\u{ffca}', '\u{ffcf}'), ('\u{ffd2}', '\u{ffd7}'), ('\u{ffda}',
+        '\u{ffdc}'), ('\u{10000}', '\u{1000b}'), ('\u{1000d}', '\u{10026}'), ('\u{10028}',
+        '\u{1003a}'), ('\u{1003c}', '\u{1003d}'), ('\u{1003f}', '\u{1004d}'), ('\u{10050}',
+        '\u{1005d}'), ('\u{10080}', '\u{100fa}'), ('\u{10280}', '\u{1029c}'), ('\u{102a0}',
+        '\u{102d0}'), ('\u{10300}', '\u{1031f}'), ('\u{10330}', '\u{10340}'), ('\u{10342}',
+        '\u{10349}'), ('\u{10350}', '\u{10375}'), ('\u{10380}', '\u{1039d}'), ('\u{103a0}',
+        '\u{103c3}'), ('\u{103c8}', '\u{103cf}'), ('\u{10450}', '\u{1049d}'), ('\u{10500}',
+        '\u{10527}'), ('\u{10530}', '\u{10563}'), ('\u{10600}', '\u{10736}'), ('\u{10740}',
+        '\u{10755}'), ('\u{10760}', '\u{10767}'), ('\u{10800}', '\u{10805}'), ('\u{10808}',
+        '\u{10808}'), ('\u{1080a}', '\u{10835}'), ('\u{10837}', '\u{10838}'), ('\u{1083c}',
+        '\u{1083c}'), ('\u{1083f}', '\u{10855}'), ('\u{10860}', '\u{10876}'), ('\u{10880}',
+        '\u{1089e}'), ('\u{10900}', '\u{10915}'), ('\u{10920}', '\u{10939}'), ('\u{10980}',
+        '\u{109b7}'), ('\u{109be}', '\u{109bf}'), ('\u{10a00}', '\u{10a00}'), ('\u{10a10}',
+        '\u{10a13}'), ('\u{10a15}', '\u{10a17}'), ('\u{10a19}', '\u{10a33}'), ('\u{10a60}',
+        '\u{10a7c}'), ('\u{10a80}', '\u{10a9c}'), ('\u{10ac0}', '\u{10ac7}'), ('\u{10ac9}',
+        '\u{10ae4}'), ('\u{10b00}', '\u{10b35}'), ('\u{10b40}', '\u{10b55}'), ('\u{10b60}',
+        '\u{10b72}'), ('\u{10b80}', '\u{10b91}'), ('\u{10c00}', '\u{10c48}'), ('\u{11003}',
+        '\u{11037}'), ('\u{11083}', '\u{110af}'), ('\u{110d0}', '\u{110e8}'), ('\u{11103}',
+        '\u{11126}'), ('\u{11150}', '\u{11172}'), ('\u{11176}', '\u{11176}'), ('\u{11183}',
+        '\u{111b2}'), ('\u{111c1}', '\u{111c4}'), ('\u{111da}', '\u{111da}'), ('\u{11200}',
+        '\u{11211}'), ('\u{11213}', '\u{1122b}'), ('\u{112b0}', '\u{112de}'), ('\u{11305}',
+        '\u{1130c}'), ('\u{1130f}', '\u{11310}'), ('\u{11313}', '\u{11328}'), ('\u{1132a}',
+        '\u{11330}'), ('\u{11332}', '\u{11333}'), ('\u{11335}', '\u{11339}'), ('\u{1133d}',
+        '\u{1133d}'), ('\u{1135d}', '\u{11361}'), ('\u{11480}', '\u{114af}'), ('\u{114c4}',
+        '\u{114c5}'), ('\u{114c7}', '\u{114c7}'), ('\u{11580}', '\u{115ae}'), ('\u{11600}',
+        '\u{1162f}'), ('\u{11644}', '\u{11644}'), ('\u{11680}', '\u{116aa}'), ('\u{118ff}',
+        '\u{118ff}'), ('\u{11ac0}', '\u{11af8}'), ('\u{12000}', '\u{12398}'), ('\u{13000}',
+        '\u{1342e}'), ('\u{16800}', '\u{16a38}'), ('\u{16a40}', '\u{16a5e}'), ('\u{16ad0}',
+        '\u{16aed}'), ('\u{16b00}', '\u{16b2f}'), ('\u{16b63}', '\u{16b77}'), ('\u{16b7d}',
+        '\u{16b8f}'), ('\u{16f00}', '\u{16f44}'), ('\u{16f50}', '\u{16f50}'), ('\u{1b000}',
+        '\u{1b001}'), ('\u{1bc00}', '\u{1bc6a}'), ('\u{1bc70}', '\u{1bc7c}'), ('\u{1bc80}',
+        '\u{1bc88}'), ('\u{1bc90}', '\u{1bc99}'), ('\u{1e800}', '\u{1e8c4}'), ('\u{1ee00}',
+        '\u{1ee03}'), ('\u{1ee05}', '\u{1ee1f}'), ('\u{1ee21}', '\u{1ee22}'), ('\u{1ee24}',
+        '\u{1ee24}'), ('\u{1ee27}', '\u{1ee27}'), ('\u{1ee29}', '\u{1ee32}'), ('\u{1ee34}',
+        '\u{1ee37}'), ('\u{1ee39}', '\u{1ee39}'), ('\u{1ee3b}', '\u{1ee3b}'), ('\u{1ee42}',
+        '\u{1ee42}'), ('\u{1ee47}', '\u{1ee47}'), ('\u{1ee49}', '\u{1ee49}'), ('\u{1ee4b}',
+        '\u{1ee4b}'), ('\u{1ee4d}', '\u{1ee4f}'), ('\u{1ee51}', '\u{1ee52}'), ('\u{1ee54}',
+        '\u{1ee54}'), ('\u{1ee57}', '\u{1ee57}'), ('\u{1ee59}', '\u{1ee59}'), ('\u{1ee5b}',
+        '\u{1ee5b}'), ('\u{1ee5d}', '\u{1ee5d}'), ('\u{1ee5f}', '\u{1ee5f}'), ('\u{1ee61}',
+        '\u{1ee62}'), ('\u{1ee64}', '\u{1ee64}'), ('\u{1ee67}', '\u{1ee6a}'), ('\u{1ee6c}',
+        '\u{1ee72}'), ('\u{1ee74}', '\u{1ee77}'), ('\u{1ee79}', '\u{1ee7c}'), ('\u{1ee7e}',
+        '\u{1ee7e}'), ('\u{1ee80}', '\u{1ee89}'), ('\u{1ee8b}', '\u{1ee9b}'), ('\u{1eea1}',
+        '\u{1eea3}'), ('\u{1eea5}', '\u{1eea9}'), ('\u{1eeab}', '\u{1eebb}'), ('\u{20000}',
+        '\u{2a6d6}'), ('\u{2a700}', '\u{2b734}'), ('\u{2b740}', '\u{2b81d}'), ('\u{2f800}',
+        '\u{2fa1d}')
     ];
 
-    pub static Lt_table: &'static [(char, char)] = &[
+    pub const Lt_table: &'static [(char, char)] = &[
         ('\u{1c5}', '\u{1c5}'), ('\u{1c8}', '\u{1c8}'), ('\u{1cb}', '\u{1cb}'), ('\u{1f2}',
         '\u{1f2}'), ('\u{1f88}', '\u{1f8f}'), ('\u{1f98}', '\u{1f9f}'), ('\u{1fa8}', '\u{1faf}'),
         ('\u{1fbc}', '\u{1fbc}'), ('\u{1fcc}', '\u{1fcc}'), ('\u{1ffc}', '\u{1ffc}')
     ];
 
-    pub static Lu_table: &'static [(char, char)] = &[
+    pub const Lu_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{5a}'), ('\u{c0}', '\u{d6}'), ('\u{d8}', '\u{de}'), ('\u{100}', '\u{100}'),
         ('\u{102}', '\u{102}'), ('\u{104}', '\u{104}'), ('\u{106}', '\u{106}'), ('\u{108}',
         '\u{108}'), ('\u{10a}', '\u{10a}'), ('\u{10c}', '\u{10c}'), ('\u{10e}', '\u{10e}'),
@@ -1153,7 +1144,7 @@ pub fn Cc(c: char) -> bool {
         '\u{1d7ca}')
     ];
 
-    pub static M_table: &'static [(char, char)] = &[
+    pub const M_table: &'static [(char, char)] = &[
         ('\u{300}', '\u{36f}'), ('\u{483}', '\u{489}'), ('\u{591}', '\u{5bd}'), ('\u{5bf}',
         '\u{5bf}'), ('\u{5c1}', '\u{5c2}'), ('\u{5c4}', '\u{5c5}'), ('\u{5c7}', '\u{5c7}'),
         ('\u{610}', '\u{61a}'), ('\u{64b}', '\u{65f}'), ('\u{670}', '\u{670}'), ('\u{6d6}',
@@ -1224,7 +1215,7 @@ pub fn Cc(c: char) -> bool {
         ('\u{1e8d0}', '\u{1e8d6}'), ('\u{e0100}', '\u{e01ef}')
     ];
 
-    pub static Mc_table: &'static [(char, char)] = &[
+    pub const Mc_table: &'static [(char, char)] = &[
         ('\u{903}', '\u{903}'), ('\u{93b}', '\u{93b}'), ('\u{93e}', '\u{940}'), ('\u{949}',
         '\u{94c}'), ('\u{94e}', '\u{94f}'), ('\u{982}', '\u{983}'), ('\u{9be}', '\u{9c0}'),
         ('\u{9c7}', '\u{9c8}'), ('\u{9cb}', '\u{9cc}'), ('\u{9d7}', '\u{9d7}'), ('\u{a03}',
@@ -1271,12 +1262,12 @@ pub fn Cc(c: char) -> bool {
         ('\u{1d165}', '\u{1d166}'), ('\u{1d16d}', '\u{1d172}')
     ];
 
-    pub static Me_table: &'static [(char, char)] = &[
+    pub const Me_table: &'static [(char, char)] = &[
         ('\u{488}', '\u{489}'), ('\u{1abe}', '\u{1abe}'), ('\u{20dd}', '\u{20e0}'), ('\u{20e2}',
         '\u{20e4}'), ('\u{a670}', '\u{a672}')
     ];
 
-    pub static Mn_table: &'static [(char, char)] = &[
+    pub const Mn_table: &'static [(char, char)] = &[
         ('\u{300}', '\u{36f}'), ('\u{483}', '\u{487}'), ('\u{591}', '\u{5bd}'), ('\u{5bf}',
         '\u{5bf}'), ('\u{5c1}', '\u{5c2}'), ('\u{5c4}', '\u{5c5}'), ('\u{5c7}', '\u{5c7}'),
         ('\u{610}', '\u{61a}'), ('\u{64b}', '\u{65f}'), ('\u{670}', '\u{670}'), ('\u{6d6}',
@@ -1355,7 +1346,7 @@ pub fn Cc(c: char) -> bool {
         '\u{1e8d6}'), ('\u{e0100}', '\u{e01ef}')
     ];
 
-    pub static N_table: &'static [(char, char)] = &[
+    pub const N_table: &'static [(char, char)] = &[
         ('\u{30}', '\u{39}'), ('\u{660}', '\u{669}'), ('\u{6f0}', '\u{6f9}'), ('\u{7c0}',
         '\u{7c9}'), ('\u{966}', '\u{96f}'), ('\u{9e6}', '\u{9ef}'), ('\u{a66}', '\u{a6f}'),
         ('\u{ae6}', '\u{aef}'), ('\u{b66}', '\u{b6f}'), ('\u{be6}', '\u{bef}'), ('\u{c66}',
@@ -1381,7 +1372,7 @@ pub fn N(c: char) -> bool {
         super::bsearch_range_table(c, N_table)
     }
 
-    pub static Nd_table: &'static [(char, char)] = &[
+    pub const Nd_table: &'static [(char, char)] = &[
         ('\u{30}', '\u{39}'), ('\u{660}', '\u{669}'), ('\u{6f0}', '\u{6f9}'), ('\u{7c0}',
         '\u{7c9}'), ('\u{966}', '\u{96f}'), ('\u{9e6}', '\u{9ef}'), ('\u{a66}', '\u{a6f}'),
         ('\u{ae6}', '\u{aef}'), ('\u{b66}', '\u{b6f}'), ('\u{be6}', '\u{bef}'), ('\u{c66}',
@@ -1399,14 +1390,14 @@ pub fn N(c: char) -> bool {
         ('\u{16a60}', '\u{16a69}'), ('\u{16b50}', '\u{16b59}'), ('\u{1d7ce}', '\u{1d7ff}')
     ];
 
-    pub static Nl_table: &'static [(char, char)] = &[
+    pub const Nl_table: &'static [(char, char)] = &[
         ('\u{16ee}', '\u{16f0}'), ('\u{2160}', '\u{2182}'), ('\u{2185}', '\u{2188}'), ('\u{3007}',
         '\u{3007}'), ('\u{3021}', '\u{3029}'), ('\u{3038}', '\u{303a}'), ('\u{a6e6}', '\u{a6ef}'),
         ('\u{10140}', '\u{10174}'), ('\u{10341}', '\u{10341}'), ('\u{1034a}', '\u{1034a}'),
         ('\u{103d1}', '\u{103d5}'), ('\u{12400}', '\u{1246e}')
     ];
 
-    pub static No_table: &'static [(char, char)] = &[
+    pub const No_table: &'static [(char, char)] = &[
         ('\u{b2}', '\u{b3}'), ('\u{b9}', '\u{b9}'), ('\u{bc}', '\u{be}'), ('\u{9f4}', '\u{9f9}'),
         ('\u{b72}', '\u{b77}'), ('\u{bf0}', '\u{bf2}'), ('\u{c78}', '\u{c7e}'), ('\u{d70}',
         '\u{d75}'), ('\u{f2a}', '\u{f33}'), ('\u{1369}', '\u{137c}'), ('\u{17f0}', '\u{17f9}'),
@@ -1425,7 +1416,7 @@ pub fn N(c: char) -> bool {
         '\u{1d371}'), ('\u{1e8c7}', '\u{1e8cf}'), ('\u{1f100}', '\u{1f10c}')
     ];
 
-    pub static P_table: &'static [(char, char)] = &[
+    pub const P_table: &'static [(char, char)] = &[
         ('\u{21}', '\u{23}'), ('\u{25}', '\u{2a}'), ('\u{2c}', '\u{2f}'), ('\u{3a}', '\u{3b}'),
         ('\u{3f}', '\u{40}'), ('\u{5b}', '\u{5d}'), ('\u{5f}', '\u{5f}'), ('\u{7b}', '\u{7b}'),
         ('\u{7d}', '\u{7d}'), ('\u{a1}', '\u{a1}'), ('\u{a7}', '\u{a7}'), ('\u{ab}', '\u{ab}'),
@@ -1474,12 +1465,12 @@ pub fn N(c: char) -> bool {
         '\u{1bc9f}')
     ];
 
-    pub static Pc_table: &'static [(char, char)] = &[
+    pub const Pc_table: &'static [(char, char)] = &[
         ('\u{5f}', '\u{5f}'), ('\u{203f}', '\u{2040}'), ('\u{2054}', '\u{2054}'), ('\u{fe33}',
         '\u{fe34}'), ('\u{fe4d}', '\u{fe4f}'), ('\u{ff3f}', '\u{ff3f}')
     ];
 
-    pub static Pd_table: &'static [(char, char)] = &[
+    pub const Pd_table: &'static [(char, char)] = &[
         ('\u{2d}', '\u{2d}'), ('\u{58a}', '\u{58a}'), ('\u{5be}', '\u{5be}'), ('\u{1400}',
         '\u{1400}'), ('\u{1806}', '\u{1806}'), ('\u{2010}', '\u{2015}'), ('\u{2e17}', '\u{2e17}'),
         ('\u{2e1a}', '\u{2e1a}'), ('\u{2e3a}', '\u{2e3b}'), ('\u{2e40}', '\u{2e40}'), ('\u{301c}',
@@ -1487,7 +1478,7 @@ pub fn N(c: char) -> bool {
         ('\u{fe58}', '\u{fe58}'), ('\u{fe63}', '\u{fe63}'), ('\u{ff0d}', '\u{ff0d}')
     ];
 
-    pub static Pe_table: &'static [(char, char)] = &[
+    pub const Pe_table: &'static [(char, char)] = &[
         ('\u{29}', '\u{29}'), ('\u{5d}', '\u{5d}'), ('\u{7d}', '\u{7d}'), ('\u{f3b}', '\u{f3b}'),
         ('\u{f3d}', '\u{f3d}'), ('\u{169c}', '\u{169c}'), ('\u{2046}', '\u{2046}'), ('\u{207e}',
         '\u{207e}'), ('\u{208e}', '\u{208e}'), ('\u{2309}', '\u{2309}'), ('\u{230b}', '\u{230b}'),
@@ -1511,20 +1502,20 @@ pub fn N(c: char) -> bool {
         '\u{ff60}'), ('\u{ff63}', '\u{ff63}')
     ];
 
-    pub static Pf_table: &'static [(char, char)] = &[
+    pub const Pf_table: &'static [(char, char)] = &[
         ('\u{bb}', '\u{bb}'), ('\u{2019}', '\u{2019}'), ('\u{201d}', '\u{201d}'), ('\u{203a}',
         '\u{203a}'), ('\u{2e03}', '\u{2e03}'), ('\u{2e05}', '\u{2e05}'), ('\u{2e0a}', '\u{2e0a}'),
         ('\u{2e0d}', '\u{2e0d}'), ('\u{2e1d}', '\u{2e1d}'), ('\u{2e21}', '\u{2e21}')
     ];
 
-    pub static Pi_table: &'static [(char, char)] = &[
+    pub const Pi_table: &'static [(char, char)] = &[
         ('\u{ab}', '\u{ab}'), ('\u{2018}', '\u{2018}'), ('\u{201b}', '\u{201c}'), ('\u{201f}',
         '\u{201f}'), ('\u{2039}', '\u{2039}'), ('\u{2e02}', '\u{2e02}'), ('\u{2e04}', '\u{2e04}'),
         ('\u{2e09}', '\u{2e09}'), ('\u{2e0c}', '\u{2e0c}'), ('\u{2e1c}', '\u{2e1c}'), ('\u{2e20}',
         '\u{2e20}')
     ];
 
-    pub static Po_table: &'static [(char, char)] = &[
+    pub const Po_table: &'static [(char, char)] = &[
         ('\u{21}', '\u{23}'), ('\u{25}', '\u{27}'), ('\u{2a}', '\u{2a}'), ('\u{2c}', '\u{2c}'),
         ('\u{2e}', '\u{2f}'), ('\u{3a}', '\u{3b}'), ('\u{3f}', '\u{40}'), ('\u{5c}', '\u{5c}'),
         ('\u{a1}', '\u{a1}'), ('\u{a7}', '\u{a7}'), ('\u{b6}', '\u{b7}'), ('\u{bf}', '\u{bf}'),
@@ -1572,7 +1563,7 @@ pub fn N(c: char) -> bool {
         '\u{1bc9f}')
     ];
 
-    pub static Ps_table: &'static [(char, char)] = &[
+    pub const Ps_table: &'static [(char, char)] = &[
         ('\u{28}', '\u{28}'), ('\u{5b}', '\u{5b}'), ('\u{7b}', '\u{7b}'), ('\u{f3a}', '\u{f3a}'),
         ('\u{f3c}', '\u{f3c}'), ('\u{169b}', '\u{169b}'), ('\u{201a}', '\u{201a}'), ('\u{201e}',
         '\u{201e}'), ('\u{2045}', '\u{2045}'), ('\u{207d}', '\u{207d}'), ('\u{208d}', '\u{208d}'),
@@ -1597,7 +1588,7 @@ pub fn N(c: char) -> bool {
         ('\u{ff62}', '\u{ff62}')
     ];
 
-    pub static S_table: &'static [(char, char)] = &[
+    pub const S_table: &'static [(char, char)] = &[
         ('\u{24}', '\u{24}'), ('\u{2b}', '\u{2b}'), ('\u{3c}', '\u{3e}'), ('\u{5e}', '\u{5e}'),
         ('\u{60}', '\u{60}'), ('\u{7c}', '\u{7c}'), ('\u{7e}', '\u{7e}'), ('\u{a2}', '\u{a6}'),
         ('\u{a8}', '\u{a9}'), ('\u{ac}', '\u{ac}'), ('\u{ae}', '\u{b1}'), ('\u{b4}', '\u{b4}'),
@@ -1663,7 +1654,7 @@ pub fn N(c: char) -> bool {
         '\u{1f887}'), ('\u{1f890}', '\u{1f8ad}')
     ];
 
-    pub static Sc_table: &'static [(char, char)] = &[
+    pub const Sc_table: &'static [(char, char)] = &[
         ('\u{24}', '\u{24}'), ('\u{a2}', '\u{a5}'), ('\u{58f}', '\u{58f}'), ('\u{60b}', '\u{60b}'),
         ('\u{9f2}', '\u{9f3}'), ('\u{9fb}', '\u{9fb}'), ('\u{af1}', '\u{af1}'), ('\u{bf9}',
         '\u{bf9}'), ('\u{e3f}', '\u{e3f}'), ('\u{17db}', '\u{17db}'), ('\u{20a0}', '\u{20bd}'),
@@ -1671,7 +1662,7 @@ pub fn N(c: char) -> bool {
         '\u{ff04}'), ('\u{ffe0}', '\u{ffe1}'), ('\u{ffe5}', '\u{ffe6}')
     ];
 
-    pub static Sk_table: &'static [(char, char)] = &[
+    pub const Sk_table: &'static [(char, char)] = &[
         ('\u{5e}', '\u{5e}'), ('\u{60}', '\u{60}'), ('\u{a8}', '\u{a8}'), ('\u{af}', '\u{af}'),
         ('\u{b4}', '\u{b4}'), ('\u{b8}', '\u{b8}'), ('\u{2c2}', '\u{2c5}'), ('\u{2d2}', '\u{2df}'),
         ('\u{2e5}', '\u{2eb}'), ('\u{2ed}', '\u{2ed}'), ('\u{2ef}', '\u{2ff}'), ('\u{375}',
@@ -1682,7 +1673,7 @@ pub fn N(c: char) -> bool {
         '\u{ff3e}'), ('\u{ff40}', '\u{ff40}'), ('\u{ffe3}', '\u{ffe3}')
     ];
 
-    pub static Sm_table: &'static [(char, char)] = &[
+    pub const Sm_table: &'static [(char, char)] = &[
         ('\u{2b}', '\u{2b}'), ('\u{3c}', '\u{3e}'), ('\u{7c}', '\u{7c}'), ('\u{7e}', '\u{7e}'),
         ('\u{ac}', '\u{ac}'), ('\u{b1}', '\u{b1}'), ('\u{d7}', '\u{d7}'), ('\u{f7}', '\u{f7}'),
         ('\u{3f6}', '\u{3f6}'), ('\u{606}', '\u{608}'), ('\u{2044}', '\u{2044}'), ('\u{2052}',
@@ -1704,7 +1695,7 @@ pub fn N(c: char) -> bool {
         '\u{1d7c3}'), ('\u{1eef0}', '\u{1eef1}')
     ];
 
-    pub static So_table: &'static [(char, char)] = &[
+    pub const So_table: &'static [(char, char)] = &[
         ('\u{a6}', '\u{a6}'), ('\u{a9}', '\u{a9}'), ('\u{ae}', '\u{ae}'), ('\u{b0}', '\u{b0}'),
         ('\u{482}', '\u{482}'), ('\u{58d}', '\u{58e}'), ('\u{60e}', '\u{60f}'), ('\u{6de}',
         '\u{6de}'), ('\u{6e9}', '\u{6e9}'), ('\u{6fd}', '\u{6fe}'), ('\u{7f6}', '\u{7f6}'),
@@ -1757,21 +1748,21 @@ pub fn N(c: char) -> bool {
         '\u{1f887}'), ('\u{1f890}', '\u{1f8ad}')
     ];
 
-    pub static Z_table: &'static [(char, char)] = &[
+    pub const Z_table: &'static [(char, char)] = &[
         ('\u{20}', '\u{20}'), ('\u{a0}', '\u{a0}'), ('\u{1680}', '\u{1680}'), ('\u{2000}',
         '\u{200a}'), ('\u{2028}', '\u{2029}'), ('\u{202f}', '\u{202f}'), ('\u{205f}', '\u{205f}'),
         ('\u{3000}', '\u{3000}')
     ];
 
-    pub static Zl_table: &'static [(char, char)] = &[
+    pub const Zl_table: &'static [(char, char)] = &[
         ('\u{2028}', '\u{2028}')
     ];
 
-    pub static Zp_table: &'static [(char, char)] = &[
+    pub const Zp_table: &'static [(char, char)] = &[
         ('\u{2029}', '\u{2029}')
     ];
 
-    pub static Zs_table: &'static [(char, char)] = &[
+    pub const Zs_table: &'static [(char, char)] = &[
         ('\u{20}', '\u{20}'), ('\u{a0}', '\u{a0}'), ('\u{1680}', '\u{1680}'), ('\u{2000}',
         '\u{200a}'), ('\u{202f}', '\u{202f}'), ('\u{205f}', '\u{205f}'), ('\u{3000}', '\u{3000}')
     ];
@@ -1779,7 +1770,7 @@ pub fn N(c: char) -> bool {
 }
 
 pub mod derived_property {
-    pub static Alphabetic_table: &'static [(char, char)] = &[
+    pub const Alphabetic_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{5a}'), ('\u{61}', '\u{7a}'), ('\u{aa}', '\u{aa}'), ('\u{b5}', '\u{b5}'),
         ('\u{ba}', '\u{ba}'), ('\u{c0}', '\u{d6}'), ('\u{d8}', '\u{f6}'), ('\u{f8}', '\u{1ba}'),
         ('\u{1bb}', '\u{1bb}'), ('\u{1bc}', '\u{1bf}'), ('\u{1c0}', '\u{1c3}'), ('\u{1c4}',
@@ -2057,7 +2048,7 @@ pub fn Alphabetic(c: char) -> bool {
         super::bsearch_range_table(c, Alphabetic_table)
     }
 
-    pub static Default_Ignorable_Code_Point_table: &'static [(char, char)] = &[
+    pub const Default_Ignorable_Code_Point_table: &'static [(char, char)] = &[
         ('\u{ad}', '\u{ad}'), ('\u{34f}', '\u{34f}'), ('\u{61c}', '\u{61c}'), ('\u{115f}',
         '\u{1160}'), ('\u{17b4}', '\u{17b5}'), ('\u{180b}', '\u{180d}'), ('\u{180e}', '\u{180e}'),
         ('\u{200b}', '\u{200f}'), ('\u{202a}', '\u{202e}'), ('\u{2060}', '\u{2064}'), ('\u{2065}',
@@ -2068,7 +2059,7 @@ pub fn Alphabetic(c: char) -> bool {
         '\u{e00ff}'), ('\u{e0100}', '\u{e01ef}'), ('\u{e01f0}', '\u{e0fff}')
     ];
 
-    pub static Lowercase_table: &'static [(char, char)] = &[
+    pub const Lowercase_table: &'static [(char, char)] = &[
         ('\u{61}', '\u{7a}'), ('\u{aa}', '\u{aa}'), ('\u{b5}', '\u{b5}'), ('\u{ba}', '\u{ba}'),
         ('\u{df}', '\u{f6}'), ('\u{f8}', '\u{ff}'), ('\u{101}', '\u{101}'), ('\u{103}', '\u{103}'),
         ('\u{105}', '\u{105}'), ('\u{107}', '\u{107}'), ('\u{109}', '\u{109}'), ('\u{10b}',
@@ -2261,7 +2252,7 @@ pub fn Lowercase(c: char) -> bool {
         super::bsearch_range_table(c, Lowercase_table)
     }
 
-    pub static Uppercase_table: &'static [(char, char)] = &[
+    pub const Uppercase_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{5a}'), ('\u{c0}', '\u{d6}'), ('\u{d8}', '\u{de}'), ('\u{100}', '\u{100}'),
         ('\u{102}', '\u{102}'), ('\u{104}', '\u{104}'), ('\u{106}', '\u{106}'), ('\u{108}',
         '\u{108}'), ('\u{10a}', '\u{10a}'), ('\u{10c}', '\u{10c}'), ('\u{10e}', '\u{10e}'),
@@ -2449,7 +2440,7 @@ pub fn Uppercase(c: char) -> bool {
         super::bsearch_range_table(c, Uppercase_table)
     }
 
-    pub static XID_Continue_table: &'static [(char, char)] = &[
+    pub const XID_Continue_table: &'static [(char, char)] = &[
         ('\u{30}', '\u{39}'), ('\u{41}', '\u{5a}'), ('\u{5f}', '\u{5f}'), ('\u{61}', '\u{7a}'),
         ('\u{aa}', '\u{aa}'), ('\u{b5}', '\u{b5}'), ('\u{b7}', '\u{b7}'), ('\u{ba}', '\u{ba}'),
         ('\u{c0}', '\u{d6}'), ('\u{d8}', '\u{f6}'), ('\u{f8}', '\u{1ba}'), ('\u{1bb}', '\u{1bb}'),
@@ -2775,7 +2766,7 @@ pub fn XID_Continue(c: char) -> bool {
         super::bsearch_range_table(c, XID_Continue_table)
     }
 
-    pub static XID_Start_table: &'static [(char, char)] = &[
+    pub const XID_Start_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{5a}'), ('\u{61}', '\u{7a}'), ('\u{aa}', '\u{aa}'), ('\u{b5}', '\u{b5}'),
         ('\u{ba}', '\u{ba}'), ('\u{c0}', '\u{d6}'), ('\u{d8}', '\u{f6}'), ('\u{f8}', '\u{1ba}'),
         ('\u{1bb}', '\u{1bb}'), ('\u{1bc}', '\u{1bf}'), ('\u{1c0}', '\u{1c3}'), ('\u{1c4}',
@@ -2967,7 +2958,7 @@ pub fn XID_Start(c: char) -> bool {
 }
 
 pub mod script {
-    pub static Arabic_table: &'static [(char, char)] = &[
+    pub const Arabic_table: &'static [(char, char)] = &[
         ('\u{600}', '\u{604}'), ('\u{606}', '\u{608}'), ('\u{609}', '\u{60a}'), ('\u{60b}',
         '\u{60b}'), ('\u{60d}', '\u{60d}'), ('\u{60e}', '\u{60f}'), ('\u{610}', '\u{61a}'),
         ('\u{61e}', '\u{61e}'), ('\u{620}', '\u{63f}'), ('\u{641}', '\u{64a}'), ('\u{656}',
@@ -2994,17 +2985,17 @@ pub mod script {
         ('\u{1eef0}', '\u{1eef1}')
     ];
 
-    pub static Armenian_table: &'static [(char, char)] = &[
+    pub const Armenian_table: &'static [(char, char)] = &[
         ('\u{531}', '\u{556}'), ('\u{559}', '\u{559}'), ('\u{55a}', '\u{55f}'), ('\u{561}',
         '\u{587}'), ('\u{58a}', '\u{58a}'), ('\u{58d}', '\u{58e}'), ('\u{58f}', '\u{58f}'),
         ('\u{fb13}', '\u{fb17}')
     ];
 
-    pub static Avestan_table: &'static [(char, char)] = &[
+    pub const Avestan_table: &'static [(char, char)] = &[
         ('\u{10b00}', '\u{10b35}'), ('\u{10b39}', '\u{10b3f}')
     ];
 
-    pub static Balinese_table: &'static [(char, char)] = &[
+    pub const Balinese_table: &'static [(char, char)] = &[
         ('\u{1b00}', '\u{1b03}'), ('\u{1b04}', '\u{1b04}'), ('\u{1b05}', '\u{1b33}'), ('\u{1b34}',
         '\u{1b34}'), ('\u{1b35}', '\u{1b35}'), ('\u{1b36}', '\u{1b3a}'), ('\u{1b3b}', '\u{1b3b}'),
         ('\u{1b3c}', '\u{1b3c}'), ('\u{1b3d}', '\u{1b41}'), ('\u{1b42}', '\u{1b42}'), ('\u{1b43}',
@@ -3012,22 +3003,22 @@ pub mod script {
         ('\u{1b61}', '\u{1b6a}'), ('\u{1b6b}', '\u{1b73}'), ('\u{1b74}', '\u{1b7c}')
     ];
 
-    pub static Bamum_table: &'static [(char, char)] = &[
+    pub const Bamum_table: &'static [(char, char)] = &[
         ('\u{a6a0}', '\u{a6e5}'), ('\u{a6e6}', '\u{a6ef}'), ('\u{a6f0}', '\u{a6f1}'), ('\u{a6f2}',
         '\u{a6f7}'), ('\u{16800}', '\u{16a38}')
     ];
 
-    pub static Bassa_Vah_table: &'static [(char, char)] = &[
+    pub const Bassa_Vah_table: &'static [(char, char)] = &[
         ('\u{16ad0}', '\u{16aed}'), ('\u{16af0}', '\u{16af4}'), ('\u{16af5}', '\u{16af5}')
     ];
 
-    pub static Batak_table: &'static [(char, char)] = &[
+    pub const Batak_table: &'static [(char, char)] = &[
         ('\u{1bc0}', '\u{1be5}'), ('\u{1be6}', '\u{1be6}'), ('\u{1be7}', '\u{1be7}'), ('\u{1be8}',
         '\u{1be9}'), ('\u{1bea}', '\u{1bec}'), ('\u{1bed}', '\u{1bed}'), ('\u{1bee}', '\u{1bee}'),
         ('\u{1bef}', '\u{1bf1}'), ('\u{1bf2}', '\u{1bf3}'), ('\u{1bfc}', '\u{1bff}')
     ];
 
-    pub static Bengali_table: &'static [(char, char)] = &[
+    pub const Bengali_table: &'static [(char, char)] = &[
         ('\u{980}', '\u{980}'), ('\u{981}', '\u{981}'), ('\u{982}', '\u{983}'), ('\u{985}',
         '\u{98c}'), ('\u{98f}', '\u{990}'), ('\u{993}', '\u{9a8}'), ('\u{9aa}', '\u{9b0}'),
         ('\u{9b2}', '\u{9b2}'), ('\u{9b6}', '\u{9b9}'), ('\u{9bc}', '\u{9bc}'), ('\u{9bd}',
@@ -3038,60 +3029,60 @@ pub mod script {
         '\u{9f9}'), ('\u{9fa}', '\u{9fa}'), ('\u{9fb}', '\u{9fb}')
     ];
 
-    pub static Bopomofo_table: &'static [(char, char)] = &[
+    pub const Bopomofo_table: &'static [(char, char)] = &[
         ('\u{2ea}', '\u{2eb}'), ('\u{3105}', '\u{312d}'), ('\u{31a0}', '\u{31ba}')
     ];
 
-    pub static Brahmi_table: &'static [(char, char)] = &[
+    pub const Brahmi_table: &'static [(char, char)] = &[
         ('\u{11000}', '\u{11000}'), ('\u{11001}', '\u{11001}'), ('\u{11002}', '\u{11002}'),
         ('\u{11003}', '\u{11037}'), ('\u{11038}', '\u{11046}'), ('\u{11047}', '\u{1104d}'),
         ('\u{11052}', '\u{11065}'), ('\u{11066}', '\u{1106f}'), ('\u{1107f}', '\u{1107f}')
     ];
 
-    pub static Braille_table: &'static [(char, char)] = &[
+    pub const Braille_table: &'static [(char, char)] = &[
         ('\u{2800}', '\u{28ff}')
     ];
 
-    pub static Buginese_table: &'static [(char, char)] = &[
+    pub const Buginese_table: &'static [(char, char)] = &[
         ('\u{1a00}', '\u{1a16}'), ('\u{1a17}', '\u{1a18}'), ('\u{1a19}', '\u{1a1a}'), ('\u{1a1b}',
         '\u{1a1b}'), ('\u{1a1e}', '\u{1a1f}')
     ];
 
-    pub static Buhid_table: &'static [(char, char)] = &[
+    pub const Buhid_table: &'static [(char, char)] = &[
         ('\u{1740}', '\u{1751}'), ('\u{1752}', '\u{1753}')
     ];
 
-    pub static Canadian_Aboriginal_table: &'static [(char, char)] = &[
+    pub const Canadian_Aboriginal_table: &'static [(char, char)] = &[
         ('\u{1400}', '\u{1400}'), ('\u{1401}', '\u{166c}'), ('\u{166d}', '\u{166e}'), ('\u{166f}',
         '\u{167f}'), ('\u{18b0}', '\u{18f5}')
     ];
 
-    pub static Carian_table: &'static [(char, char)] = &[
+    pub const Carian_table: &'static [(char, char)] = &[
         ('\u{102a0}', '\u{102d0}')
     ];
 
-    pub static Caucasian_Albanian_table: &'static [(char, char)] = &[
+    pub const Caucasian_Albanian_table: &'static [(char, char)] = &[
         ('\u{10530}', '\u{10563}'), ('\u{1056f}', '\u{1056f}')
     ];
 
-    pub static Chakma_table: &'static [(char, char)] = &[
+    pub const Chakma_table: &'static [(char, char)] = &[
         ('\u{11100}', '\u{11102}'), ('\u{11103}', '\u{11126}'), ('\u{11127}', '\u{1112b}'),
         ('\u{1112c}', '\u{1112c}'), ('\u{1112d}', '\u{11134}'), ('\u{11136}', '\u{1113f}'),
         ('\u{11140}', '\u{11143}')
     ];
 
-    pub static Cham_table: &'static [(char, char)] = &[
+    pub const Cham_table: &'static [(char, char)] = &[
         ('\u{aa00}', '\u{aa28}'), ('\u{aa29}', '\u{aa2e}'), ('\u{aa2f}', '\u{aa30}'), ('\u{aa31}',
         '\u{aa32}'), ('\u{aa33}', '\u{aa34}'), ('\u{aa35}', '\u{aa36}'), ('\u{aa40}', '\u{aa42}'),
         ('\u{aa43}', '\u{aa43}'), ('\u{aa44}', '\u{aa4b}'), ('\u{aa4c}', '\u{aa4c}'), ('\u{aa4d}',
         '\u{aa4d}'), ('\u{aa50}', '\u{aa59}'), ('\u{aa5c}', '\u{aa5f}')
     ];
 
-    pub static Cherokee_table: &'static [(char, char)] = &[
+    pub const Cherokee_table: &'static [(char, char)] = &[
         ('\u{13a0}', '\u{13f4}')
     ];
 
-    pub static Common_table: &'static [(char, char)] = &[
+    pub const Common_table: &'static [(char, char)] = &[
         ('\u{0}', '\u{1f}'), ('\u{20}', '\u{20}'), ('\u{21}', '\u{23}'), ('\u{24}', '\u{24}'),
         ('\u{25}', '\u{27}'), ('\u{28}', '\u{28}'), ('\u{29}', '\u{29}'), ('\u{2a}', '\u{2a}'),
         ('\u{2b}', '\u{2b}'), ('\u{2c}', '\u{2c}'), ('\u{2d}', '\u{2d}'), ('\u{2e}', '\u{2f}'),
@@ -3261,22 +3252,22 @@ pub mod script {
         ('\u{1f890}', '\u{1f8ad}'), ('\u{e0001}', '\u{e0001}'), ('\u{e0020}', '\u{e007f}')
     ];
 
-    pub static Coptic_table: &'static [(char, char)] = &[
+    pub const Coptic_table: &'static [(char, char)] = &[
         ('\u{3e2}', '\u{3ef}'), ('\u{2c80}', '\u{2ce4}'), ('\u{2ce5}', '\u{2cea}'), ('\u{2ceb}',
         '\u{2cee}'), ('\u{2cef}', '\u{2cf1}'), ('\u{2cf2}', '\u{2cf3}'), ('\u{2cf9}', '\u{2cfc}'),
         ('\u{2cfd}', '\u{2cfd}'), ('\u{2cfe}', '\u{2cff}')
     ];
 
-    pub static Cuneiform_table: &'static [(char, char)] = &[
+    pub const Cuneiform_table: &'static [(char, char)] = &[
         ('\u{12000}', '\u{12398}'), ('\u{12400}', '\u{1246e}'), ('\u{12470}', '\u{12474}')
     ];
 
-    pub static Cypriot_table: &'static [(char, char)] = &[
+    pub const Cypriot_table: &'static [(char, char)] = &[
         ('\u{10800}', '\u{10805}'), ('\u{10808}', '\u{10808}'), ('\u{1080a}', '\u{10835}'),
         ('\u{10837}', '\u{10838}'), ('\u{1083c}', '\u{1083c}'), ('\u{1083f}', '\u{1083f}')
     ];
 
-    pub static Cyrillic_table: &'static [(char, char)] = &[
+    pub const Cyrillic_table: &'static [(char, char)] = &[
         ('\u{400}', '\u{481}'), ('\u{482}', '\u{482}'), ('\u{483}', '\u{484}'), ('\u{487}',
         '\u{487}'), ('\u{488}', '\u{489}'), ('\u{48a}', '\u{52f}'), ('\u{1d2b}', '\u{1d2b}'),
         ('\u{1d78}', '\u{1d78}'), ('\u{2de0}', '\u{2dff}'), ('\u{a640}', '\u{a66d}'), ('\u{a66e}',
@@ -3285,11 +3276,11 @@ pub mod script {
         '\u{a69b}'), ('\u{a69c}', '\u{a69d}'), ('\u{a69f}', '\u{a69f}')
     ];
 
-    pub static Deseret_table: &'static [(char, char)] = &[
+    pub const Deseret_table: &'static [(char, char)] = &[
         ('\u{10400}', '\u{1044f}')
     ];
 
-    pub static Devanagari_table: &'static [(char, char)] = &[
+    pub const Devanagari_table: &'static [(char, char)] = &[
         ('\u{900}', '\u{902}'), ('\u{903}', '\u{903}'), ('\u{904}', '\u{939}'), ('\u{93a}',
         '\u{93a}'), ('\u{93b}', '\u{93b}'), ('\u{93c}', '\u{93c}'), ('\u{93d}', '\u{93d}'),
         ('\u{93e}', '\u{940}'), ('\u{941}', '\u{948}'), ('\u{949}', '\u{94c}'), ('\u{94d}',
@@ -3299,21 +3290,21 @@ pub mod script {
         ('\u{a8f2}', '\u{a8f7}'), ('\u{a8f8}', '\u{a8fa}'), ('\u{a8fb}', '\u{a8fb}')
     ];
 
-    pub static Duployan_table: &'static [(char, char)] = &[
+    pub const Duployan_table: &'static [(char, char)] = &[
         ('\u{1bc00}', '\u{1bc6a}'), ('\u{1bc70}', '\u{1bc7c}'), ('\u{1bc80}', '\u{1bc88}'),
         ('\u{1bc90}', '\u{1bc99}'), ('\u{1bc9c}', '\u{1bc9c}'), ('\u{1bc9d}', '\u{1bc9e}'),
         ('\u{1bc9f}', '\u{1bc9f}')
     ];
 
-    pub static Egyptian_Hieroglyphs_table: &'static [(char, char)] = &[
+    pub const Egyptian_Hieroglyphs_table: &'static [(char, char)] = &[
         ('\u{13000}', '\u{1342e}')
     ];
 
-    pub static Elbasan_table: &'static [(char, char)] = &[
+    pub const Elbasan_table: &'static [(char, char)] = &[
         ('\u{10500}', '\u{10527}')
     ];
 
-    pub static Ethiopic_table: &'static [(char, char)] = &[
+    pub const Ethiopic_table: &'static [(char, char)] = &[
         ('\u{1200}', '\u{1248}'), ('\u{124a}', '\u{124d}'), ('\u{1250}', '\u{1256}'), ('\u{1258}',
         '\u{1258}'), ('\u{125a}', '\u{125d}'), ('\u{1260}', '\u{1288}'), ('\u{128a}', '\u{128d}'),
         ('\u{1290}', '\u{12b0}'), ('\u{12b2}', '\u{12b5}'), ('\u{12b8}', '\u{12be}'), ('\u{12c0}',
@@ -3326,22 +3317,22 @@ pub mod script {
         '\u{ab0e}'), ('\u{ab11}', '\u{ab16}'), ('\u{ab20}', '\u{ab26}'), ('\u{ab28}', '\u{ab2e}')
     ];
 
-    pub static Georgian_table: &'static [(char, char)] = &[
+    pub const Georgian_table: &'static [(char, char)] = &[
         ('\u{10a0}', '\u{10c5}'), ('\u{10c7}', '\u{10c7}'), ('\u{10cd}', '\u{10cd}'), ('\u{10d0}',
         '\u{10fa}'), ('\u{10fc}', '\u{10fc}'), ('\u{10fd}', '\u{10ff}'), ('\u{2d00}', '\u{2d25}'),
         ('\u{2d27}', '\u{2d27}'), ('\u{2d2d}', '\u{2d2d}')
     ];
 
-    pub static Glagolitic_table: &'static [(char, char)] = &[
+    pub const Glagolitic_table: &'static [(char, char)] = &[
         ('\u{2c00}', '\u{2c2e}'), ('\u{2c30}', '\u{2c5e}')
     ];
 
-    pub static Gothic_table: &'static [(char, char)] = &[
+    pub const Gothic_table: &'static [(char, char)] = &[
         ('\u{10330}', '\u{10340}'), ('\u{10341}', '\u{10341}'), ('\u{10342}', '\u{10349}'),
         ('\u{1034a}', '\u{1034a}')
     ];
 
-    pub static Grantha_table: &'static [(char, char)] = &[
+    pub const Grantha_table: &'static [(char, char)] = &[
         ('\u{11301}', '\u{11301}'), ('\u{11302}', '\u{11303}'), ('\u{11305}', '\u{1130c}'),
         ('\u{1130f}', '\u{11310}'), ('\u{11313}', '\u{11328}'), ('\u{1132a}', '\u{11330}'),
         ('\u{11332}', '\u{11333}'), ('\u{11335}', '\u{11339}'), ('\u{1133c}', '\u{1133c}'),
@@ -3351,7 +3342,7 @@ pub mod script {
         ('\u{11366}', '\u{1136c}'), ('\u{11370}', '\u{11374}')
     ];
 
-    pub static Greek_table: &'static [(char, char)] = &[
+    pub const Greek_table: &'static [(char, char)] = &[
         ('\u{370}', '\u{373}'), ('\u{375}', '\u{375}'), ('\u{376}', '\u{377}'), ('\u{37a}',
         '\u{37a}'), ('\u{37b}', '\u{37d}'), ('\u{37f}', '\u{37f}'), ('\u{384}', '\u{384}'),
         ('\u{386}', '\u{386}'), ('\u{388}', '\u{38a}'), ('\u{38c}', '\u{38c}'), ('\u{38e}',
@@ -3371,7 +3362,7 @@ pub mod script {
         '\u{1d245}')
     ];
 
-    pub static Gujarati_table: &'static [(char, char)] = &[
+    pub const Gujarati_table: &'static [(char, char)] = &[
         ('\u{a81}', '\u{a82}'), ('\u{a83}', '\u{a83}'), ('\u{a85}', '\u{a8d}'), ('\u{a8f}',
         '\u{a91}'), ('\u{a93}', '\u{aa8}'), ('\u{aaa}', '\u{ab0}'), ('\u{ab2}', '\u{ab3}'),
         ('\u{ab5}', '\u{ab9}'), ('\u{abc}', '\u{abc}'), ('\u{abd}', '\u{abd}'), ('\u{abe}',
@@ -3381,7 +3372,7 @@ pub mod script {
         ('\u{af1}', '\u{af1}')
     ];
 
-    pub static Gurmukhi_table: &'static [(char, char)] = &[
+    pub const Gurmukhi_table: &'static [(char, char)] = &[
         ('\u{a01}', '\u{a02}'), ('\u{a03}', '\u{a03}'), ('\u{a05}', '\u{a0a}'), ('\u{a0f}',
         '\u{a10}'), ('\u{a13}', '\u{a28}'), ('\u{a2a}', '\u{a30}'), ('\u{a32}', '\u{a33}'),
         ('\u{a35}', '\u{a36}'), ('\u{a38}', '\u{a39}'), ('\u{a3c}', '\u{a3c}'), ('\u{a3e}',
@@ -3390,7 +3381,7 @@ pub mod script {
         '\u{a6f}'), ('\u{a70}', '\u{a71}'), ('\u{a72}', '\u{a74}'), ('\u{a75}', '\u{a75}')
     ];
 
-    pub static Han_table: &'static [(char, char)] = &[
+    pub const Han_table: &'static [(char, char)] = &[
         ('\u{2e80}', '\u{2e99}'), ('\u{2e9b}', '\u{2ef3}'), ('\u{2f00}', '\u{2fd5}'), ('\u{3005}',
         '\u{3005}'), ('\u{3007}', '\u{3007}'), ('\u{3021}', '\u{3029}'), ('\u{3038}', '\u{303a}'),
         ('\u{303b}', '\u{303b}'), ('\u{3400}', '\u{4db5}'), ('\u{4e00}', '\u{9fcc}'), ('\u{f900}',
@@ -3398,18 +3389,18 @@ pub mod script {
         '\u{2b734}'), ('\u{2b740}', '\u{2b81d}'), ('\u{2f800}', '\u{2fa1d}')
     ];
 
-    pub static Hangul_table: &'static [(char, char)] = &[
+    pub const Hangul_table: &'static [(char, char)] = &[
         ('\u{1100}', '\u{11ff}'), ('\u{302e}', '\u{302f}'), ('\u{3131}', '\u{318e}'), ('\u{3200}',
         '\u{321e}'), ('\u{3260}', '\u{327e}'), ('\u{a960}', '\u{a97c}'), ('\u{ac00}', '\u{d7a3}'),
         ('\u{d7b0}', '\u{d7c6}'), ('\u{d7cb}', '\u{d7fb}'), ('\u{ffa0}', '\u{ffbe}'), ('\u{ffc2}',
         '\u{ffc7}'), ('\u{ffca}', '\u{ffcf}'), ('\u{ffd2}', '\u{ffd7}'), ('\u{ffda}', '\u{ffdc}')
     ];
 
-    pub static Hanunoo_table: &'static [(char, char)] = &[
+    pub const Hanunoo_table: &'static [(char, char)] = &[
         ('\u{1720}', '\u{1731}'), ('\u{1732}', '\u{1734}')
     ];
 
-    pub static Hebrew_table: &'static [(char, char)] = &[
+    pub const Hebrew_table: &'static [(char, char)] = &[
         ('\u{591}', '\u{5bd}'), ('\u{5be}', '\u{5be}'), ('\u{5bf}', '\u{5bf}'), ('\u{5c0}',
         '\u{5c0}'), ('\u{5c1}', '\u{5c2}'), ('\u{5c3}', '\u{5c3}'), ('\u{5c4}', '\u{5c5}'),
         ('\u{5c6}', '\u{5c6}'), ('\u{5c7}', '\u{5c7}'), ('\u{5d0}', '\u{5ea}'), ('\u{5f0}',
@@ -3419,16 +3410,16 @@ pub mod script {
         ('\u{fb46}', '\u{fb4f}')
     ];
 
-    pub static Hiragana_table: &'static [(char, char)] = &[
+    pub const Hiragana_table: &'static [(char, char)] = &[
         ('\u{3041}', '\u{3096}'), ('\u{309d}', '\u{309e}'), ('\u{309f}', '\u{309f}'), ('\u{1b001}',
         '\u{1b001}'), ('\u{1f200}', '\u{1f200}')
     ];
 
-    pub static Imperial_Aramaic_table: &'static [(char, char)] = &[
+    pub const Imperial_Aramaic_table: &'static [(char, char)] = &[
         ('\u{10840}', '\u{10855}'), ('\u{10857}', '\u{10857}'), ('\u{10858}', '\u{1085f}')
     ];
 
-    pub static Inherited_table: &'static [(char, char)] = &[
+    pub const Inherited_table: &'static [(char, char)] = &[
         ('\u{300}', '\u{36f}'), ('\u{485}', '\u{486}'), ('\u{64b}', '\u{655}'), ('\u{670}',
         '\u{670}'), ('\u{951}', '\u{952}'), ('\u{1ab0}', '\u{1abd}'), ('\u{1abe}', '\u{1abe}'),
         ('\u{1cd0}', '\u{1cd2}'), ('\u{1cd4}', '\u{1ce0}'), ('\u{1ce2}', '\u{1ce8}'), ('\u{1ced}',
@@ -3441,29 +3432,29 @@ pub mod script {
         '\u{1d1ad}'), ('\u{e0100}', '\u{e01ef}')
     ];
 
-    pub static Inscriptional_Pahlavi_table: &'static [(char, char)] = &[
+    pub const Inscriptional_Pahlavi_table: &'static [(char, char)] = &[
         ('\u{10b60}', '\u{10b72}'), ('\u{10b78}', '\u{10b7f}')
     ];
 
-    pub static Inscriptional_Parthian_table: &'static [(char, char)] = &[
+    pub const Inscriptional_Parthian_table: &'static [(char, char)] = &[
         ('\u{10b40}', '\u{10b55}'), ('\u{10b58}', '\u{10b5f}')
     ];
 
-    pub static Javanese_table: &'static [(char, char)] = &[
+    pub const Javanese_table: &'static [(char, char)] = &[
         ('\u{a980}', '\u{a982}'), ('\u{a983}', '\u{a983}'), ('\u{a984}', '\u{a9b2}'), ('\u{a9b3}',
         '\u{a9b3}'), ('\u{a9b4}', '\u{a9b5}'), ('\u{a9b6}', '\u{a9b9}'), ('\u{a9ba}', '\u{a9bb}'),
         ('\u{a9bc}', '\u{a9bc}'), ('\u{a9bd}', '\u{a9c0}'), ('\u{a9c1}', '\u{a9cd}'), ('\u{a9d0}',
         '\u{a9d9}'), ('\u{a9de}', '\u{a9df}')
     ];
 
-    pub static Kaithi_table: &'static [(char, char)] = &[
+    pub const Kaithi_table: &'static [(char, char)] = &[
         ('\u{11080}', '\u{11081}'), ('\u{11082}', '\u{11082}'), ('\u{11083}', '\u{110af}'),
         ('\u{110b0}', '\u{110b2}'), ('\u{110b3}', '\u{110b6}'), ('\u{110b7}', '\u{110b8}'),
         ('\u{110b9}', '\u{110ba}'), ('\u{110bb}', '\u{110bc}'), ('\u{110bd}', '\u{110bd}'),
         ('\u{110be}', '\u{110c1}')
     ];
 
-    pub static Kannada_table: &'static [(char, char)] = &[
+    pub const Kannada_table: &'static [(char, char)] = &[
         ('\u{c81}', '\u{c81}'), ('\u{c82}', '\u{c83}'), ('\u{c85}', '\u{c8c}'), ('\u{c8e}',
         '\u{c90}'), ('\u{c92}', '\u{ca8}'), ('\u{caa}', '\u{cb3}'), ('\u{cb5}', '\u{cb9}'),
         ('\u{cbc}', '\u{cbc}'), ('\u{cbd}', '\u{cbd}'), ('\u{cbe}', '\u{cbe}'), ('\u{cbf}',
@@ -3473,25 +3464,25 @@ pub mod script {
         ('\u{cf1}', '\u{cf2}')
     ];
 
-    pub static Katakana_table: &'static [(char, char)] = &[
+    pub const Katakana_table: &'static [(char, char)] = &[
         ('\u{30a1}', '\u{30fa}'), ('\u{30fd}', '\u{30fe}'), ('\u{30ff}', '\u{30ff}'), ('\u{31f0}',
         '\u{31ff}'), ('\u{32d0}', '\u{32fe}'), ('\u{3300}', '\u{3357}'), ('\u{ff66}', '\u{ff6f}'),
         ('\u{ff71}', '\u{ff9d}'), ('\u{1b000}', '\u{1b000}')
     ];
 
-    pub static Kayah_Li_table: &'static [(char, char)] = &[
+    pub const Kayah_Li_table: &'static [(char, char)] = &[
         ('\u{a900}', '\u{a909}'), ('\u{a90a}', '\u{a925}'), ('\u{a926}', '\u{a92d}'), ('\u{a92f}',
         '\u{a92f}')
     ];
 
-    pub static Kharoshthi_table: &'static [(char, char)] = &[
+    pub const Kharoshthi_table: &'static [(char, char)] = &[
         ('\u{10a00}', '\u{10a00}'), ('\u{10a01}', '\u{10a03}'), ('\u{10a05}', '\u{10a06}'),
         ('\u{10a0c}', '\u{10a0f}'), ('\u{10a10}', '\u{10a13}'), ('\u{10a15}', '\u{10a17}'),
         ('\u{10a19}', '\u{10a33}'), ('\u{10a38}', '\u{10a3a}'), ('\u{10a3f}', '\u{10a3f}'),
         ('\u{10a40}', '\u{10a47}'), ('\u{10a50}', '\u{10a58}')
     ];
 
-    pub static Khmer_table: &'static [(char, char)] = &[
+    pub const Khmer_table: &'static [(char, char)] = &[
         ('\u{1780}', '\u{17b3}'), ('\u{17b4}', '\u{17b5}'), ('\u{17b6}', '\u{17b6}'), ('\u{17b7}',
         '\u{17bd}'), ('\u{17be}', '\u{17c5}'), ('\u{17c6}', '\u{17c6}'), ('\u{17c7}', '\u{17c8}'),
         ('\u{17c9}', '\u{17d3}'), ('\u{17d4}', '\u{17d6}'), ('\u{17d7}', '\u{17d7}'), ('\u{17d8}',
@@ -3499,18 +3490,18 @@ pub mod script {
         ('\u{17e0}', '\u{17e9}'), ('\u{17f0}', '\u{17f9}'), ('\u{19e0}', '\u{19ff}')
     ];
 
-    pub static Khojki_table: &'static [(char, char)] = &[
+    pub const Khojki_table: &'static [(char, char)] = &[
         ('\u{11200}', '\u{11211}'), ('\u{11213}', '\u{1122b}'), ('\u{1122c}', '\u{1122e}'),
         ('\u{1122f}', '\u{11231}'), ('\u{11232}', '\u{11233}'), ('\u{11234}', '\u{11234}'),
         ('\u{11235}', '\u{11235}'), ('\u{11236}', '\u{11237}'), ('\u{11238}', '\u{1123d}')
     ];
 
-    pub static Khudawadi_table: &'static [(char, char)] = &[
+    pub const Khudawadi_table: &'static [(char, char)] = &[
         ('\u{112b0}', '\u{112de}'), ('\u{112df}', '\u{112df}'), ('\u{112e0}', '\u{112e2}'),
         ('\u{112e3}', '\u{112ea}'), ('\u{112f0}', '\u{112f9}')
     ];
 
-    pub static Lao_table: &'static [(char, char)] = &[
+    pub const Lao_table: &'static [(char, char)] = &[
         ('\u{e81}', '\u{e82}'), ('\u{e84}', '\u{e84}'), ('\u{e87}', '\u{e88}'), ('\u{e8a}',
         '\u{e8a}'), ('\u{e8d}', '\u{e8d}'), ('\u{e94}', '\u{e97}'), ('\u{e99}', '\u{e9f}'),
         ('\u{ea1}', '\u{ea3}'), ('\u{ea5}', '\u{ea5}'), ('\u{ea7}', '\u{ea7}'), ('\u{eaa}',
@@ -3520,7 +3511,7 @@ pub mod script {
         ('\u{edc}', '\u{edf}')
     ];
 
-    pub static Latin_table: &'static [(char, char)] = &[
+    pub const Latin_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{5a}'), ('\u{61}', '\u{7a}'), ('\u{aa}', '\u{aa}'), ('\u{ba}', '\u{ba}'),
         ('\u{c0}', '\u{d6}'), ('\u{d8}', '\u{f6}'), ('\u{f8}', '\u{1ba}'), ('\u{1bb}', '\u{1bb}'),
         ('\u{1bc}', '\u{1bf}'), ('\u{1c0}', '\u{1c3}'), ('\u{1c4}', '\u{293}'), ('\u{294}',
@@ -3537,47 +3528,47 @@ pub mod script {
         '\u{ab64}'), ('\u{fb00}', '\u{fb06}'), ('\u{ff21}', '\u{ff3a}'), ('\u{ff41}', '\u{ff5a}')
     ];
 
-    pub static Lepcha_table: &'static [(char, char)] = &[
+    pub const Lepcha_table: &'static [(char, char)] = &[
         ('\u{1c00}', '\u{1c23}'), ('\u{1c24}', '\u{1c2b}'), ('\u{1c2c}', '\u{1c33}'), ('\u{1c34}',
         '\u{1c35}'), ('\u{1c36}', '\u{1c37}'), ('\u{1c3b}', '\u{1c3f}'), ('\u{1c40}', '\u{1c49}'),
         ('\u{1c4d}', '\u{1c4f}')
     ];
 
-    pub static Limbu_table: &'static [(char, char)] = &[
+    pub const Limbu_table: &'static [(char, char)] = &[
         ('\u{1900}', '\u{191e}'), ('\u{1920}', '\u{1922}'), ('\u{1923}', '\u{1926}'), ('\u{1927}',
         '\u{1928}'), ('\u{1929}', '\u{192b}'), ('\u{1930}', '\u{1931}'), ('\u{1932}', '\u{1932}'),
         ('\u{1933}', '\u{1938}'), ('\u{1939}', '\u{193b}'), ('\u{1940}', '\u{1940}'), ('\u{1944}',
         '\u{1945}'), ('\u{1946}', '\u{194f}')
     ];
 
-    pub static Linear_A_table: &'static [(char, char)] = &[
+    pub const Linear_A_table: &'static [(char, char)] = &[
         ('\u{10600}', '\u{10736}'), ('\u{10740}', '\u{10755}'), ('\u{10760}', '\u{10767}')
     ];
 
-    pub static Linear_B_table: &'static [(char, char)] = &[
+    pub const Linear_B_table: &'static [(char, char)] = &[
         ('\u{10000}', '\u{1000b}'), ('\u{1000d}', '\u{10026}'), ('\u{10028}', '\u{1003a}'),
         ('\u{1003c}', '\u{1003d}'), ('\u{1003f}', '\u{1004d}'), ('\u{10050}', '\u{1005d}'),
         ('\u{10080}', '\u{100fa}')
     ];
 
-    pub static Lisu_table: &'static [(char, char)] = &[
+    pub const Lisu_table: &'static [(char, char)] = &[
         ('\u{a4d0}', '\u{a4f7}'), ('\u{a4f8}', '\u{a4fd}'), ('\u{a4fe}', '\u{a4ff}')
     ];
 
-    pub static Lycian_table: &'static [(char, char)] = &[
+    pub const Lycian_table: &'static [(char, char)] = &[
         ('\u{10280}', '\u{1029c}')
     ];
 
-    pub static Lydian_table: &'static [(char, char)] = &[
+    pub const Lydian_table: &'static [(char, char)] = &[
         ('\u{10920}', '\u{10939}'), ('\u{1093f}', '\u{1093f}')
     ];
 
-    pub static Mahajani_table: &'static [(char, char)] = &[
+    pub const Mahajani_table: &'static [(char, char)] = &[
         ('\u{11150}', '\u{11172}'), ('\u{11173}', '\u{11173}'), ('\u{11174}', '\u{11175}'),
         ('\u{11176}', '\u{11176}')
     ];
 
-    pub static Malayalam_table: &'static [(char, char)] = &[
+    pub const Malayalam_table: &'static [(char, char)] = &[
         ('\u{d01}', '\u{d01}'), ('\u{d02}', '\u{d03}'), ('\u{d05}', '\u{d0c}'), ('\u{d0e}',
         '\u{d10}'), ('\u{d12}', '\u{d3a}'), ('\u{d3d}', '\u{d3d}'), ('\u{d3e}', '\u{d40}'),
         ('\u{d41}', '\u{d44}'), ('\u{d46}', '\u{d48}'), ('\u{d4a}', '\u{d4c}'), ('\u{d4d}',
@@ -3586,16 +3577,16 @@ pub mod script {
         '\u{d79}'), ('\u{d7a}', '\u{d7f}')
     ];
 
-    pub static Mandaic_table: &'static [(char, char)] = &[
+    pub const Mandaic_table: &'static [(char, char)] = &[
         ('\u{840}', '\u{858}'), ('\u{859}', '\u{85b}'), ('\u{85e}', '\u{85e}')
     ];
 
-    pub static Manichaean_table: &'static [(char, char)] = &[
+    pub const Manichaean_table: &'static [(char, char)] = &[
         ('\u{10ac0}', '\u{10ac7}'), ('\u{10ac8}', '\u{10ac8}'), ('\u{10ac9}', '\u{10ae4}'),
         ('\u{10ae5}', '\u{10ae6}'), ('\u{10aeb}', '\u{10aef}'), ('\u{10af0}', '\u{10af6}')
     ];
 
-    pub static Meetei_Mayek_table: &'static [(char, char)] = &[
+    pub const Meetei_Mayek_table: &'static [(char, char)] = &[
         ('\u{aae0}', '\u{aaea}'), ('\u{aaeb}', '\u{aaeb}'), ('\u{aaec}', '\u{aaed}'), ('\u{aaee}',
         '\u{aaef}'), ('\u{aaf0}', '\u{aaf1}'), ('\u{aaf2}', '\u{aaf2}'), ('\u{aaf3}', '\u{aaf4}'),
         ('\u{aaf5}', '\u{aaf5}'), ('\u{aaf6}', '\u{aaf6}'), ('\u{abc0}', '\u{abe2}'), ('\u{abe3}',
@@ -3604,42 +3595,42 @@ pub mod script {
         '\u{abed}'), ('\u{abf0}', '\u{abf9}')
     ];
 
-    pub static Mende_Kikakui_table: &'static [(char, char)] = &[
+    pub const Mende_Kikakui_table: &'static [(char, char)] = &[
         ('\u{1e800}', '\u{1e8c4}'), ('\u{1e8c7}', '\u{1e8cf}'), ('\u{1e8d0}', '\u{1e8d6}')
     ];
 
-    pub static Meroitic_Cursive_table: &'static [(char, char)] = &[
+    pub const Meroitic_Cursive_table: &'static [(char, char)] = &[
         ('\u{109a0}', '\u{109b7}'), ('\u{109be}', '\u{109bf}')
     ];
 
-    pub static Meroitic_Hieroglyphs_table: &'static [(char, char)] = &[
+    pub const Meroitic_Hieroglyphs_table: &'static [(char, char)] = &[
         ('\u{10980}', '\u{1099f}')
     ];
 
-    pub static Miao_table: &'static [(char, char)] = &[
+    pub const Miao_table: &'static [(char, char)] = &[
         ('\u{16f00}', '\u{16f44}'), ('\u{16f50}', '\u{16f50}'), ('\u{16f51}', '\u{16f7e}'),
         ('\u{16f8f}', '\u{16f92}'), ('\u{16f93}', '\u{16f9f}')
     ];
 
-    pub static Modi_table: &'static [(char, char)] = &[
+    pub const Modi_table: &'static [(char, char)] = &[
         ('\u{11600}', '\u{1162f}'), ('\u{11630}', '\u{11632}'), ('\u{11633}', '\u{1163a}'),
         ('\u{1163b}', '\u{1163c}'), ('\u{1163d}', '\u{1163d}'), ('\u{1163e}', '\u{1163e}'),
         ('\u{1163f}', '\u{11640}'), ('\u{11641}', '\u{11643}'), ('\u{11644}', '\u{11644}'),
         ('\u{11650}', '\u{11659}')
     ];
 
-    pub static Mongolian_table: &'static [(char, char)] = &[
+    pub const Mongolian_table: &'static [(char, char)] = &[
         ('\u{1800}', '\u{1801}'), ('\u{1804}', '\u{1804}'), ('\u{1806}', '\u{1806}'), ('\u{1807}',
         '\u{180a}'), ('\u{180b}', '\u{180d}'), ('\u{180e}', '\u{180e}'), ('\u{1810}', '\u{1819}'),
         ('\u{1820}', '\u{1842}'), ('\u{1843}', '\u{1843}'), ('\u{1844}', '\u{1877}'), ('\u{1880}',
         '\u{18a8}'), ('\u{18a9}', '\u{18a9}'), ('\u{18aa}', '\u{18aa}')
     ];
 
-    pub static Mro_table: &'static [(char, char)] = &[
+    pub const Mro_table: &'static [(char, char)] = &[
         ('\u{16a40}', '\u{16a5e}'), ('\u{16a60}', '\u{16a69}'), ('\u{16a6e}', '\u{16a6f}')
     ];
 
-    pub static Myanmar_table: &'static [(char, char)] = &[
+    pub const Myanmar_table: &'static [(char, char)] = &[
         ('\u{1000}', '\u{102a}'), ('\u{102b}', '\u{102c}'), ('\u{102d}', '\u{1030}'), ('\u{1031}',
         '\u{1031}'), ('\u{1032}', '\u{1037}'), ('\u{1038}', '\u{1038}'), ('\u{1039}', '\u{103a}'),
         ('\u{103b}', '\u{103c}'), ('\u{103d}', '\u{103e}'), ('\u{103f}', '\u{103f}'), ('\u{1040}',
@@ -3657,56 +3648,56 @@ pub mod script {
         ('\u{aa7e}', '\u{aa7f}')
     ];
 
-    pub static Nabataean_table: &'static [(char, char)] = &[
+    pub const Nabataean_table: &'static [(char, char)] = &[
         ('\u{10880}', '\u{1089e}'), ('\u{108a7}', '\u{108af}')
     ];
 
-    pub static New_Tai_Lue_table: &'static [(char, char)] = &[
+    pub const New_Tai_Lue_table: &'static [(char, char)] = &[
         ('\u{1980}', '\u{19ab}'), ('\u{19b0}', '\u{19c0}'), ('\u{19c1}', '\u{19c7}'), ('\u{19c8}',
         '\u{19c9}'), ('\u{19d0}', '\u{19d9}'), ('\u{19da}', '\u{19da}'), ('\u{19de}', '\u{19df}')
     ];
 
-    pub static Nko_table: &'static [(char, char)] = &[
+    pub const Nko_table: &'static [(char, char)] = &[
         ('\u{7c0}', '\u{7c9}'), ('\u{7ca}', '\u{7ea}'), ('\u{7eb}', '\u{7f3}'), ('\u{7f4}',
         '\u{7f5}'), ('\u{7f6}', '\u{7f6}'), ('\u{7f7}', '\u{7f9}'), ('\u{7fa}', '\u{7fa}')
     ];
 
-    pub static Ogham_table: &'static [(char, char)] = &[
+    pub const Ogham_table: &'static [(char, char)] = &[
         ('\u{1680}', '\u{1680}'), ('\u{1681}', '\u{169a}'), ('\u{169b}', '\u{169b}'), ('\u{169c}',
         '\u{169c}')
     ];
 
-    pub static Ol_Chiki_table: &'static [(char, char)] = &[
+    pub const Ol_Chiki_table: &'static [(char, char)] = &[
         ('\u{1c50}', '\u{1c59}'), ('\u{1c5a}', '\u{1c77}'), ('\u{1c78}', '\u{1c7d}'), ('\u{1c7e}',
         '\u{1c7f}')
     ];
 
-    pub static Old_Italic_table: &'static [(char, char)] = &[
+    pub const Old_Italic_table: &'static [(char, char)] = &[
         ('\u{10300}', '\u{1031f}'), ('\u{10320}', '\u{10323}')
     ];
 
-    pub static Old_North_Arabian_table: &'static [(char, char)] = &[
+    pub const Old_North_Arabian_table: &'static [(char, char)] = &[
         ('\u{10a80}', '\u{10a9c}'), ('\u{10a9d}', '\u{10a9f}')
     ];
 
-    pub static Old_Permic_table: &'static [(char, char)] = &[
+    pub const Old_Permic_table: &'static [(char, char)] = &[
         ('\u{10350}', '\u{10375}'), ('\u{10376}', '\u{1037a}')
     ];
 
-    pub static Old_Persian_table: &'static [(char, char)] = &[
+    pub const Old_Persian_table: &'static [(char, char)] = &[
         ('\u{103a0}', '\u{103c3}'), ('\u{103c8}', '\u{103cf}'), ('\u{103d0}', '\u{103d0}'),
         ('\u{103d1}', '\u{103d5}')
     ];
 
-    pub static Old_South_Arabian_table: &'static [(char, char)] = &[
+    pub const Old_South_Arabian_table: &'static [(char, char)] = &[
         ('\u{10a60}', '\u{10a7c}'), ('\u{10a7d}', '\u{10a7e}'), ('\u{10a7f}', '\u{10a7f}')
     ];
 
-    pub static Old_Turkic_table: &'static [(char, char)] = &[
+    pub const Old_Turkic_table: &'static [(char, char)] = &[
         ('\u{10c00}', '\u{10c48}')
     ];
 
-    pub static Oriya_table: &'static [(char, char)] = &[
+    pub const Oriya_table: &'static [(char, char)] = &[
         ('\u{b01}', '\u{b01}'), ('\u{b02}', '\u{b03}'), ('\u{b05}', '\u{b0c}'), ('\u{b0f}',
         '\u{b10}'), ('\u{b13}', '\u{b28}'), ('\u{b2a}', '\u{b30}'), ('\u{b32}', '\u{b33}'),
         ('\u{b35}', '\u{b39}'), ('\u{b3c}', '\u{b3c}'), ('\u{b3d}', '\u{b3d}'), ('\u{b3e}',
@@ -3717,75 +3708,75 @@ pub mod script {
         '\u{b71}'), ('\u{b72}', '\u{b77}')
     ];
 
-    pub static Osmanya_table: &'static [(char, char)] = &[
+    pub const Osmanya_table: &'static [(char, char)] = &[
         ('\u{10480}', '\u{1049d}'), ('\u{104a0}', '\u{104a9}')
     ];
 
-    pub static Pahawh_Hmong_table: &'static [(char, char)] = &[
+    pub const Pahawh_Hmong_table: &'static [(char, char)] = &[
         ('\u{16b00}', '\u{16b2f}'), ('\u{16b30}', '\u{16b36}'), ('\u{16b37}', '\u{16b3b}'),
         ('\u{16b3c}', '\u{16b3f}'), ('\u{16b40}', '\u{16b43}'), ('\u{16b44}', '\u{16b44}'),
         ('\u{16b45}', '\u{16b45}'), ('\u{16b50}', '\u{16b59}'), ('\u{16b5b}', '\u{16b61}'),
         ('\u{16b63}', '\u{16b77}'), ('\u{16b7d}', '\u{16b8f}')
     ];
 
-    pub static Palmyrene_table: &'static [(char, char)] = &[
+    pub const Palmyrene_table: &'static [(char, char)] = &[
         ('\u{10860}', '\u{10876}'), ('\u{10877}', '\u{10878}'), ('\u{10879}', '\u{1087f}')
     ];
 
-    pub static Pau_Cin_Hau_table: &'static [(char, char)] = &[
+    pub const Pau_Cin_Hau_table: &'static [(char, char)] = &[
         ('\u{11ac0}', '\u{11af8}')
     ];
 
-    pub static Phags_Pa_table: &'static [(char, char)] = &[
+    pub const Phags_Pa_table: &'static [(char, char)] = &[
         ('\u{a840}', '\u{a873}'), ('\u{a874}', '\u{a877}')
     ];
 
-    pub static Phoenician_table: &'static [(char, char)] = &[
+    pub const Phoenician_table: &'static [(char, char)] = &[
         ('\u{10900}', '\u{10915}'), ('\u{10916}', '\u{1091b}'), ('\u{1091f}', '\u{1091f}')
     ];
 
-    pub static Psalter_Pahlavi_table: &'static [(char, char)] = &[
+    pub const Psalter_Pahlavi_table: &'static [(char, char)] = &[
         ('\u{10b80}', '\u{10b91}'), ('\u{10b99}', '\u{10b9c}'), ('\u{10ba9}', '\u{10baf}')
     ];
 
-    pub static Rejang_table: &'static [(char, char)] = &[
+    pub const Rejang_table: &'static [(char, char)] = &[
         ('\u{a930}', '\u{a946}'), ('\u{a947}', '\u{a951}'), ('\u{a952}', '\u{a953}'), ('\u{a95f}',
         '\u{a95f}')
     ];
 
-    pub static Runic_table: &'static [(char, char)] = &[
+    pub const Runic_table: &'static [(char, char)] = &[
         ('\u{16a0}', '\u{16ea}'), ('\u{16ee}', '\u{16f0}'), ('\u{16f1}', '\u{16f8}')
     ];
 
-    pub static Samaritan_table: &'static [(char, char)] = &[
+    pub const Samaritan_table: &'static [(char, char)] = &[
         ('\u{800}', '\u{815}'), ('\u{816}', '\u{819}'), ('\u{81a}', '\u{81a}'), ('\u{81b}',
         '\u{823}'), ('\u{824}', '\u{824}'), ('\u{825}', '\u{827}'), ('\u{828}', '\u{828}'),
         ('\u{829}', '\u{82d}'), ('\u{830}', '\u{83e}')
     ];
 
-    pub static Saurashtra_table: &'static [(char, char)] = &[
+    pub const Saurashtra_table: &'static [(char, char)] = &[
         ('\u{a880}', '\u{a881}'), ('\u{a882}', '\u{a8b3}'), ('\u{a8b4}', '\u{a8c3}'), ('\u{a8c4}',
         '\u{a8c4}'), ('\u{a8ce}', '\u{a8cf}'), ('\u{a8d0}', '\u{a8d9}')
     ];
 
-    pub static Sharada_table: &'static [(char, char)] = &[
+    pub const Sharada_table: &'static [(char, char)] = &[
         ('\u{11180}', '\u{11181}'), ('\u{11182}', '\u{11182}'), ('\u{11183}', '\u{111b2}'),
         ('\u{111b3}', '\u{111b5}'), ('\u{111b6}', '\u{111be}'), ('\u{111bf}', '\u{111c0}'),
         ('\u{111c1}', '\u{111c4}'), ('\u{111c5}', '\u{111c8}'), ('\u{111cd}', '\u{111cd}'),
         ('\u{111d0}', '\u{111d9}'), ('\u{111da}', '\u{111da}')
     ];
 
-    pub static Shavian_table: &'static [(char, char)] = &[
+    pub const Shavian_table: &'static [(char, char)] = &[
         ('\u{10450}', '\u{1047f}')
     ];
 
-    pub static Siddham_table: &'static [(char, char)] = &[
+    pub const Siddham_table: &'static [(char, char)] = &[
         ('\u{11580}', '\u{115ae}'), ('\u{115af}', '\u{115b1}'), ('\u{115b2}', '\u{115b5}'),
         ('\u{115b8}', '\u{115bb}'), ('\u{115bc}', '\u{115bd}'), ('\u{115be}', '\u{115be}'),
         ('\u{115bf}', '\u{115c0}'), ('\u{115c1}', '\u{115c9}')
     ];
 
-    pub static Sinhala_table: &'static [(char, char)] = &[
+    pub const Sinhala_table: &'static [(char, char)] = &[
         ('\u{d82}', '\u{d83}'), ('\u{d85}', '\u{d96}'), ('\u{d9a}', '\u{db1}'), ('\u{db3}',
         '\u{dbb}'), ('\u{dbd}', '\u{dbd}'), ('\u{dc0}', '\u{dc6}'), ('\u{dca}', '\u{dca}'),
         ('\u{dcf}', '\u{dd1}'), ('\u{dd2}', '\u{dd4}'), ('\u{dd6}', '\u{dd6}'), ('\u{dd8}',
@@ -3793,42 +3784,42 @@ pub mod script {
         ('\u{111e1}', '\u{111f4}')
     ];
 
-    pub static Sora_Sompeng_table: &'static [(char, char)] = &[
+    pub const Sora_Sompeng_table: &'static [(char, char)] = &[
         ('\u{110d0}', '\u{110e8}'), ('\u{110f0}', '\u{110f9}')
     ];
 
-    pub static Sundanese_table: &'static [(char, char)] = &[
+    pub const Sundanese_table: &'static [(char, char)] = &[
         ('\u{1b80}', '\u{1b81}'), ('\u{1b82}', '\u{1b82}'), ('\u{1b83}', '\u{1ba0}'), ('\u{1ba1}',
         '\u{1ba1}'), ('\u{1ba2}', '\u{1ba5}'), ('\u{1ba6}', '\u{1ba7}'), ('\u{1ba8}', '\u{1ba9}'),
         ('\u{1baa}', '\u{1baa}'), ('\u{1bab}', '\u{1bad}'), ('\u{1bae}', '\u{1baf}'), ('\u{1bb0}',
         '\u{1bb9}'), ('\u{1bba}', '\u{1bbf}'), ('\u{1cc0}', '\u{1cc7}')
     ];
 
-    pub static Syloti_Nagri_table: &'static [(char, char)] = &[
+    pub const Syloti_Nagri_table: &'static [(char, char)] = &[
         ('\u{a800}', '\u{a801}'), ('\u{a802}', '\u{a802}'), ('\u{a803}', '\u{a805}'), ('\u{a806}',
         '\u{a806}'), ('\u{a807}', '\u{a80a}'), ('\u{a80b}', '\u{a80b}'), ('\u{a80c}', '\u{a822}'),
         ('\u{a823}', '\u{a824}'), ('\u{a825}', '\u{a826}'), ('\u{a827}', '\u{a827}'), ('\u{a828}',
         '\u{a82b}')
     ];
 
-    pub static Syriac_table: &'static [(char, char)] = &[
+    pub const Syriac_table: &'static [(char, char)] = &[
         ('\u{700}', '\u{70d}'), ('\u{70f}', '\u{70f}'), ('\u{710}', '\u{710}'), ('\u{711}',
         '\u{711}'), ('\u{712}', '\u{72f}'), ('\u{730}', '\u{74a}'), ('\u{74d}', '\u{74f}')
     ];
 
-    pub static Tagalog_table: &'static [(char, char)] = &[
+    pub const Tagalog_table: &'static [(char, char)] = &[
         ('\u{1700}', '\u{170c}'), ('\u{170e}', '\u{1711}'), ('\u{1712}', '\u{1714}')
     ];
 
-    pub static Tagbanwa_table: &'static [(char, char)] = &[
+    pub const Tagbanwa_table: &'static [(char, char)] = &[
         ('\u{1760}', '\u{176c}'), ('\u{176e}', '\u{1770}'), ('\u{1772}', '\u{1773}')
     ];
 
-    pub static Tai_Le_table: &'static [(char, char)] = &[
+    pub const Tai_Le_table: &'static [(char, char)] = &[
         ('\u{1950}', '\u{196d}'), ('\u{1970}', '\u{1974}')
     ];
 
-    pub static Tai_Tham_table: &'static [(char, char)] = &[
+    pub const Tai_Tham_table: &'static [(char, char)] = &[
         ('\u{1a20}', '\u{1a54}'), ('\u{1a55}', '\u{1a55}'), ('\u{1a56}', '\u{1a56}'), ('\u{1a57}',
         '\u{1a57}'), ('\u{1a58}', '\u{1a5e}'), ('\u{1a60}', '\u{1a60}'), ('\u{1a61}', '\u{1a61}'),
         ('\u{1a62}', '\u{1a62}'), ('\u{1a63}', '\u{1a64}'), ('\u{1a65}', '\u{1a6c}'), ('\u{1a6d}',
@@ -3837,20 +3828,20 @@ pub mod script {
         '\u{1aad}')
     ];
 
-    pub static Tai_Viet_table: &'static [(char, char)] = &[
+    pub const Tai_Viet_table: &'static [(char, char)] = &[
         ('\u{aa80}', '\u{aaaf}'), ('\u{aab0}', '\u{aab0}'), ('\u{aab1}', '\u{aab1}'), ('\u{aab2}',
         '\u{aab4}'), ('\u{aab5}', '\u{aab6}'), ('\u{aab7}', '\u{aab8}'), ('\u{aab9}', '\u{aabd}'),
         ('\u{aabe}', '\u{aabf}'), ('\u{aac0}', '\u{aac0}'), ('\u{aac1}', '\u{aac1}'), ('\u{aac2}',
         '\u{aac2}'), ('\u{aadb}', '\u{aadc}'), ('\u{aadd}', '\u{aadd}'), ('\u{aade}', '\u{aadf}')
     ];
 
-    pub static Takri_table: &'static [(char, char)] = &[
+    pub const Takri_table: &'static [(char, char)] = &[
         ('\u{11680}', '\u{116aa}'), ('\u{116ab}', '\u{116ab}'), ('\u{116ac}', '\u{116ac}'),
         ('\u{116ad}', '\u{116ad}'), ('\u{116ae}', '\u{116af}'), ('\u{116b0}', '\u{116b5}'),
         ('\u{116b6}', '\u{116b6}'), ('\u{116b7}', '\u{116b7}'), ('\u{116c0}', '\u{116c9}')
     ];
 
-    pub static Tamil_table: &'static [(char, char)] = &[
+    pub const Tamil_table: &'static [(char, char)] = &[
         ('\u{b82}', '\u{b82}'), ('\u{b83}', '\u{b83}'), ('\u{b85}', '\u{b8a}'), ('\u{b8e}',
         '\u{b90}'), ('\u{b92}', '\u{b95}'), ('\u{b99}', '\u{b9a}'), ('\u{b9c}', '\u{b9c}'),
         ('\u{b9e}', '\u{b9f}'), ('\u{ba3}', '\u{ba4}'), ('\u{ba8}', '\u{baa}'), ('\u{bae}',
@@ -3860,7 +3851,7 @@ pub mod script {
         ('\u{bf3}', '\u{bf8}'), ('\u{bf9}', '\u{bf9}'), ('\u{bfa}', '\u{bfa}')
     ];
 
-    pub static Telugu_table: &'static [(char, char)] = &[
+    pub const Telugu_table: &'static [(char, char)] = &[
         ('\u{c00}', '\u{c00}'), ('\u{c01}', '\u{c03}'), ('\u{c05}', '\u{c0c}'), ('\u{c0e}',
         '\u{c10}'), ('\u{c12}', '\u{c28}'), ('\u{c2a}', '\u{c39}'), ('\u{c3d}', '\u{c3d}'),
         ('\u{c3e}', '\u{c40}'), ('\u{c41}', '\u{c44}'), ('\u{c46}', '\u{c48}'), ('\u{c4a}',
@@ -3869,17 +3860,17 @@ pub mod script {
         '\u{c7f}')
     ];
 
-    pub static Thaana_table: &'static [(char, char)] = &[
+    pub const Thaana_table: &'static [(char, char)] = &[
         ('\u{780}', '\u{7a5}'), ('\u{7a6}', '\u{7b0}'), ('\u{7b1}', '\u{7b1}')
     ];
 
-    pub static Thai_table: &'static [(char, char)] = &[
+    pub const Thai_table: &'static [(char, char)] = &[
         ('\u{e01}', '\u{e30}'), ('\u{e31}', '\u{e31}'), ('\u{e32}', '\u{e33}'), ('\u{e34}',
         '\u{e3a}'), ('\u{e40}', '\u{e45}'), ('\u{e46}', '\u{e46}'), ('\u{e47}', '\u{e4e}'),
         ('\u{e4f}', '\u{e4f}'), ('\u{e50}', '\u{e59}'), ('\u{e5a}', '\u{e5b}')
     ];
 
-    pub static Tibetan_table: &'static [(char, char)] = &[
+    pub const Tibetan_table: &'static [(char, char)] = &[
         ('\u{f00}', '\u{f00}'), ('\u{f01}', '\u{f03}'), ('\u{f04}', '\u{f12}'), ('\u{f13}',
         '\u{f13}'), ('\u{f14}', '\u{f14}'), ('\u{f15}', '\u{f17}'), ('\u{f18}', '\u{f19}'),
         ('\u{f1a}', '\u{f1f}'), ('\u{f20}', '\u{f29}'), ('\u{f2a}', '\u{f33}'), ('\u{f34}',
@@ -3893,12 +3884,12 @@ pub mod script {
         ('\u{fd0}', '\u{fd4}'), ('\u{fd9}', '\u{fda}')
     ];
 
-    pub static Tifinagh_table: &'static [(char, char)] = &[
+    pub const Tifinagh_table: &'static [(char, char)] = &[
         ('\u{2d30}', '\u{2d67}'), ('\u{2d6f}', '\u{2d6f}'), ('\u{2d70}', '\u{2d70}'), ('\u{2d7f}',
         '\u{2d7f}')
     ];
 
-    pub static Tirhuta_table: &'static [(char, char)] = &[
+    pub const Tirhuta_table: &'static [(char, char)] = &[
         ('\u{11480}', '\u{114af}'), ('\u{114b0}', '\u{114b2}'), ('\u{114b3}', '\u{114b8}'),
         ('\u{114b9}', '\u{114b9}'), ('\u{114ba}', '\u{114ba}'), ('\u{114bb}', '\u{114be}'),
         ('\u{114bf}', '\u{114c0}'), ('\u{114c1}', '\u{114c1}'), ('\u{114c2}', '\u{114c3}'),
@@ -3906,21 +3897,21 @@ pub mod script {
         ('\u{114d0}', '\u{114d9}')
     ];
 
-    pub static Ugaritic_table: &'static [(char, char)] = &[
+    pub const Ugaritic_table: &'static [(char, char)] = &[
         ('\u{10380}', '\u{1039d}'), ('\u{1039f}', '\u{1039f}')
     ];
 
-    pub static Vai_table: &'static [(char, char)] = &[
+    pub const Vai_table: &'static [(char, char)] = &[
         ('\u{a500}', '\u{a60b}'), ('\u{a60c}', '\u{a60c}'), ('\u{a60d}', '\u{a60f}'), ('\u{a610}',
         '\u{a61f}'), ('\u{a620}', '\u{a629}'), ('\u{a62a}', '\u{a62b}')
     ];
 
-    pub static Warang_Citi_table: &'static [(char, char)] = &[
+    pub const Warang_Citi_table: &'static [(char, char)] = &[
         ('\u{118a0}', '\u{118df}'), ('\u{118e0}', '\u{118e9}'), ('\u{118ea}', '\u{118f2}'),
         ('\u{118ff}', '\u{118ff}')
     ];
 
-    pub static Yi_table: &'static [(char, char)] = &[
+    pub const Yi_table: &'static [(char, char)] = &[
         ('\u{a000}', '\u{a014}'), ('\u{a015}', '\u{a015}'), ('\u{a016}', '\u{a48c}'), ('\u{a490}',
         '\u{a4c6}')
     ];
@@ -3928,11 +3919,11 @@ pub mod script {
 }
 
 pub mod property {
-    pub static Join_Control_table: &'static [(char, char)] = &[
+    pub const Join_Control_table: &'static [(char, char)] = &[
         ('\u{200c}', '\u{200d}')
     ];
 
-    pub static Noncharacter_Code_Point_table: &'static [(char, char)] = &[
+    pub const Noncharacter_Code_Point_table: &'static [(char, char)] = &[
         ('\u{fdd0}', '\u{fdef}'), ('\u{fffe}', '\u{ffff}'), ('\u{1fffe}', '\u{1ffff}'),
         ('\u{2fffe}', '\u{2ffff}'), ('\u{3fffe}', '\u{3ffff}'), ('\u{4fffe}', '\u{4ffff}'),
         ('\u{5fffe}', '\u{5ffff}'), ('\u{6fffe}', '\u{6ffff}'), ('\u{7fffe}', '\u{7ffff}'),
@@ -3941,7 +3932,7 @@ pub mod property {
         ('\u{efffe}', '\u{effff}'), ('\u{ffffe}', '\u{fffff}')
     ];
 
-    pub static White_Space_table: &'static [(char, char)] = &[
+    pub const White_Space_table: &'static [(char, char)] = &[
         ('\u{9}', '\u{d}'), ('\u{20}', '\u{20}'), ('\u{85}', '\u{85}'), ('\u{a0}', '\u{a0}'),
         ('\u{1680}', '\u{1680}'), ('\u{2000}', '\u{200a}'), ('\u{2028}', '\u{2028}'), ('\u{2029}',
         '\u{2029}'), ('\u{202f}', '\u{202f}'), ('\u{205f}', '\u{205f}'), ('\u{3000}', '\u{3000}')
@@ -3954,111 +3945,110 @@ pub fn White_Space(c: char) -> bool {
 }
 
 pub mod regex {
-    pub static UNICODE_CLASSES: &'static [(&'static str, &'static &'static [(char, char)])] = &[
-        ("Alphabetic", &super::derived_property::Alphabetic_table), ("Arabic",
-        &super::script::Arabic_table), ("Armenian", &super::script::Armenian_table), ("Avestan",
-        &super::script::Avestan_table), ("Balinese", &super::script::Balinese_table), ("Bamum",
-        &super::script::Bamum_table), ("Bassa_Vah", &super::script::Bassa_Vah_table), ("Batak",
-        &super::script::Batak_table), ("Bengali", &super::script::Bengali_table), ("Bopomofo",
-        &super::script::Bopomofo_table), ("Brahmi", &super::script::Brahmi_table), ("Braille",
-        &super::script::Braille_table), ("Buginese", &super::script::Buginese_table), ("Buhid",
-        &super::script::Buhid_table), ("C", &super::general_category::C_table),
-        ("Canadian_Aboriginal", &super::script::Canadian_Aboriginal_table), ("Carian",
-        &super::script::Carian_table), ("Caucasian_Albanian",
-        &super::script::Caucasian_Albanian_table), ("Cc", &super::general_category::Cc_table),
-        ("Cf", &super::general_category::Cf_table), ("Chakma", &super::script::Chakma_table),
-        ("Cham", &super::script::Cham_table), ("Cherokee", &super::script::Cherokee_table), ("Cn",
-        &super::general_category::Cn_table), ("Co", &super::general_category::Co_table), ("Common",
-        &super::script::Common_table), ("Coptic", &super::script::Coptic_table), ("Cuneiform",
-        &super::script::Cuneiform_table), ("Cypriot", &super::script::Cypriot_table), ("Cyrillic",
-        &super::script::Cyrillic_table), ("Default_Ignorable_Code_Point",
-        &super::derived_property::Default_Ignorable_Code_Point_table), ("Deseret",
-        &super::script::Deseret_table), ("Devanagari", &super::script::Devanagari_table),
-        ("Duployan", &super::script::Duployan_table), ("Egyptian_Hieroglyphs",
-        &super::script::Egyptian_Hieroglyphs_table), ("Elbasan", &super::script::Elbasan_table),
-        ("Ethiopic", &super::script::Ethiopic_table), ("Georgian", &super::script::Georgian_table),
-        ("Glagolitic", &super::script::Glagolitic_table), ("Gothic", &super::script::Gothic_table),
-        ("Grantha", &super::script::Grantha_table), ("Greek", &super::script::Greek_table),
-        ("Gujarati", &super::script::Gujarati_table), ("Gurmukhi", &super::script::Gurmukhi_table),
-        ("Han", &super::script::Han_table), ("Hangul", &super::script::Hangul_table), ("Hanunoo",
-        &super::script::Hanunoo_table), ("Hebrew", &super::script::Hebrew_table), ("Hiragana",
-        &super::script::Hiragana_table), ("Imperial_Aramaic",
-        &super::script::Imperial_Aramaic_table), ("Inherited", &super::script::Inherited_table),
-        ("Inscriptional_Pahlavi", &super::script::Inscriptional_Pahlavi_table),
-        ("Inscriptional_Parthian", &super::script::Inscriptional_Parthian_table), ("Javanese",
-        &super::script::Javanese_table), ("Join_Control", &super::property::Join_Control_table),
-        ("Kaithi", &super::script::Kaithi_table), ("Kannada", &super::script::Kannada_table),
-        ("Katakana", &super::script::Katakana_table), ("Kayah_Li", &super::script::Kayah_Li_table),
-        ("Kharoshthi", &super::script::Kharoshthi_table), ("Khmer", &super::script::Khmer_table),
-        ("Khojki", &super::script::Khojki_table), ("Khudawadi", &super::script::Khudawadi_table),
-        ("L", &super::general_category::L_table), ("LC", &super::general_category::LC_table),
-        ("Lao", &super::script::Lao_table), ("Latin", &super::script::Latin_table), ("Lepcha",
-        &super::script::Lepcha_table), ("Limbu", &super::script::Limbu_table), ("Linear_A",
-        &super::script::Linear_A_table), ("Linear_B", &super::script::Linear_B_table), ("Lisu",
-        &super::script::Lisu_table), ("Ll", &super::general_category::Ll_table), ("Lm",
-        &super::general_category::Lm_table), ("Lo", &super::general_category::Lo_table),
-        ("Lowercase", &super::derived_property::Lowercase_table), ("Lt",
-        &super::general_category::Lt_table), ("Lu", &super::general_category::Lu_table), ("Lycian",
-        &super::script::Lycian_table), ("Lydian", &super::script::Lydian_table), ("M",
-        &super::general_category::M_table), ("Mahajani", &super::script::Mahajani_table),
-        ("Malayalam", &super::script::Malayalam_table), ("Mandaic", &super::script::Mandaic_table),
-        ("Manichaean", &super::script::Manichaean_table), ("Mc",
-        &super::general_category::Mc_table), ("Me", &super::general_category::Me_table),
-        ("Meetei_Mayek", &super::script::Meetei_Mayek_table), ("Mende_Kikakui",
-        &super::script::Mende_Kikakui_table), ("Meroitic_Cursive",
-        &super::script::Meroitic_Cursive_table), ("Meroitic_Hieroglyphs",
-        &super::script::Meroitic_Hieroglyphs_table), ("Miao", &super::script::Miao_table), ("Mn",
-        &super::general_category::Mn_table), ("Modi", &super::script::Modi_table), ("Mongolian",
-        &super::script::Mongolian_table), ("Mro", &super::script::Mro_table), ("Myanmar",
-        &super::script::Myanmar_table), ("N", &super::general_category::N_table), ("Nabataean",
-        &super::script::Nabataean_table), ("Nd", &super::general_category::Nd_table),
-        ("New_Tai_Lue", &super::script::New_Tai_Lue_table), ("Nko", &super::script::Nko_table),
-        ("Nl", &super::general_category::Nl_table), ("No", &super::general_category::No_table),
-        ("Noncharacter_Code_Point", &super::property::Noncharacter_Code_Point_table), ("Ogham",
-        &super::script::Ogham_table), ("Ol_Chiki", &super::script::Ol_Chiki_table), ("Old_Italic",
-        &super::script::Old_Italic_table), ("Old_North_Arabian",
-        &super::script::Old_North_Arabian_table), ("Old_Permic", &super::script::Old_Permic_table),
-        ("Old_Persian", &super::script::Old_Persian_table), ("Old_South_Arabian",
-        &super::script::Old_South_Arabian_table), ("Old_Turkic", &super::script::Old_Turkic_table),
-        ("Oriya", &super::script::Oriya_table), ("Osmanya", &super::script::Osmanya_table), ("P",
-        &super::general_category::P_table), ("Pahawh_Hmong", &super::script::Pahawh_Hmong_table),
-        ("Palmyrene", &super::script::Palmyrene_table), ("Pau_Cin_Hau",
-        &super::script::Pau_Cin_Hau_table), ("Pc", &super::general_category::Pc_table), ("Pd",
-        &super::general_category::Pd_table), ("Pe", &super::general_category::Pe_table), ("Pf",
-        &super::general_category::Pf_table), ("Phags_Pa", &super::script::Phags_Pa_table),
-        ("Phoenician", &super::script::Phoenician_table), ("Pi",
-        &super::general_category::Pi_table), ("Po", &super::general_category::Po_table), ("Ps",
-        &super::general_category::Ps_table), ("Psalter_Pahlavi",
-        &super::script::Psalter_Pahlavi_table), ("Rejang", &super::script::Rejang_table), ("Runic",
-        &super::script::Runic_table), ("S", &super::general_category::S_table), ("Samaritan",
-        &super::script::Samaritan_table), ("Saurashtra", &super::script::Saurashtra_table), ("Sc",
-        &super::general_category::Sc_table), ("Sharada", &super::script::Sharada_table), ("Shavian",
-        &super::script::Shavian_table), ("Siddham", &super::script::Siddham_table), ("Sinhala",
-        &super::script::Sinhala_table), ("Sk", &super::general_category::Sk_table), ("Sm",
-        &super::general_category::Sm_table), ("So", &super::general_category::So_table),
-        ("Sora_Sompeng", &super::script::Sora_Sompeng_table), ("Sundanese",
-        &super::script::Sundanese_table), ("Syloti_Nagri", &super::script::Syloti_Nagri_table),
-        ("Syriac", &super::script::Syriac_table), ("Tagalog", &super::script::Tagalog_table),
-        ("Tagbanwa", &super::script::Tagbanwa_table), ("Tai_Le", &super::script::Tai_Le_table),
-        ("Tai_Tham", &super::script::Tai_Tham_table), ("Tai_Viet", &super::script::Tai_Viet_table),
-        ("Takri", &super::script::Takri_table), ("Tamil", &super::script::Tamil_table), ("Telugu",
-        &super::script::Telugu_table), ("Thaana", &super::script::Thaana_table), ("Thai",
-        &super::script::Thai_table), ("Tibetan", &super::script::Tibetan_table), ("Tifinagh",
-        &super::script::Tifinagh_table), ("Tirhuta", &super::script::Tirhuta_table), ("Ugaritic",
-        &super::script::Ugaritic_table), ("Uppercase", &super::derived_property::Uppercase_table),
-        ("Vai", &super::script::Vai_table), ("Warang_Citi", &super::script::Warang_Citi_table),
-        ("White_Space", &super::property::White_Space_table), ("XID_Continue",
-        &super::derived_property::XID_Continue_table), ("XID_Start",
-        &super::derived_property::XID_Start_table), ("Yi", &super::script::Yi_table), ("Z",
-        &super::general_category::Z_table), ("Zl", &super::general_category::Zl_table), ("Zp",
-        &super::general_category::Zp_table), ("Zs", &super::general_category::Zs_table)
-    ];
-
-    pub static PERLD: &'static &'static [(char, char)] = &super::general_category::Nd_table;
-
-    pub static PERLS: &'static &'static [(char, char)] = &super::property::White_Space_table;
-
-    pub static PERLW: &'static [(char, char)] = &[
+    pub const UNICODE_CLASSES: &'static [(&'static str, &'static [(char, char)])] = &[
+        ("Alphabetic", super::derived_property::Alphabetic_table), ("Arabic",
+        super::script::Arabic_table), ("Armenian", super::script::Armenian_table), ("Avestan",
+        super::script::Avestan_table), ("Balinese", super::script::Balinese_table), ("Bamum",
+        super::script::Bamum_table), ("Bassa_Vah", super::script::Bassa_Vah_table), ("Batak",
+        super::script::Batak_table), ("Bengali", super::script::Bengali_table), ("Bopomofo",
+        super::script::Bopomofo_table), ("Brahmi", super::script::Brahmi_table), ("Braille",
+        super::script::Braille_table), ("Buginese", super::script::Buginese_table), ("Buhid",
+        super::script::Buhid_table), ("C", super::general_category::C_table),
+        ("Canadian_Aboriginal", super::script::Canadian_Aboriginal_table), ("Carian",
+        super::script::Carian_table), ("Caucasian_Albanian",
+        super::script::Caucasian_Albanian_table), ("Cc", super::general_category::Cc_table), ("Cf",
+        super::general_category::Cf_table), ("Chakma", super::script::Chakma_table), ("Cham",
+        super::script::Cham_table), ("Cherokee", super::script::Cherokee_table), ("Cn",
+        super::general_category::Cn_table), ("Co", super::general_category::Co_table), ("Common",
+        super::script::Common_table), ("Coptic", super::script::Coptic_table), ("Cuneiform",
+        super::script::Cuneiform_table), ("Cypriot", super::script::Cypriot_table), ("Cyrillic",
+        super::script::Cyrillic_table), ("Default_Ignorable_Code_Point",
+        super::derived_property::Default_Ignorable_Code_Point_table), ("Deseret",
+        super::script::Deseret_table), ("Devanagari", super::script::Devanagari_table), ("Duployan",
+        super::script::Duployan_table), ("Egyptian_Hieroglyphs",
+        super::script::Egyptian_Hieroglyphs_table), ("Elbasan", super::script::Elbasan_table),
+        ("Ethiopic", super::script::Ethiopic_table), ("Georgian", super::script::Georgian_table),
+        ("Glagolitic", super::script::Glagolitic_table), ("Gothic", super::script::Gothic_table),
+        ("Grantha", super::script::Grantha_table), ("Greek", super::script::Greek_table),
+        ("Gujarati", super::script::Gujarati_table), ("Gurmukhi", super::script::Gurmukhi_table),
+        ("Han", super::script::Han_table), ("Hangul", super::script::Hangul_table), ("Hanunoo",
+        super::script::Hanunoo_table), ("Hebrew", super::script::Hebrew_table), ("Hiragana",
+        super::script::Hiragana_table), ("Imperial_Aramaic", super::script::Imperial_Aramaic_table),
+        ("Inherited", super::script::Inherited_table), ("Inscriptional_Pahlavi",
+        super::script::Inscriptional_Pahlavi_table), ("Inscriptional_Parthian",
+        super::script::Inscriptional_Parthian_table), ("Javanese", super::script::Javanese_table),
+        ("Join_Control", super::property::Join_Control_table), ("Kaithi",
+        super::script::Kaithi_table), ("Kannada", super::script::Kannada_table), ("Katakana",
+        super::script::Katakana_table), ("Kayah_Li", super::script::Kayah_Li_table), ("Kharoshthi",
+        super::script::Kharoshthi_table), ("Khmer", super::script::Khmer_table), ("Khojki",
+        super::script::Khojki_table), ("Khudawadi", super::script::Khudawadi_table), ("L",
+        super::general_category::L_table), ("LC", super::general_category::LC_table), ("Lao",
+        super::script::Lao_table), ("Latin", super::script::Latin_table), ("Lepcha",
+        super::script::Lepcha_table), ("Limbu", super::script::Limbu_table), ("Linear_A",
+        super::script::Linear_A_table), ("Linear_B", super::script::Linear_B_table), ("Lisu",
+        super::script::Lisu_table), ("Ll", super::general_category::Ll_table), ("Lm",
+        super::general_category::Lm_table), ("Lo", super::general_category::Lo_table), ("Lowercase",
+        super::derived_property::Lowercase_table), ("Lt", super::general_category::Lt_table), ("Lu",
+        super::general_category::Lu_table), ("Lycian", super::script::Lycian_table), ("Lydian",
+        super::script::Lydian_table), ("M", super::general_category::M_table), ("Mahajani",
+        super::script::Mahajani_table), ("Malayalam", super::script::Malayalam_table), ("Mandaic",
+        super::script::Mandaic_table), ("Manichaean", super::script::Manichaean_table), ("Mc",
+        super::general_category::Mc_table), ("Me", super::general_category::Me_table),
+        ("Meetei_Mayek", super::script::Meetei_Mayek_table), ("Mende_Kikakui",
+        super::script::Mende_Kikakui_table), ("Meroitic_Cursive",
+        super::script::Meroitic_Cursive_table), ("Meroitic_Hieroglyphs",
+        super::script::Meroitic_Hieroglyphs_table), ("Miao", super::script::Miao_table), ("Mn",
+        super::general_category::Mn_table), ("Modi", super::script::Modi_table), ("Mongolian",
+        super::script::Mongolian_table), ("Mro", super::script::Mro_table), ("Myanmar",
+        super::script::Myanmar_table), ("N", super::general_category::N_table), ("Nabataean",
+        super::script::Nabataean_table), ("Nd", super::general_category::Nd_table), ("New_Tai_Lue",
+        super::script::New_Tai_Lue_table), ("Nko", super::script::Nko_table), ("Nl",
+        super::general_category::Nl_table), ("No", super::general_category::No_table),
+        ("Noncharacter_Code_Point", super::property::Noncharacter_Code_Point_table), ("Ogham",
+        super::script::Ogham_table), ("Ol_Chiki", super::script::Ol_Chiki_table), ("Old_Italic",
+        super::script::Old_Italic_table), ("Old_North_Arabian",
+        super::script::Old_North_Arabian_table), ("Old_Permic", super::script::Old_Permic_table),
+        ("Old_Persian", super::script::Old_Persian_table), ("Old_South_Arabian",
+        super::script::Old_South_Arabian_table), ("Old_Turkic", super::script::Old_Turkic_table),
+        ("Oriya", super::script::Oriya_table), ("Osmanya", super::script::Osmanya_table), ("P",
+        super::general_category::P_table), ("Pahawh_Hmong", super::script::Pahawh_Hmong_table),
+        ("Palmyrene", super::script::Palmyrene_table), ("Pau_Cin_Hau",
+        super::script::Pau_Cin_Hau_table), ("Pc", super::general_category::Pc_table), ("Pd",
+        super::general_category::Pd_table), ("Pe", super::general_category::Pe_table), ("Pf",
+        super::general_category::Pf_table), ("Phags_Pa", super::script::Phags_Pa_table),
+        ("Phoenician", super::script::Phoenician_table), ("Pi", super::general_category::Pi_table),
+        ("Po", super::general_category::Po_table), ("Ps", super::general_category::Ps_table),
+        ("Psalter_Pahlavi", super::script::Psalter_Pahlavi_table), ("Rejang",
+        super::script::Rejang_table), ("Runic", super::script::Runic_table), ("S",
+        super::general_category::S_table), ("Samaritan", super::script::Samaritan_table),
+        ("Saurashtra", super::script::Saurashtra_table), ("Sc", super::general_category::Sc_table),
+        ("Sharada", super::script::Sharada_table), ("Shavian", super::script::Shavian_table),
+        ("Siddham", super::script::Siddham_table), ("Sinhala", super::script::Sinhala_table), ("Sk",
+        super::general_category::Sk_table), ("Sm", super::general_category::Sm_table), ("So",
+        super::general_category::So_table), ("Sora_Sompeng", super::script::Sora_Sompeng_table),
+        ("Sundanese", super::script::Sundanese_table), ("Syloti_Nagri",
+        super::script::Syloti_Nagri_table), ("Syriac", super::script::Syriac_table), ("Tagalog",
+        super::script::Tagalog_table), ("Tagbanwa", super::script::Tagbanwa_table), ("Tai_Le",
+        super::script::Tai_Le_table), ("Tai_Tham", super::script::Tai_Tham_table), ("Tai_Viet",
+        super::script::Tai_Viet_table), ("Takri", super::script::Takri_table), ("Tamil",
+        super::script::Tamil_table), ("Telugu", super::script::Telugu_table), ("Thaana",
+        super::script::Thaana_table), ("Thai", super::script::Thai_table), ("Tibetan",
+        super::script::Tibetan_table), ("Tifinagh", super::script::Tifinagh_table), ("Tirhuta",
+        super::script::Tirhuta_table), ("Ugaritic", super::script::Ugaritic_table), ("Uppercase",
+        super::derived_property::Uppercase_table), ("Vai", super::script::Vai_table),
+        ("Warang_Citi", super::script::Warang_Citi_table), ("White_Space",
+        super::property::White_Space_table), ("XID_Continue",
+        super::derived_property::XID_Continue_table), ("XID_Start",
+        super::derived_property::XID_Start_table), ("Yi", super::script::Yi_table), ("Z",
+        super::general_category::Z_table), ("Zl", super::general_category::Zl_table), ("Zp",
+        super::general_category::Zp_table), ("Zs", super::general_category::Zs_table)
+    ];
+
+    pub const PERLD: &'static [(char, char)] = super::general_category::Nd_table;
+
+    pub const PERLS: &'static [(char, char)] = super::property::White_Space_table;
+
+    pub const PERLW: &'static [(char, char)] = &[
         ('\u{30}', '\u{39}'), ('\u{41}', '\u{5a}'), ('\u{5f}', '\u{5f}'), ('\u{61}', '\u{7a}'),
         ('\u{aa}', '\u{aa}'), ('\u{b5}', '\u{b5}'), ('\u{ba}', '\u{ba}'), ('\u{c0}', '\u{d6}'),
         ('\u{d8}', '\u{f6}'), ('\u{f8}', '\u{2c1}'), ('\u{2c6}', '\u{2d1}'), ('\u{2e0}', '\u{2e4}'),
@@ -4254,7 +4244,7 @@ pub mod regex {
 
 pub mod normalization {
     // Canonical decompositions
-    pub static canonical_table: &'static [(char, &'static [char])] = &[
+    pub const canonical_table: &'static [(char, &'static [char])] = &[
         ('\u{c0}', &['\u{41}', '\u{300}']), ('\u{c1}', &['\u{41}', '\u{301}']), ('\u{c2}',
         &['\u{41}', '\u{302}']), ('\u{c3}', &['\u{41}', '\u{303}']), ('\u{c4}', &['\u{41}',
         '\u{308}']), ('\u{c5}', &['\u{41}', '\u{30a}']), ('\u{c7}', &['\u{43}', '\u{327}']),
@@ -5056,7 +5046,7 @@ pub mod normalization {
     ];
 
     // Compatibility decompositions
-    pub static compatibility_table: &'static [(char, &'static [char])] = &[
+    pub const compatibility_table: &'static [(char, &'static [char])] = &[
         ('\u{a0}', &['\u{20}']), ('\u{a8}', &['\u{20}', '\u{308}']), ('\u{aa}', &['\u{61}']),
         ('\u{af}', &['\u{20}', '\u{304}']), ('\u{b2}', &['\u{32}']), ('\u{b3}', &['\u{33}']),
         ('\u{b4}', &['\u{20}', '\u{301}']), ('\u{b5}', &['\u{3bc}']), ('\u{b8}', &['\u{20}',
@@ -6480,7 +6470,7 @@ pub mod normalization {
     ];
 
     // Canonical compositions
-    pub static composition_table: &'static [(char, &'static [(char, char)])] = &[
+    pub const composition_table: &'static [(char, &'static [(char, char)])] = &[
         ('\u{3c}', &[('\u{338}', '\u{226e}')]), ('\u{3d}', &[('\u{338}', '\u{2260}')]), ('\u{3e}',
         &[('\u{338}', '\u{226f}')]), ('\u{41}', &[('\u{300}', '\u{c0}'), ('\u{301}', '\u{c1}'),
         ('\u{302}', '\u{c2}'), ('\u{303}', '\u{c3}'), ('\u{304}', '\u{100}'), ('\u{306}',
@@ -6840,7 +6830,7 @@ fn bsearch_range_value_table(c: char, r: &'static [(char, char, u8)]) -> u8 {
         }
     }
 
-    static combining_class_table: &'static [(char, char, u8)] = &[
+    const combining_class_table: &'static [(char, char, u8)] = &[
         ('\u{300}', '\u{314}', 230), ('\u{315}', '\u{315}', 232), ('\u{316}', '\u{319}', 220),
         ('\u{31a}', '\u{31a}', 232), ('\u{31b}', '\u{31b}', 216), ('\u{31c}', '\u{320}', 220),
         ('\u{321}', '\u{322}', 202), ('\u{323}', '\u{326}', 220), ('\u{327}', '\u{328}', 202),
@@ -6988,7 +6978,7 @@ fn bsearch_case_table(c: char, table: &'static [(char, char)]) -> Option<usize>
         }
     }
 
-    static LuLl_table: &'static [(char, char)] = &[
+    const LuLl_table: &'static [(char, char)] = &[
         ('\u{41}', '\u{61}'), ('\u{42}', '\u{62}'), ('\u{43}', '\u{63}'), ('\u{44}', '\u{64}'),
         ('\u{45}', '\u{65}'), ('\u{46}', '\u{66}'), ('\u{47}', '\u{67}'), ('\u{48}', '\u{68}'),
         ('\u{49}', '\u{69}'), ('\u{4a}', '\u{6a}'), ('\u{4b}', '\u{6b}'), ('\u{4c}', '\u{6c}'),
@@ -7284,7 +7274,7 @@ fn bsearch_case_table(c: char, table: &'static [(char, char)]) -> Option<usize>
         ('\u{118be}', '\u{118de}'), ('\u{118bf}', '\u{118df}')
     ];
 
-    static LlLu_table: &'static [(char, char)] = &[
+    const LlLu_table: &'static [(char, char)] = &[
         ('\u{61}', '\u{41}'), ('\u{62}', '\u{42}'), ('\u{63}', '\u{43}'), ('\u{64}', '\u{44}'),
         ('\u{65}', '\u{45}'), ('\u{66}', '\u{46}'), ('\u{67}', '\u{47}'), ('\u{68}', '\u{48}'),
         ('\u{69}', '\u{49}'), ('\u{6a}', '\u{4a}'), ('\u{6b}', '\u{4b}'), ('\u{6c}', '\u{4c}'),
@@ -7625,7 +7615,7 @@ pub fn width(c: char, is_cjk: bool) -> Option<usize> {
 
     // character width table. Based on Markus Kuhn's free wcwidth() implementation,
     //     http://www.cl.cam.ac.uk/~mgk25/ucs/wcwidth.c
-    static charwidth_table: &'static [(char, char, u8, u8)] = &[
+    const charwidth_table: &'static [(char, char, u8, u8)] = &[
         ('\u{a1}', '\u{a1}', 1, 2), ('\u{a4}', '\u{a4}', 1, 2), ('\u{a7}', '\u{a8}', 1, 2),
         ('\u{aa}', '\u{aa}', 1, 2), ('\u{ae}', '\u{ae}', 1, 2), ('\u{b0}', '\u{b4}', 1, 2),
         ('\u{b6}', '\u{ba}', 1, 2), ('\u{bc}', '\u{bf}', 1, 2), ('\u{c6}', '\u{c6}', 1, 2),
@@ -7839,7 +7829,7 @@ pub fn grapheme_category(c: char) -> GraphemeCat {
         bsearch_range_value_table(c, grapheme_cat_table)
     }
 
-    static grapheme_cat_table: &'static [(char, char, GraphemeCat)] = &[
+    const grapheme_cat_table: &'static [(char, char, GraphemeCat)] = &[
         ('\u{0}', '\u{1f}', GC_Control), ('\u{7f}', '\u{9f}', GC_Control), ('\u{ad}', '\u{ad}',
         GC_Control), ('\u{300}', '\u{36f}', GC_Extend), ('\u{483}', '\u{487}', GC_Extend),
         ('\u{488}', '\u{489}', GC_Extend), ('\u{591}', '\u{5bd}', GC_Extend), ('\u{5bf}', '\u{5bf}',
diff --git a/src/libunicode/u_char.rs b/src/libunicode/u_char.rs
deleted file mode 100644 (file)
index c0f45ca..0000000
+++ /dev/null
@@ -1,317 +0,0 @@
-// 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.
-
-//! Unicode-intensive `char` methods along with the `core` methods.
-//!
-//! These methods implement functionality for `char` that requires knowledge of
-//! Unicode definitions, including normalization, categorization, and display information.
-
-use core::char;
-use core::char::CharExt as C;
-use core::option::Option;
-use tables::{derived_property, property, general_category, conversions, charwidth};
-
-/// Functionality for manipulating `char`.
-#[stable(feature = "rust1", since = "1.0.0")]
-pub trait CharExt {
-    /// Checks if a `char` parses as a numeric digit in the given radix.
-    ///
-    /// Compared to `is_numeric()`, this function only recognizes the characters
-    /// `0-9`, `a-z` and `A-Z`.
-    ///
-    /// # Return value
-    ///
-    /// Returns `true` if `c` is a valid digit under `radix`, and `false`
-    /// otherwise.
-    ///
-    /// # Panics
-    ///
-    /// Panics if given a radix > 36.
-    #[unstable(feature = "unicode",
-               reason = "pending integer conventions")]
-    fn is_digit(self, radix: u32) -> bool;
-
-    /// Converts a character to the corresponding digit.
-    ///
-    /// # Return value
-    ///
-    /// If `c` is between '0' and '9', the corresponding value between 0 and
-    /// 9. If `c` is 'a' or 'A', 10. If `c` is 'b' or 'B', 11, etc. Returns
-    /// none if the character does not refer to a digit in the given radix.
-    ///
-    /// # Panics
-    ///
-    /// Panics if given a radix outside the range [0..36].
-    #[unstable(feature = "unicode",
-               reason = "pending integer conventions")]
-    fn to_digit(self, radix: u32) -> Option<u32>;
-
-    /// Returns an iterator that yields the hexadecimal Unicode escape
-    /// of a character, as `char`s.
-    ///
-    /// All characters are escaped with Rust syntax of the form `\\u{NNNN}`
-    /// where `NNNN` is the shortest hexadecimal representation of the code
-    /// point.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn escape_unicode(self) -> char::EscapeUnicode;
-
-    /// Returns an iterator that yields the 'default' ASCII and
-    /// C++11-like literal escape of a character, as `char`s.
-    ///
-    /// The default is chosen with a bias toward producing literals that are
-    /// legal in a variety of languages, including C++11 and similar C-family
-    /// languages. The exact rules are:
-    ///
-    /// * Tab, CR and LF are escaped as '\t', '\r' and '\n' respectively.
-    /// * Single-quote, double-quote and backslash chars are backslash-
-    ///   escaped.
-    /// * Any other chars in the range [0x20,0x7e] are not escaped.
-    /// * Any other chars are given hex Unicode escapes; see `escape_unicode`.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn escape_default(self) -> char::EscapeDefault;
-
-    /// Returns the amount of bytes this character would need if encoded in
-    /// UTF-8.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn len_utf8(self) -> usize;
-
-    /// Returns the amount of bytes this character would need if encoded in
-    /// UTF-16.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn len_utf16(self) -> usize;
-
-    /// Encodes this character as UTF-8 into the provided byte buffer,
-    /// and then returns the number of bytes written.
-    ///
-    /// If the buffer is not large enough, nothing will be written into it
-    /// and a `None` will be returned.
-    #[unstable(feature = "unicode",
-               reason = "pending decision about Iterator/Writer/Reader")]
-    fn encode_utf8(self, dst: &mut [u8]) -> Option<usize>;
-
-    /// Encodes this character as UTF-16 into the provided `u16` buffer,
-    /// and then returns the number of `u16`s written.
-    ///
-    /// If the buffer is not large enough, nothing will be written into it
-    /// and a `None` will be returned.
-    #[unstable(feature = "unicode",
-               reason = "pending decision about Iterator/Writer/Reader")]
-    fn encode_utf16(self, dst: &mut [u16]) -> Option<usize>;
-
-    /// Returns whether the specified character is considered a Unicode
-    /// alphabetic code point.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_alphabetic(self) -> bool;
-
-    /// Returns whether the specified character satisfies the 'XID_Start'
-    /// Unicode property.
-    ///
-    /// 'XID_Start' is a Unicode Derived Property specified in
-    /// [UAX #31](http://unicode.org/reports/tr31/#NFKC_Modifications),
-    /// mostly similar to ID_Start but modified for closure under NFKx.
-    #[unstable(feature = "unicode",
-               reason = "mainly needed for compiler internals")]
-    fn is_xid_start(self) -> bool;
-
-    /// Returns whether the specified `char` satisfies the 'XID_Continue'
-    /// Unicode property.
-    ///
-    /// 'XID_Continue' is a Unicode Derived Property specified in
-    /// [UAX #31](http://unicode.org/reports/tr31/#NFKC_Modifications),
-    /// mostly similar to 'ID_Continue' but modified for closure under NFKx.
-    #[unstable(feature = "unicode",
-               reason = "mainly needed for compiler internals")]
-    fn is_xid_continue(self) -> bool;
-
-    /// Indicates whether a character is in lowercase.
-    ///
-    /// This is defined according to the terms of the Unicode Derived Core
-    /// Property `Lowercase`.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_lowercase(self) -> bool;
-
-    /// Indicates whether a character is in uppercase.
-    ///
-    /// This is defined according to the terms of the Unicode Derived Core
-    /// Property `Uppercase`.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_uppercase(self) -> bool;
-
-    /// Indicates whether a character is whitespace.
-    ///
-    /// Whitespace is defined in terms of the Unicode Property `White_Space`.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_whitespace(self) -> bool;
-
-    /// Indicates whether a character is alphanumeric.
-    ///
-    /// Alphanumericness is defined in terms of the Unicode General Categories
-    /// 'Nd', 'Nl', 'No' and the Derived Core Property 'Alphabetic'.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_alphanumeric(self) -> bool;
-
-    /// Indicates whether a character is a control code point.
-    ///
-    /// Control code points are defined in terms of the Unicode General
-    /// Category `Cc`.
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_control(self) -> bool;
-
-    /// Indicates whether the character is numeric (Nd, Nl, or No).
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_numeric(self) -> bool;
-
-    /// Converts a character to its lowercase equivalent.
-    ///
-    /// The case-folding performed is the common or simple mapping. See
-    /// `to_uppercase()` for references and more information.
-    ///
-    /// # Return value
-    ///
-    /// Returns the lowercase equivalent of the character, or the character
-    /// itself if no conversion is possible.
-    #[unstable(feature = "unicode",
-               reason = "pending case transformation decisions")]
-    fn to_lowercase(self) -> char;
-
-    /// Converts a character to its uppercase equivalent.
-    ///
-    /// The case-folding performed is the common or simple mapping: it maps
-    /// one Unicode codepoint (one character in Rust) to its uppercase
-    /// equivalent according to the Unicode database [1]. The additional
-    /// [`SpecialCasing.txt`] is not considered here, as it expands to multiple
-    /// codepoints in some cases.
-    ///
-    /// A full reference can be found here [2].
-    ///
-    /// # Return value
-    ///
-    /// Returns the uppercase equivalent of the character, or the character
-    /// itself if no conversion was made.
-    ///
-    /// [1]: ftp://ftp.unicode.org/Public/UNIDATA/UnicodeData.txt
-    ///
-    /// [`SpecialCasing`.txt`]: ftp://ftp.unicode.org/Public/UNIDATA/SpecialCasing.txt
-    ///
-    /// [2]: http://www.unicode.org/versions/Unicode4.0.0/ch03.pdf#G33992
-    #[unstable(feature = "unicode",
-               reason = "pending case transformation decisions")]
-    fn to_uppercase(self) -> char;
-
-    /// Returns this character's displayed width in columns, or `None` if it is a
-    /// control character other than `'\x00'`.
-    ///
-    /// `is_cjk` determines behavior for characters in the Ambiguous category:
-    /// if `is_cjk` is `true`, these are 2 columns wide; otherwise, they are 1.
-    /// In CJK contexts, `is_cjk` should be `true`, else it should be `false`.
-    /// [Unicode Standard Annex #11](http://www.unicode.org/reports/tr11/)
-    /// recommends that these characters be treated as 1 column (i.e.,
-    /// `is_cjk` = `false`) if the context cannot be reliably determined.
-    #[unstable(feature = "unicode",
-               reason = "needs expert opinion. is_cjk flag stands out as ugly")]
-    fn width(self, is_cjk: bool) -> Option<usize>;
-}
-
-#[stable(feature = "rust1", since = "1.0.0")]
-impl CharExt for char {
-    #[unstable(feature = "unicode",
-               reason = "pending integer conventions")]
-    fn is_digit(self, radix: u32) -> bool { C::is_digit(self, radix) }
-    #[unstable(feature = "unicode",
-               reason = "pending integer conventions")]
-    fn to_digit(self, radix: u32) -> Option<u32> { C::to_digit(self, radix) }
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn escape_unicode(self) -> char::EscapeUnicode { C::escape_unicode(self) }
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn escape_default(self) -> char::EscapeDefault { C::escape_default(self) }
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn len_utf8(self) -> usize { C::len_utf8(self) }
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn len_utf16(self) -> usize { C::len_utf16(self) }
-    #[unstable(feature = "unicode",
-               reason = "pending decision about Iterator/Writer/Reader")]
-    fn encode_utf8(self, dst: &mut [u8]) -> Option<usize> { C::encode_utf8(self, dst) }
-    #[unstable(feature = "unicode",
-               reason = "pending decision about Iterator/Writer/Reader")]
-    fn encode_utf16(self, dst: &mut [u16]) -> Option<usize> { C::encode_utf16(self, dst) }
-
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_alphabetic(self) -> bool {
-        match self {
-            'a' ... 'z' | 'A' ... 'Z' => true,
-            c if c > '\x7f' => derived_property::Alphabetic(c),
-            _ => false
-        }
-    }
-
-    #[unstable(feature = "unicode",
-               reason = "mainly needed for compiler internals")]
-    fn is_xid_start(self) -> bool { derived_property::XID_Start(self) }
-
-    #[unstable(feature = "unicode",
-               reason = "mainly needed for compiler internals")]
-    fn is_xid_continue(self) -> bool { derived_property::XID_Continue(self) }
-
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_lowercase(self) -> bool {
-        match self {
-            'a' ... 'z' => true,
-            c if c > '\x7f' => derived_property::Lowercase(c),
-            _ => false
-        }
-    }
-
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_uppercase(self) -> bool {
-        match self {
-            'A' ... 'Z' => true,
-            c if c > '\x7f' => derived_property::Uppercase(c),
-            _ => false
-        }
-    }
-
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_whitespace(self) -> bool {
-        match self {
-            ' ' | '\x09' ... '\x0d' => true,
-            c if c > '\x7f' => property::White_Space(c),
-            _ => false
-        }
-    }
-
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_alphanumeric(self) -> bool {
-        self.is_alphabetic() || self.is_numeric()
-    }
-
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_control(self) -> bool { general_category::Cc(self) }
-
-    #[stable(feature = "rust1", since = "1.0.0")]
-    fn is_numeric(self) -> bool {
-        match self {
-            '0' ... '9' => true,
-            c if c > '\x7f' => general_category::N(c),
-            _ => false
-        }
-    }
-
-    #[unstable(feature = "unicode",
-               reason = "pending case transformation decisions")]
-    fn to_lowercase(self) -> char { conversions::to_lower(self) }
-
-    #[unstable(feature = "unicode",
-               reason = "pending case transformation decisions")]
-    fn to_uppercase(self) -> char { conversions::to_upper(self) }
-
-    #[unstable(feature = "unicode",
-               reason = "needs expert opinion. is_cjk flag stands out as ugly")]
-    fn width(self, is_cjk: bool) -> Option<usize> { charwidth::width(self, is_cjk) }
-}
index 38cbe5c7dea16218d1942fc7eef3f9e70406dc18..9b3f4b0521da3fadfe986078e80523368514ff46 100644 (file)
@@ -26,7 +26,7 @@
 use core::slice;
 use core::str::Split;
 
-use u_char::CharExt as UCharExt; // conflicts with core::prelude::CharExt
+use char::CharExt as UCharExt; // conflicts with core::prelude::CharExt
 use tables::grapheme::GraphemeCat;
 
 /// An iterator over the words of a string, separated by a sequence of whitespace
@@ -525,7 +525,7 @@ fn next(&mut self) -> Option<u16> {
             return Some(tmp);
         }
 
-        let mut buf = [0u16; 2];
+        let mut buf = [0; 2];
         self.chars.next().map(|ch| {
             let n = CharExt::encode_utf16(ch, &mut buf).unwrap_or(0);
             if n == 2 { self.extra = buf[1]; }
index b89c3f039b61edbb077771eda2ee8a718dbec7e0..bff69076975642c64e76dbeaa53476bfa7212086 160000 (submodule)
--- a/src/llvm
+++ b/src/llvm
@@ -1 +1 @@
-Subproject commit b89c3f039b61edbb077771eda2ee8a718dbec7e0
+Subproject commit bff69076975642c64e76dbeaa53476bfa7212086
index 8900b60d1913a2eb533702a630fda0cb4f0b9063..ac7f2f824cbbf9ab9c5d3dcab3fb911ad7ea8df0 100644 (file)
 
 //! Basic data structures for representing a book.
 
-use std::old_io::BufferedReader;
+use std::io::prelude::*;
+use std::io::BufReader;
 use std::iter;
 use std::iter::AdditiveIterator;
+use std::path::{Path, PathBuf};
 
 pub struct BookItem {
     pub title: String,
-    pub path: Path,
-    pub path_to_root: Path,
+    pub path: PathBuf,
+    pub path_to_root: PathBuf,
     pub children: Vec<BookItem>,
 }
 
@@ -76,7 +78,7 @@ pub fn iter(&self) -> BookItems {
 }
 
 /// Construct a book by parsing a summary (markdown table of contents).
-pub fn parse_summary<R: Reader>(input: R, src: &Path) -> Result<Book, Vec<String>> {
+pub fn parse_summary(input: &mut Read, src: &Path) -> Result<Book, Vec<String>> {
     fn collapse(stack: &mut Vec<BookItem>,
                 top_items: &mut Vec<BookItem>,
                 to_level: usize) {
@@ -100,16 +102,16 @@ fn collapse(stack: &mut Vec<BookItem>,
     // always include the introduction
     top_items.push(BookItem {
         title: "Introduction".to_string(),
-        path: Path::new("README.md"),
-        path_to_root: Path::new("."),
+        path: PathBuf::new("README.md"),
+        path_to_root: PathBuf::new("."),
         children: vec!(),
     });
 
-    for line_result in BufferedReader::new(input).lines() {
+    for line_result in BufReader::new(input).lines() {
         let line = match line_result {
             Ok(line) => line,
             Err(err) => {
-                errors.push(err.desc.to_string()); // FIXME: include detail
+                errors.push(err.to_string());
                 return Err(errors);
             }
         };
@@ -125,16 +127,16 @@ fn collapse(stack: &mut Vec<BookItem>,
         let title = line[start_bracket + 1..end_bracket].to_string();
         let indent = &line[..star_idx];
 
-        let path_from_root = match src.join(given_path).path_relative_from(src) {
-            Some(p) => p,
+        let path_from_root = match src.join(given_path).relative_from(src) {
+            Some(p) => p.to_path_buf(),
             None => {
                 errors.push(format!("paths in SUMMARY.md must be relative, \
                                      but path '{}' for section '{}' is not.",
                                      given_path, title));
-                Path::new("")
+                PathBuf::new("")
             }
         };
-        let path_to_root = Path::new(iter::repeat("../")
+        let path_to_root = PathBuf::new(&iter::repeat("../")
                                          .take(path_from_root.components().count() - 1)
                                          .collect::<String>());
         let item = BookItem {
index f36d97d6d120d50ef2f42aaa2f47f3de788e49c7..731773917e09118452152504f0df79da09bd10e4 100644 (file)
 //! Implementation of the `build` subcommand, used to compile a book.
 
 use std::env;
-use std::os;
-use std::old_io;
-use std::old_io::{fs, File, BufferedWriter, TempDir, IoResult};
+use std::fs::{self, File};
+use std::io::prelude::*;
+use std::io::{self, BufWriter};
+use std::path::{Path, PathBuf};
+use rustc_back::tempdir::TempDir;
 
 use subcommand::Subcommand;
 use term::Term;
-use error::{Error, CliResult, CommandResult};
+use error::{err, CliResult, CommandResult};
 use book;
 use book::{Book, BookItem};
 use css;
 
 pub fn parse_cmd(name: &str) -> Option<Box<Subcommand>> {
     if name == "build" {
-        Some(box Build as Box<Subcommand>)
+        Some(Box::new(Build))
     } else {
         None
     }
 }
 
-fn write_toc(book: &Book, path_to_root: &Path, out: &mut Writer) -> IoResult<()> {
+fn write_toc(book: &Book, path_to_root: &Path, out: &mut Write) -> io::Result<()> {
     fn walk_items(items: &[BookItem],
                   section: &str,
                   path_to_root: &Path,
-                  out: &mut Writer) -> IoResult<()> {
+                  out: &mut Write) -> io::Result<()> {
         for (i, item) in items.iter().enumerate() {
             try!(walk_item(item, &format!("{}{}.", section, i + 1)[..], path_to_root, out));
         }
@@ -48,9 +50,9 @@ fn walk_items(items: &[BookItem],
     fn walk_item(item: &BookItem,
                  section: &str,
                  path_to_root: &Path,
-                 out: &mut Writer) -> IoResult<()> {
+                 out: &mut Write) -> io::Result<()> {
         try!(writeln!(out, "<li><a href='{}'><b>{}</b> {}</a>",
-                 path_to_root.join(item.path.with_extension("html")).display(),
+                 path_to_root.join(&item.path.with_extension("html")).display(),
                  section,
                  item.title));
         if !item.children.is_empty() {
@@ -75,30 +77,35 @@ fn walk_item(item: &BookItem,
 fn render(book: &Book, tgt: &Path) -> CliResult<()> {
     let tmp = try!(TempDir::new("rust-book"));
 
-    for (section, item) in book.iter() {
-        println!("{} {}", section, item.title);
-
-        let out_path = tgt.join(item.path.dirname());
+    for (_section, item) in book.iter() {
+        let out_path = match item.path.parent() {
+            Some(p) => tgt.join(p),
+            None => tgt.to_path_buf(),
+        };
 
         let src;
         if env::args().len() < 3 {
-            src = os::getcwd().unwrap().clone();
+            src = env::current_dir().unwrap().clone();
         } else {
-            src = Path::new(env::args().nth(2).unwrap().clone());
+            src = PathBuf::new(&env::args().nth(2).unwrap());
         }
         // preprocess the markdown, rerouting markdown references to html references
-        let markdown_data = try!(File::open(&src.join(&item.path)).read_to_string());
-        let preprocessed_path = tmp.path().join(item.path.filename().unwrap());
+        let mut markdown_data = String::new();
+        try!(File::open(&src.join(&item.path)).and_then(|mut f| {
+            f.read_to_string(&mut markdown_data)
+        }));
+        let preprocessed_path = tmp.path().join(item.path.file_name().unwrap());
         {
             let urls = markdown_data.replace(".md)", ".html)");
-            try!(File::create(&preprocessed_path)
-                      .write_str(&urls[..]));
+            try!(File::create(&preprocessed_path).and_then(|mut f| {
+                f.write_all(urls.as_bytes())
+            }));
         }
 
         // write the prelude to a temporary HTML file for rustdoc inclusion
         let prelude = tmp.path().join("prelude.html");
         {
-            let mut toc = BufferedWriter::new(try!(File::create(&prelude)));
+            let mut toc = BufWriter::new(try!(File::create(&prelude)));
             try!(writeln!(&mut toc, r#"<div id="nav">
                 <button id="toggle-nav">
                   <span class="sr-only">Toggle navigation</span>
@@ -115,12 +122,12 @@ fn render(book: &Book, tgt: &Path) -> CliResult<()> {
         // write the postlude to a temporary HTML file for rustdoc inclusion
         let postlude = tmp.path().join("postlude.html");
         {
-            let mut toc = BufferedWriter::new(try!(File::create(&postlude)));
-            try!(toc.write_str(javascript::JAVASCRIPT));
+            let mut toc = BufWriter::new(try!(File::create(&postlude)));
+            try!(toc.write_all(javascript::JAVASCRIPT.as_bytes()));
             try!(writeln!(&mut toc, "</div></div>"));
         }
 
-        try!(fs::mkdir_recursive(&out_path, old_io::USER_DIR));
+        try!(fs::create_dir_all(&out_path));
 
         let rustdoc_args: &[String] = &[
             "".to_string(),
@@ -135,7 +142,7 @@ fn render(book: &Book, tgt: &Path) -> CliResult<()> {
         if output_result != 0 {
             let message = format!("Could not execute `rustdoc` with {:?}: {}",
                                   rustdoc_args, output_result);
-            return Err(box message as Box<Error>);
+            return Err(err(&message));
         }
     }
 
@@ -150,28 +157,30 @@ fn parse_args(&mut self, _: &[String]) -> CliResult<()> {
     }
     fn usage(&self) {}
     fn execute(&mut self, term: &mut Term) -> CommandResult<()> {
-        let cwd = os::getcwd().unwrap();
+        let cwd = env::current_dir().unwrap();
         let src;
         let tgt;
 
         if env::args().len() < 3 {
             src = cwd.clone();
         } else {
-            src = Path::new(env::args().nth(2).unwrap().clone());
+            src = PathBuf::new(&env::args().nth(2).unwrap());
         }
 
         if env::args().len() < 4 {
             tgt = cwd.join("_book");
         } else {
-            tgt = Path::new(env::args().nth(3).unwrap().clone());
+            tgt = PathBuf::new(&env::args().nth(3).unwrap());
         }
 
-        try!(fs::mkdir(&tgt, old_io::USER_DIR));
+        try!(fs::create_dir(&tgt));
 
-        try!(File::create(&tgt.join("rust-book.css")).write_str(css::STYLE));
+        try!(File::create(&tgt.join("rust-book.css")).and_then(|mut f| {
+            f.write_all(css::STYLE.as_bytes())
+        }));
 
-        let summary = try!(File::open(&src.join("SUMMARY.md")));
-        match book::parse_summary(summary, &src) {
+        let mut summary = try!(File::open(&src.join("SUMMARY.md")));
+        match book::parse_summary(&mut summary, &src) {
             Ok(book) => {
                 // execute rustdoc on the whole book
                 render(&book, &tgt)
@@ -182,7 +191,7 @@ fn execute(&mut self, term: &mut Term) -> CommandResult<()> {
                     term.err(&format!("error: {}", err)[..]);
                 }
 
-                Err(box format!("{} errors occurred", n) as Box<Error>)
+                Err(err(&format!("{} errors occurred", n)))
             }
         }
     }
index 43c882c7d5b8a69c1c660049f7abf6f969fe8764..294b4e556694ad2be1c935ab5749226a392877bf 100644 (file)
 
 //! Error handling utilities. WIP.
 
+use std::error::Error;
 use std::fmt;
-use std::fmt::{Debug, Formatter};
-
-use std::old_io::IoError;
 
 pub type CliError = Box<Error + 'static>;
 pub type CliResult<T> = Result<T, CliError>;
 pub type CommandError = Box<Error + 'static>;
 pub type CommandResult<T> = Result<T, CommandError>;
 
-pub trait Error {
-    fn description(&self) -> &str;
-
-    fn detail(&self) -> Option<&str> { None }
-    fn cause(&self) -> Option<&Error> { None }
-}
-
-pub trait FromError<E> {
-    fn from_err(err: E) -> Self;
-}
-
-impl Debug for Box<Error + 'static> {
-    fn fmt(&self, f: &mut Formatter) -> fmt::Result {
-        write!(f, "{}", self.description())
-    }
-}
-
-impl<E: Error + 'static> FromError<E> for Box<Error + 'static> {
-    fn from_err(err: E) -> Box<Error + 'static> {
-        box err as Box<Error>
-    }
-}
+pub fn err(s: &str) -> CliError {
+    struct E(String);
 
-impl<'a> Error for &'a str {
-    fn description<'b>(&'b self) -> &'b str {
-        *self
+    impl Error for E {
+        fn description(&self) -> &str { &self.0 }
     }
-}
-
-impl Error for String {
-    fn description<'a>(&'a self) -> &'a str {
-        &self[..]
+    impl fmt::Display for E {
+        fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+            self.0.fmt(f)
+        }
     }
-}
-
-impl<'a> Error for Box<Error + 'a> {
-    fn description(&self) -> &str { (**self).description() }
-    fn detail(&self) -> Option<&str> { (**self).detail() }
-    fn cause(&self) -> Option<&Error> { (**self).cause() }
-}
-
-impl FromError<()> for () {
-    fn from_err(_: ()) -> () { () }
-}
 
-impl FromError<IoError> for IoError {
-    fn from_err(error: IoError) -> IoError { error }
+    Box::new(E(s.to_string()))
 }
-
-impl Error for IoError {
-    fn description(&self) -> &str {
-        self.desc
-    }
-    fn detail(&self) -> Option<&str> {
-        self.detail.as_ref().map(|s| &s[..])
-    }
-}
-
-
-//fn iter_map_err<T, U, E, I: Iterator<Result<T,E>>>(iter: I,
index 7fd8214f7311af078614aaf7ebcb4eebaa8f3569..995d2f2494a490b1845344aaa86886152a733bd9 100644 (file)
@@ -19,7 +19,7 @@
 
 pub fn parse_cmd(name: &str) -> Option<Box<Subcommand>> {
     match name {
-        "help" | "--help" | "-h" | "-?" => Some(box Help as Box<Subcommand>),
+        "help" | "--help" | "-h" | "-?" => Some(Box::new(Help)),
         _ => None
     }
 }
index b9fc011e8b9a584edf198247e2eb1d0de9f67399..8df622b0b5d0c2e58c5b4a984dc0316293d44bf6 100644 (file)
@@ -8,31 +8,24 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-#![feature(collections)]
+#![deny(warnings)]
+
 #![feature(core)]
+#![feature(exit_status)]
+#![feature(io)]
 #![feature(old_io)]
-#![feature(env)]
-#![feature(os)]
-#![feature(old_path)]
+#![feature(path)]
 #![feature(rustdoc)]
+#![feature(rustc_private)]
 
 extern crate rustdoc;
+extern crate rustc_back;
 
 use std::env;
+use std::error::Error;
 use subcommand::Subcommand;
 use term::Term;
 
-macro_rules! try (
-    ($expr:expr) => ({
-        use error;
-        match $expr {
-            Ok(val) => val,
-            Err(err) => return Err(error::FromError::from_err(err))
-        }
-    })
-);
-
 mod term;
 mod error;
 mod book;
@@ -56,15 +49,12 @@ fn main() {
     } else {
         match subcommand::parse_name(&cmd[1][..]) {
             Some(mut subcmd) => {
-                match subcmd.parse_args(cmd.tail()) {
+                match subcmd.parse_args(&cmd[..cmd.len()-1]) {
                     Ok(_) => {
                         match subcmd.execute(&mut term) {
                             Ok(_) => (),
                             Err(err) => {
-                                term.err(&format!("error: {}", err.description())[..]);
-                                err.detail().map(|detail| {
-                                    term.err(&format!("detail: {}", detail)[..]);
-                                });
+                                term.err(&format!("error: {}", err));
                             }
                         }
                     }
index 808527dcef95eeeaa2b2b96f3dbfe37abc24e4aa..2fa7b7eed7b05d77a8bd6f58ea0b29c7a4f7bc48 100644 (file)
@@ -19,7 +19,7 @@
 
 pub fn parse_cmd(name: &str) -> Option<Box<Subcommand>> {
     if name == "serve" {
-        Some(box Serve as Box<Subcommand>)
+        Some(Box::new(Serve))
     } else {
         None
     }
index 98aa3fca184dca3f4c05e04fc9d09ba91641892d..06595cb0455a31d1bb4cecc50bbd546688bcb952 100644 (file)
@@ -21,7 +21,7 @@ pub struct Term {
 impl Term {
     pub fn new() -> Term {
         Term {
-            err: box stdio::stderr() as Box<Writer>,
+            err: Box::new(stdio::stderr())
         }
     }
 
index 727a385a8f02811e19eb7a43d87b6500cd369e63..72df0768e7b9b5c70972123ec3c2425db87bbafe 100644 (file)
 //! Implementation of the `test` subcommand. Just a stub for now.
 
 use subcommand::Subcommand;
-use error::CliResult;
-use error::CommandResult;
-use error::Error;
+use error::{err, CliResult, CommandResult};
 use term::Term;
 use book;
-use std::old_io::{Command, File};
-use std::os;
+
+use std::fs::File;
+use std::env;
+use std::process::Command;
 
 struct Test;
 
 pub fn parse_cmd(name: &str) -> Option<Box<Subcommand>> {
     if name == "test" {
-        Some(box Test as Box<Subcommand>)
+        Some(Box::new(Test))
     } else {
         None
     }
@@ -35,11 +35,11 @@ fn parse_args(&mut self, _: &[String]) -> CliResult<()> {
     }
     fn usage(&self) {}
     fn execute(&mut self, term: &mut Term) -> CommandResult<()> {
-        let cwd = os::getcwd().unwrap();
+        let cwd = env::current_dir().unwrap();
         let src = cwd.clone();
 
-        let summary = File::open(&src.join("SUMMARY.md"));
-        match book::parse_summary(summary, &src) {
+        let mut summary = try!(File::open(&src.join("SUMMARY.md")));
+        match book::parse_summary(&mut summary, &src) {
             Ok(book) => {
                 for (_, item) in book.iter() {
                     let output_result = Command::new("rustdoc")
@@ -50,15 +50,15 @@ fn execute(&mut self, term: &mut Term) -> CommandResult<()> {
                         Ok(output) => {
                             if !output.status.success() {
                                 term.err(&format!("{}\n{}",
-                                         String::from_utf8_lossy(&output.output[..]),
-                                         String::from_utf8_lossy(&output.error[..]))[..]);
-                                return Err(box "Some tests failed." as Box<Error>);
+                                         String::from_utf8_lossy(&output.stdout),
+                                         String::from_utf8_lossy(&output.stderr)));
+                                return Err(err("some tests failed"));
                             }
 
                         }
                         Err(e) => {
-                            let message = format!("Could not execute `rustdoc`: {}", e);
-                            return Err(box message as Box<Error>);
+                            let message = format!("could not execute `rustdoc`: {}", e);
+                            return Err(err(&message))
                         }
                     }
                 }
@@ -67,7 +67,7 @@ fn execute(&mut self, term: &mut Term) -> CommandResult<()> {
                 for err in errors {
                     term.err(&err[..]);
                 }
-                return Err(box "There was an error." as Box<Error>);
+                return Err(err("there was an error"))
             }
         }
         Ok(()) // lol
index 2cd7ed6c1550781d31be6ab2bf7a54e56b264294..1ea40fc46a52196764be269294605440a042f794 100644 (file)
@@ -1,4 +1,4 @@
 # If this file is modified, then llvm will be forcibly cleaned and then rebuilt.
 # The actual contents of this file do not matter, but to trigger a change on the
 # build bots then the contents should be changed so git updates the mtime.
-2015-02-19
+2015-03-04
index 318f66b946585d6cbd44f6760ab8e0e56f54d62b..35f46ca6d3299a68f4e5b9cc33c8160864a01e20 100644 (file)
@@ -1,4 +1,14 @@
+S 2015-03-07 270a677
+  freebsd-x86_64 3c147d8e4cfdcb02c2569f5aca689a1d8920d17b
+  linux-i386 50a47ef247610fb089d2c4f24e4b641eb0ba4afb
+  linux-x86_64 ccb20709b3c984f960ddde996451be8ce2268d7c
+  macos-i386 ad263bdeadcf9bf1889426e0c1391a7cf277364e
+  macos-x86_64 01c8275828042264206b7acd8e86dc719a2f27aa
+  winnt-i386 cb73ac7a9bf408e8b5cdb92d595082a537a90794
+  winnt-x86_64 b9b47e80101f726ae4f5919373ea20b92d827f3c
+
 S 2015-02-25 880fb89
+  bitrig-x86_64 8cdc4ca0a80103100f46cbf8caa9fe497df048c5
   freebsd-x86_64 f4cbe4227739de986444211f8ee8d74745ab8f7f
   linux-i386 3278ebbce8cb269acc0614dac5ddac07eab6a99c
   linux-x86_64 72287d0d88de3e5a53bae78ac0d958e1a7637d73
index 98881eb09bf9bc89848da0b64cee29cfc309cb6e..44d3a69fde48ffea2eb6d1a9e2bb1982ebd20af4 100644 (file)
@@ -16,7 +16,7 @@ pub struct cat {
     }
 
     impl cat {
-        pub fn speak(&mut self) { self.meows += 1_usize; }
+        pub fn speak(&mut self) { self.meows += 1; }
         pub fn meow_count(&mut self) -> uint { self.meows }
     }
 
index 9d7905cdebd04eb10cb8f1ccca51fe02c1bea8ab..c10ef805a65de941aafdf7029ca799a496c01dd6 100644 (file)
@@ -34,8 +34,8 @@ pub fn eat(&mut self) -> bool {
     impl cat {
         pub fn meow(&mut self) {
             println!("Meow");
-            self.meows += 1_usize;
-            if self.meows % 5_usize == 0_usize {
+            self.meows += 1;
+            if self.meows % 5 == 0 {
                 self.how_hungry += 1;
             }
         }
index 96a06968c5fa3cc961496cba8a20ee33163eddc7..28fa354fef34ceda4b8a0a66998aa6f35b8e80b0 100644 (file)
@@ -26,8 +26,8 @@ fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
     impl cat {
         fn meow(&mut self) {
             println!("Meow");
-            self.meows += 1_usize;
-            if self.meows % 5_usize == 0_usize {
+            self.meows += 1;
+            if self.meows % 5 == 0 {
                 self.how_hungry += 1;
             }
         }
index 6ee497370e8e33da19591b74937a8327ba3493fd..a650b30e593f9d9f4c7c6c76acd9518c16fc4745 100644 (file)
@@ -20,7 +20,7 @@ fn to<F>(&self, v: uint, mut f: F) where F: FnMut(uint) {
         let mut i = *self;
         while i < v {
             f(i);
-            i += 1_usize;
+            i += 1;
         }
     }
 }
index 8e00b0dc7be74f444d5234084a323a4b2234160b..07d03b4c7590ff9d66d6e9d2fd8beff8245759dc 100644 (file)
 
 #[inline]
 pub fn iter<T, F>(v: &[T], mut f: F) where F: FnMut(&T) {
-    let mut i = 0_usize;
+    let mut i = 0;
     let n = v.len();
     while i < n {
         f(&v[i]);
-        i += 1_usize;
+        i += 1;
     }
 }
index ce041118906ed9a2f9c174e454000d9248493648..f3ad2a3aeb963c2208924e41d0a360c88e40d258 100644 (file)
 
 // same as cci_iter_lib, more-or-less, but not marked inline
 pub fn iter<F>(v: Vec<uint> , mut f: F) where F: FnMut(uint) {
-    let mut i = 0_usize;
+    let mut i = 0;
     let n = v.len();
     while i < n {
         f(v[i]);
-        i += 1_usize;
+        i += 1;
     }
 }
diff --git a/src/test/auxiliary/cross_crate_spans.rs b/src/test/auxiliary/cross_crate_spans.rs
new file mode 100644 (file)
index 0000000..22c2068
--- /dev/null
@@ -0,0 +1,26 @@
+// Copyright 2013-2015 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.
+
+#![crate_type = "rlib"]
+#![omit_gdb_pretty_printer_section]
+
+// no-prefer-dynamic
+// compile-flags:-g
+
+pub fn generic_function<T: Clone>(val: T) -> (T, T) {
+    let result = (val.clone(), val.clone());
+    let a_variable: u32 = 123456789;
+    let another_variable: f64 = 123456789.5;
+    zzz();
+    result
+}
+
+#[inline(never)]
+fn zzz() {()}
\ No newline at end of file
diff --git a/src/test/auxiliary/custom_derive_plugin.rs b/src/test/auxiliary/custom_derive_plugin.rs
new file mode 100644 (file)
index 0000000..e268896
--- /dev/null
@@ -0,0 +1,74 @@
+// Copyright 2015 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.
+
+// force-host
+
+#![feature(plugin_registrar)]
+#![feature(box_syntax)]
+#![feature(rustc_private)]
+
+extern crate syntax;
+extern crate rustc;
+
+use syntax::ast;
+use syntax::codemap::Span;
+use syntax::ext::base::{Decorator, ExtCtxt};
+use syntax::ext::build::AstBuilder;
+use syntax::ext::deriving::generic::{cs_fold, TraitDef, MethodDef, combine_substructure};
+use syntax::ext::deriving::generic::ty::{Literal, LifetimeBounds, Path, borrowed_explicit_self};
+use syntax::parse::token;
+use syntax::ptr::P;
+use rustc::plugin::Registry;
+
+#[plugin_registrar]
+pub fn plugin_registrar(reg: &mut Registry) {
+    reg.register_syntax_extension(
+        token::intern("derive_TotalSum"),
+        Decorator(box expand));
+}
+
+fn expand(cx: &mut ExtCtxt,
+          span: Span,
+          mitem: &ast::MetaItem,
+          item: &ast::Item,
+          push: &mut FnMut(P<ast::Item>)) {
+    let trait_def = TraitDef {
+        span: span,
+        attributes: vec![],
+        path: Path::new(vec!["TotalSum"]),
+        additional_bounds: vec![],
+        generics: LifetimeBounds::empty(),
+        associated_types: vec![],
+        methods: vec![
+            MethodDef {
+                name: "total_sum",
+                generics: LifetimeBounds::empty(),
+                explicit_self: borrowed_explicit_self(),
+                args: vec![],
+                ret_ty: Literal(Path::new_local("isize")),
+                attributes: vec![],
+                combine_substructure: combine_substructure(box |cx, span, substr| {
+                    let zero = cx.expr_int(span, 0);
+                    cs_fold(false,
+                            |cx, span, subexpr, field, _| {
+                                cx.expr_binary(span, ast::BiAdd, subexpr,
+                                    cx.expr_method_call(span, field,
+                                        token::str_to_ident("total_sum"), vec![]))
+                            },
+                            zero,
+                            box |cx, span, _, _| { cx.span_bug(span, "wtf??"); },
+                            cx, span, substr)
+                }),
+            },
+        ],
+    };
+
+    trait_def.expand(cx, mitem, item, |i| push(i))
+}
diff --git a/src/test/auxiliary/internal_unstable.rs b/src/test/auxiliary/internal_unstable.rs
new file mode 100644 (file)
index 0000000..3d59b8e
--- /dev/null
@@ -0,0 +1,60 @@
+// Copyright 2015 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(staged_api, allow_internal_unstable)]
+#![staged_api]
+#![stable(feature = "stable", since = "1.0.0")]
+
+#[unstable(feature = "function")]
+pub fn unstable() {}
+
+
+#[stable(feature = "stable", since = "1.0.0")]
+pub struct Foo {
+    #[unstable(feature = "struct_field")]
+    pub x: u8
+}
+
+#[allow_internal_unstable]
+#[macro_export]
+macro_rules! call_unstable_allow {
+    () => { $crate::unstable() }
+}
+
+#[allow_internal_unstable]
+#[macro_export]
+macro_rules! construct_unstable_allow {
+    ($e: expr) => {
+        $crate::Foo { x: $e }
+    }
+}
+
+#[allow_internal_unstable]
+#[macro_export]
+macro_rules! pass_through_allow {
+    ($e: expr) => { $e }
+}
+
+#[macro_export]
+macro_rules! call_unstable_noallow {
+    () => { $crate::unstable() }
+}
+
+#[macro_export]
+macro_rules! construct_unstable_noallow {
+    ($e: expr) => {
+        $crate::Foo { x: $e }
+    }
+}
+
+#[macro_export]
+macro_rules! pass_through_noallow {
+    ($e: expr) => { $e }
+}
diff --git a/src/test/auxiliary/lint_for_crate.rs b/src/test/auxiliary/lint_for_crate.rs
new file mode 100644 (file)
index 0000000..1be37ce
--- /dev/null
@@ -0,0 +1,43 @@
+// Copyright 2015 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.
+
+// force-host
+
+#![feature(plugin_registrar)]
+#![feature(box_syntax)]
+
+extern crate syntax;
+#[macro_use] extern crate rustc;
+
+use syntax::{ast, attr};
+use rustc::lint::{Context, LintPass, LintPassObject, LintArray};
+use rustc::plugin::Registry;
+
+declare_lint!(CRATE_NOT_OKAY, Warn, "crate not marked with #![crate_okay]");
+
+struct Pass;
+
+impl LintPass for Pass {
+    fn get_lints(&self) -> LintArray {
+        lint_array!(CRATE_NOT_OKAY)
+    }
+
+    fn check_crate(&mut self, cx: &Context, krate: &ast::Crate) {
+        if !attr::contains_name(&krate.attrs, "crate_okay") {
+            cx.span_lint(CRATE_NOT_OKAY, krate.span,
+                         "crate is not marked with #![crate_okay]");
+        }
+    }
+}
+
+#[plugin_registrar]
+pub fn plugin_registrar(reg: &mut Registry) {
+    reg.register_lint_pass(box Pass as LintPassObject);
+}
old mode 100755 (executable)
new mode 100644 (file)
index 01bfbd3dbceb6f65e52de3217a9773bac356455f..d9afc1df28ebf79348ec3bb8255a3d803ba78519 100644 (file)
@@ -36,10 +36,12 @@ pub fn plugin_registrar(reg: &mut Registry) {
     reg.register_macro("identity", expand_identity);
     reg.register_syntax_extension(
         token::intern("into_foo"),
-        Modifier(box expand_into_foo));
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        Modifier(Box::new(expand_into_foo)));
     reg.register_syntax_extension(
         token::intern("into_multi_foo"),
-        MultiModifier(box expand_into_foo_multi));
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        MultiModifier(Box::new(expand_into_foo_multi)));
 }
 
 fn expand_make_a_1(cx: &mut ExtCtxt, sp: Span, tts: &[TokenTree])
index 9c72cb1a6800ad7b25e62f098c2dafad4e4907cf..aaeccc6e89883865bdbdb5607523f9d6ce369f0c 100644 (file)
@@ -11,5 +11,5 @@
 #![crate_type = "dylib"]
 #[macro_export]
 macro_rules! reexported {
-    () => ( 3_usize )
+    () => ( 3 )
 }
index 1775bbf4af21f635ce32c5d6434d9daae132ded1..30b18a3618ffa09174f70bcb64757472a20a5934 100644 (file)
@@ -46,5 +46,6 @@ fn expand<'cx>(&self,
 pub fn plugin_registrar(reg: &mut Registry) {
     let args = reg.args().clone();
     reg.register_syntax_extension(token::intern("plugin_args"),
-        NormalTT(box Expander { args: args, }, None));
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        NormalTT(Box::new(Expander { args: args, }), None, false));
 }
diff --git a/src/test/auxiliary/procedural_mbe_matching.rs b/src/test/auxiliary/procedural_mbe_matching.rs
new file mode 100644 (file)
index 0000000..d9a2b06
--- /dev/null
@@ -0,0 +1,69 @@
+// Copyright 2015 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.
+
+// force-host
+
+#![crate_type="dylib"]
+#![feature(plugin_registrar, quote)]
+
+extern crate syntax;
+extern crate rustc;
+
+use syntax::codemap::Span;
+use syntax::parse::token::{self, str_to_ident, NtExpr, NtPat};
+use syntax::ast::{TokenTree, TtToken, Pat};
+use syntax::ext::base::{ExtCtxt, MacResult, DummyResult, MacEager};
+use syntax::ext::build::AstBuilder;
+use syntax::ext::tt::macro_parser::{MatchedSeq, MatchedNonterminal};
+use syntax::ext::tt::macro_parser::{Success, Failure, Error};
+use syntax::ptr::P;
+use rustc::plugin::Registry;
+
+fn expand_mbe_matches(cx: &mut ExtCtxt, sp: Span, args: &[TokenTree])
+        -> Box<MacResult + 'static> {
+
+    let mbe_matcher = quote_matcher!(cx, $matched:expr, $($pat:pat)|+);
+
+    let mac_expr = match TokenTree::parse(cx, &mbe_matcher[..], args) {
+        Success(map) => {
+            match (&*map[str_to_ident("matched")], &*map[str_to_ident("pat")]) {
+                (&MatchedNonterminal(NtExpr(ref matched_expr)),
+                 &MatchedSeq(ref pats, seq_sp)) => {
+                    let pats: Vec<P<Pat>> = pats.iter().map(|pat_nt|
+                        if let &MatchedNonterminal(NtPat(ref pat)) = &**pat_nt {
+                            pat.clone()
+                        } else {
+                            unreachable!()
+                        }
+                    ).collect();
+                    let arm = cx.arm(seq_sp, pats, cx.expr_bool(seq_sp, true));
+
+                    quote_expr!(cx,
+                        match $matched_expr {
+                            $arm
+                            _ => false
+                        }
+                    )
+                }
+                _ => unreachable!()
+            }
+        }
+        Failure(_, s) | Error(_, s) => {
+            panic!("expected Success, but got Error/Failure: {}", s);
+        }
+    };
+
+    MacEager::expr(mac_expr)
+}
+
+#[plugin_registrar]
+pub fn plugin_registrar(reg: &mut Registry) {
+    reg.register_macro("matches", expand_mbe_matches);
+}
index e5c4211110558f21adb45c51e2d07be93a504551..0ea7c0005707defad9aa5a93cbb278a2f64d7c80 100644 (file)
@@ -47,7 +47,7 @@ fn expand_rn(cx: &mut ExtCtxt, sp: Span, args: &[TokenTree])
     };
 
     let mut text = &*text;
-    let mut total = 0_usize;
+    let mut total = 0;
     while !text.is_empty() {
         match NUMERALS.iter().find(|&&(rn, _)| text.starts_with(rn)) {
             Some(&(rn, val)) => {
diff --git a/src/test/auxiliary/typeck-default-trait-impl-cross-crate-coherence-lib.rs b/src/test/auxiliary/typeck-default-trait-impl-cross-crate-coherence-lib.rs
new file mode 100644 (file)
index 0000000..506e7a0
--- /dev/null
@@ -0,0 +1,19 @@
+// Copyright 2015 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(optin_builtin_traits)]
+#![crate_type = "rlib"]
+
+use std::marker::MarkerTrait;
+
+pub trait DefaultedTrait : MarkerTrait { }
+impl DefaultedTrait for .. { }
+
+pub struct Something<T> { t: T }
index a5178c03443f796bff07ebc61cdb2785bf974657..26925a350676491d09bb2ceb64dbd0c8658bc064 100644 (file)
@@ -14,9 +14,9 @@
 
 #[inline]
 pub fn has_closures() -> uint {
-    let x = 1_usize;
+    let x = 1;
     let mut f = move || x;
-    let y = 1_usize;
+    let y = 1;
     let g = || y;
     f() + g()
 }
index 53c52ae3019f015a11204a29d1132b145fb0b4de..de88c7733b379b87e7edf7996e4a434d26b41b95 100644 (file)
@@ -49,7 +49,7 @@ fn new() -> Noise2DContext {
             *x = random_gradient(&mut rng);
         }
 
-        let mut permutations = [0i32; 256];
+        let mut permutations = [0; 256];
         for (i, x) in permutations.iter_mut().enumerate() {
             *x = i as i32;
         }
index 73e7c8eb073d1884d23be37a9c5de2fea9417489..4a8bb24270d7fe7b79d7de42234ef56b274f084c 100644 (file)
@@ -145,7 +145,7 @@ fn creature(
     to_rendezvous: Sender<CreatureInfo>,
     to_rendezvous_log: Sender<String>
 ) {
-    let mut creatures_met = 0i32;
+    let mut creatures_met = 0;
     let mut evil_clones_met = 0;
     let mut rendezvous = from_rendezvous.iter();
 
index f7de935d08fdd3b67fcfc13d264a66154d48a8bf..3688c224a7df4b5aacd9cd5b6018270ff92af224 100644 (file)
@@ -91,7 +91,7 @@ fn new(n: u32) -> Perm {
     }
 
     fn get(&mut self, mut idx: i32) -> P {
-        let mut pp = [0u8; 16];
+        let mut pp = [0; 16];
         self.permcount = idx as u32;
         for (i, place) in self.perm.p.iter_mut().enumerate() {
             *place = i as i32 + 1;
@@ -183,7 +183,7 @@ fn main() {
     let n = std::env::args()
         .nth(1)
         .and_then(|arg| arg.parse().ok())
-        .unwrap_or(2i32);
+        .unwrap_or(2);
 
     let (checksum, maxflips) = fannkuch(n);
     println!("{}\nPfannkuchen({}) = {}", checksum, n, maxflips);
index 277c3ee73dff1aa8693eb4154292a13d85c8822a..9cee75757aa1c13a6805e00424a950173ccfa6d2 100644 (file)
@@ -121,7 +121,7 @@ fn new(alu: &'static str, w: &'a mut W) -> RepeatFasta<'a, W> {
 
     fn make(&mut self, n: usize) -> IoResult<()> {
         let alu_len = self.alu.len();
-        let mut buf = repeat(0u8).take(alu_len + LINE_LEN).collect::<Vec<_>>();
+        let mut buf = repeat(0).take(alu_len + LINE_LEN).collect::<Vec<_>>();
         let alu: &[u8] = self.alu.as_bytes();
 
         copy_memory(&mut buf, alu);
index 2c640c4b092556cab96df76819b992575a0fbf66..e15f9d99ff691fa4f3f92d49633e7d0cba306541 100644 (file)
@@ -89,7 +89,7 @@ fn make_fasta<W: Writer, I: Iterator<Item=u8>>(
     -> std::old_io::IoResult<()>
 {
     try!(wr.write(header.as_bytes()));
-    let mut line = [0u8; LINE_LENGTH + 1];
+    let mut line = [0; LINE_LENGTH + 1];
     while n > 0 {
         let nb = min(LINE_LENGTH, n);
         for i in 0..nb {
index f239a0d78d1ddd9875bb6c873d5f5f07e0aeb6b4..9e5885041b66b98875006e13b6b4238322c1c8d1 100644 (file)
@@ -78,11 +78,11 @@ fn push_char(&self, c: u8) -> Code {
     }
 
     fn rotate(&self, c: u8, frame: usize) -> Code {
-        Code(self.push_char(c).hash() & ((1u64 << (2 * frame)) - 1))
+        Code(self.push_char(c).hash() & ((1 << (2 * frame)) - 1))
     }
 
     fn pack(string: &str) -> Code {
-        string.bytes().fold(Code(0u64), |a, b| a.push_char(b))
+        string.bytes().fold(Code(0), |a, b| a.push_char(b))
     }
 
     fn unpack(&self, frame: usize) -> String {
@@ -146,7 +146,7 @@ fn new() -> Table {
     fn search_remainder<C:TableCallback>(item: &mut Entry, key: Code, c: C) {
         match item.next {
             None => {
-                let mut entry = box Entry {
+                let mut entry: Box<_> = box Entry {
                     code: key,
                     count: 0,
                     next: None,
@@ -170,7 +170,7 @@ fn lookup<C:TableCallback>(&mut self, key: Code, c: C) {
 
         {
             if self.items[index as usize].is_none() {
-                let mut entry = box Entry {
+                let mut entry: Box<_> = box Entry {
                     code: key,
                     count: 0,
                     next: None,
index a94fe0ccd959848a364d890eef0a1058128ad958..79a5245a40849bc8842324917e8ed84b7c1ae110 100644 (file)
@@ -169,7 +169,7 @@ fn make_masks() -> Vec<Vec<Vec<u64> > > {
         .map(|(id, p)| transform(p, id != 3))
         .collect();
 
-    (0i32..50).map(|yx| {
+    (0..50).map(|yx| {
         transforms.iter().enumerate().map(|(id, t)| {
             t.iter().filter_map(|p| mask(yx / 5, yx % 5, id, p)).collect()
         }).collect()
@@ -211,7 +211,7 @@ fn filter_masks(masks: &mut Vec<Vec<Vec<u64>>>) {
 
 // Gets the identifier of a mask.
 fn get_id(m: u64) -> u8 {
-    for id in 0u8..10 {
+    for id in 0..10 {
         if m & (1 << (id + 50) as usize) != 0 {return id;}
     }
     panic!("{:016x} does not have a valid identifier", m);
index 40e1e7d2b76b02614a211db532013b8a9a0b1452..9a82614510eb265431596d82b1d34ec472e7a203 100644 (file)
@@ -60,7 +60,7 @@ pub fn read(reader: &mut BufRead) -> Sudoku {
         reader.read_line(&mut s).unwrap();
         assert_eq!(s, "9,9\n");
 
-        let mut g = repeat(vec![0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8, 0u8])
+        let mut g = repeat(vec![0, 0, 0, 0, 0, 0, 0, 0, 0])
                           .take(10).collect::<Vec<_>>();
         for line in reader.lines() {
             let line = line.unwrap();
@@ -94,10 +94,10 @@ pub fn write(&self, writer: &mut Write) {
     // solve sudoku grid
     pub fn solve(&mut self) {
         let mut work: Vec<(u8, u8)> = Vec::new(); /* queue of uncolored fields */
-        for row in 0u8..9u8 {
-            for col in 0u8..9u8 {
+        for row in 0..9 {
+            for col in 0..9 {
                 let color = self.grid[row as usize][col as usize];
-                if color == 0u8 {
+                if color == 0 {
                     work.push((row, col));
                 }
             }
@@ -122,9 +122,9 @@ pub fn solve(&mut self) {
     }
 
     fn next_color(&mut self, row: u8, col: u8, start_color: u8) -> bool {
-        if start_color < 10u8 {
+        if start_color < 10 {
             // colors not yet used
-            let mut avail = box Colors::new(start_color);
+            let mut avail: Box<_> = box Colors::new(start_color);
 
             // drop colors already in use in neighbourhood
             self.drop_colors(&mut *avail, row, col);
@@ -132,15 +132,15 @@ fn next_color(&mut self, row: u8, col: u8, start_color: u8) -> bool {
             // find first remaining color that is available
             let next = avail.next();
             self.grid[row as usize][col as usize] = next;
-            return 0u8 != next;
+            return 0 != next;
         }
-        self.grid[row as usize][col as usize] = 0u8;
+        self.grid[row as usize][col as usize] = 0;
         return false;
     }
 
     // find colors available in neighbourhood of (row, col)
     fn drop_colors(&mut self, avail: &mut Colors, row: u8, col: u8) {
-        for idx in 0u8..9u8 {
+        for idx in 0..9 {
             /* check same column fields */
             avail.remove(self.grid[idx as usize][col as usize]);
             /* check same row fields */
@@ -148,10 +148,10 @@ fn drop_colors(&mut self, avail: &mut Colors, row: u8, col: u8) {
         }
 
         // check same block fields
-        let row0 = (row / 3u8) * 3u8;
-        let col0 = (col / 3u8) * 3u8;
-        for alt_row in row0..row0 + 3u8 {
-            for alt_col in col0..col0 + 3u8 {
+        let row0 = (row / 3) * 3;
+        let col0 = (col / 3) * 3;
+        for alt_row in row0..row0 + 3 {
+            for alt_col in col0..col0 + 3 {
                 avail.remove(self.grid[alt_row as usize][alt_col as usize]);
             }
         }
@@ -161,29 +161,29 @@ fn drop_colors(&mut self, avail: &mut Colors, row: u8, col: u8) {
 // Stores available colors as simple bitfield, bit 0 is always unset
 struct Colors(u16);
 
-static HEADS: u16 = (1u16 << 10) - 1; /* bits 9..0 */
+static HEADS: u16 = (1 << 10) - 1; /* bits 9..0 */
 
 impl Colors {
     fn new(start_color: u8) -> Colors {
         // Sets bits 9..start_color
-        let tails = !0u16 << start_color as usize;
+        let tails = !0 << start_color as usize;
         return Colors(HEADS & tails);
     }
 
     fn next(&self) -> u8 {
         let Colors(c) = *self;
         let val = c & HEADS;
-        if 0u16 == val {
-            return 0u8;
+        if 0 == val {
+            return 0;
         } else {
             return val.trailing_zeros() as u8
         }
     }
 
     fn remove(&mut self, color: u8) {
-        if color != 0u8 {
+        if color != 0 {
             let Colors(val) = *self;
-            let mask = !(1u16 << color as usize);
+            let mask = !(1 << color as usize);
             *self    = Colors(val & mask);
         }
     }
@@ -191,57 +191,57 @@ fn remove(&mut self, color: u8) {
 
 static DEFAULT_SUDOKU: [[u8;9];9] = [
          /* 0    1    2    3    4    5    6    7    8    */
-  /* 0 */  [0u8, 4u8, 0u8, 6u8, 0u8, 0u8, 0u8, 3u8, 2u8],
-  /* 1 */  [0u8, 0u8, 8u8, 0u8, 2u8, 0u8, 0u8, 0u8, 0u8],
-  /* 2 */  [7u8, 0u8, 0u8, 8u8, 0u8, 0u8, 0u8, 0u8, 0u8],
-  /* 3 */  [0u8, 0u8, 0u8, 5u8, 0u8, 0u8, 0u8, 0u8, 0u8],
-  /* 4 */  [0u8, 5u8, 0u8, 0u8, 0u8, 3u8, 6u8, 0u8, 0u8],
-  /* 5 */  [6u8, 8u8, 0u8, 0u8, 0u8, 0u8, 0u8, 9u8, 0u8],
-  /* 6 */  [0u8, 9u8, 5u8, 0u8, 0u8, 6u8, 0u8, 7u8, 0u8],
-  /* 7 */  [0u8, 0u8, 0u8, 0u8, 4u8, 0u8, 0u8, 6u8, 0u8],
-  /* 8 */  [4u8, 0u8, 0u8, 0u8, 0u8, 7u8, 2u8, 0u8, 3u8]
+  /* 0 */  [0, 4, 0, 6, 0, 0, 0, 3, 2],
+  /* 1 */  [0, 0, 8, 0, 2, 0, 0, 0, 0],
+  /* 2 */  [7, 0, 0, 8, 0, 0, 0, 0, 0],
+  /* 3 */  [0, 0, 0, 5, 0, 0, 0, 0, 0],
+  /* 4 */  [0, 5, 0, 0, 0, 3, 6, 0, 0],
+  /* 5 */  [6, 8, 0, 0, 0, 0, 0, 9, 0],
+  /* 6 */  [0, 9, 5, 0, 0, 6, 0, 7, 0],
+  /* 7 */  [0, 0, 0, 0, 4, 0, 0, 6, 0],
+  /* 8 */  [4, 0, 0, 0, 0, 7, 2, 0, 3]
 ];
 
 #[cfg(test)]
 static DEFAULT_SOLUTION: [[u8;9];9] = [
          /* 0    1    2    3    4    5    6    7    8    */
-  /* 0 */  [1u8, 4u8, 9u8, 6u8, 7u8, 5u8, 8u8, 3u8, 2u8],
-  /* 1 */  [5u8, 3u8, 8u8, 1u8, 2u8, 9u8, 7u8, 4u8, 6u8],
-  /* 2 */  [7u8, 2u8, 6u8, 8u8, 3u8, 4u8, 1u8, 5u8, 9u8],
-  /* 3 */  [9u8, 1u8, 4u8, 5u8, 6u8, 8u8, 3u8, 2u8, 7u8],
-  /* 4 */  [2u8, 5u8, 7u8, 4u8, 9u8, 3u8, 6u8, 1u8, 8u8],
-  /* 5 */  [6u8, 8u8, 3u8, 7u8, 1u8, 2u8, 5u8, 9u8, 4u8],
-  /* 6 */  [3u8, 9u8, 5u8, 2u8, 8u8, 6u8, 4u8, 7u8, 1u8],
-  /* 7 */  [8u8, 7u8, 2u8, 3u8, 4u8, 1u8, 9u8, 6u8, 5u8],
-  /* 8 */  [4u8, 6u8, 1u8, 9u8, 5u8, 7u8, 2u8, 8u8, 3u8]
+  /* 0 */  [1, 4, 9, 6, 7, 5, 8, 3, 2],
+  /* 1 */  [5, 3, 8, 1, 2, 9, 7, 4, 6],
+  /* 2 */  [7, 2, 6, 8, 3, 4, 1, 5, 9],
+  /* 3 */  [9, 1, 4, 5, 6, 8, 3, 2, 7],
+  /* 4 */  [2, 5, 7, 4, 9, 3, 6, 1, 8],
+  /* 5 */  [6, 8, 3, 7, 1, 2, 5, 9, 4],
+  /* 6 */  [3, 9, 5, 2, 8, 6, 4, 7, 1],
+  /* 7 */  [8, 7, 2, 3, 4, 1, 9, 6, 5],
+  /* 8 */  [4, 6, 1, 9, 5, 7, 2, 8, 3]
 ];
 
 #[test]
 fn colors_new_works() {
-    assert_eq!(*Colors::new(1), 1022u16);
-    assert_eq!(*Colors::new(2), 1020u16);
-    assert_eq!(*Colors::new(3), 1016u16);
-    assert_eq!(*Colors::new(4), 1008u16);
-    assert_eq!(*Colors::new(5), 992u16);
-    assert_eq!(*Colors::new(6), 960u16);
-    assert_eq!(*Colors::new(7), 896u16);
-    assert_eq!(*Colors::new(8), 768u16);
-    assert_eq!(*Colors::new(9), 512u16);
+    assert_eq!(*Colors::new(1), 1022);
+    assert_eq!(*Colors::new(2), 1020);
+    assert_eq!(*Colors::new(3), 1016);
+    assert_eq!(*Colors::new(4), 1008);
+    assert_eq!(*Colors::new(5), 992);
+    assert_eq!(*Colors::new(6), 960);
+    assert_eq!(*Colors::new(7), 896);
+    assert_eq!(*Colors::new(8), 768);
+    assert_eq!(*Colors::new(9), 512);
 }
 
 #[test]
 fn colors_next_works() {
-    assert_eq!(Colors(0).next(), 0u8);
-    assert_eq!(Colors(2).next(), 1u8);
-    assert_eq!(Colors(4).next(), 2u8);
-    assert_eq!(Colors(8).next(), 3u8);
-    assert_eq!(Colors(16).next(), 4u8);
-    assert_eq!(Colors(32).next(), 5u8);
-    assert_eq!(Colors(64).next(), 6u8);
-    assert_eq!(Colors(128).next(), 7u8);
-    assert_eq!(Colors(256).next(), 8u8);
-    assert_eq!(Colors(512).next(), 9u8);
-    assert_eq!(Colors(1024).next(), 0u8);
+    assert_eq!(Colors(0).next(), 0);
+    assert_eq!(Colors(2).next(), 1);
+    assert_eq!(Colors(4).next(), 2);
+    assert_eq!(Colors(8).next(), 3);
+    assert_eq!(Colors(16).next(), 4);
+    assert_eq!(Colors(32).next(), 5);
+    assert_eq!(Colors(64).next(), 6);
+    assert_eq!(Colors(128).next(), 7);
+    assert_eq!(Colors(256).next(), 8);
+    assert_eq!(Colors(512).next(), 9);
+    assert_eq!(Colors(1024).next(), 0);
 }
 
 #[test]
@@ -253,7 +253,7 @@ fn colors_remove_works() {
     colors.remove(1);
 
     // THEN
-    assert_eq!(colors.next(), 2u8);
+    assert_eq!(colors.next(), 2);
 }
 
 #[test]
diff --git a/src/test/compile-fail-fulldeps/gated-quote.rs b/src/test/compile-fail-fulldeps/gated-quote.rs
new file mode 100644 (file)
index 0000000..6a5cd88
--- /dev/null
@@ -0,0 +1,50 @@
+// Copyright 2015 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.
+
+// Test that `quote`-related macro are gated by `quote` feature gate.
+
+// (To sanity-check the code, uncomment this.)
+// #![feature(quote)]
+
+// FIXME the error message that is current emitted seems pretty bad.
+
+#![feature(rustc_private)]
+#![allow(dead_code, unused_imports, unused_variables)]
+
+#[macro_use]
+extern crate syntax;
+
+use syntax::ast;
+use syntax::codemap::Span;
+use syntax::parse;
+
+struct ParseSess;
+
+impl ParseSess {
+    fn cfg(&self) -> ast::CrateConfig { loop { } }
+    fn parse_sess<'a>(&'a self) -> &'a parse::ParseSess { loop { } }
+    fn call_site(&self) -> Span { loop { } }
+    fn ident_of(&self, st: &str) -> ast::Ident { loop { } }
+    fn name_of(&self, st: &str) -> ast::Name { loop { } }
+}
+
+pub fn main() {
+    let ecx = &ParseSess;
+    let x = quote_tokens!(ecx, 3);   //~ ERROR macro undefined: 'quote_tokens!'
+    let x = quote_expr!(ecx, 3);     //~ ERROR macro undefined: 'quote_expr!'
+    let x = quote_ty!(ecx, 3);       //~ ERROR macro undefined: 'quote_ty!'
+    let x = quote_method!(ecx, 3);   //~ ERROR macro undefined: 'quote_method!'
+    let x = quote_item!(ecx, 3);     //~ ERROR macro undefined: 'quote_item!'
+    let x = quote_pat!(ecx, 3);      //~ ERROR macro undefined: 'quote_pat!'
+    let x = quote_arm!(ecx, 3);      //~ ERROR macro undefined: 'quote_arm!'
+    let x = quote_stmt!(ecx, 3);     //~ ERROR macro undefined: 'quote_stmt!'
+    let x = quote_matcher!(ecx, 3);  //~ ERROR macro undefined: 'quote_matcher!'
+    let x = quote_attr!(ecx, 3);     //~ ERROR macro undefined: 'quote_attr!'
+}
diff --git a/src/test/compile-fail-fulldeps/issue-15778-fail.rs b/src/test/compile-fail-fulldeps/issue-15778-fail.rs
new file mode 100644 (file)
index 0000000..8c6889f
--- /dev/null
@@ -0,0 +1,18 @@
+// Copyright 2015 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.
+
+// aux-build:lint_for_crate.rs
+// ignore-stage1
+// compile-flags: -D crate-not-okay
+
+#![feature(plugin, custom_attribute)] //~ ERROR crate is not marked with #![crate_okay]
+#![plugin(lint_for_crate)]
+
+pub fn main() { }
index 9b696e05c50df27f5f7c62b341aa113d83ba565b..06fc3db58c1598db6836e14ca4286eb5ac48691e 100644 (file)
@@ -15,6 +15,6 @@
 
 fn main() {
     match () {
-        Trait { x: 42_usize } => () //~ ERROR use of trait `Trait` in a struct pattern
+        Trait { x: 42 } => () //~ ERROR use of trait `Trait` in a struct pattern
     }
 }
index 7111c00d1246aa32dfa7ad3edbcd787f1e4b4f0f..6c9b8f81b2faf6779cb23a297d3f778d59db929a 100644 (file)
@@ -9,14 +9,14 @@
 // except according to those terms.
 
 fn main() {
-    let _x: i32 = [1i32, 2, 3];
+    let _x: i32 = [1, 2, 3];
     //~^ ERROR mismatched types
     //~| expected `i32`
-    //~| found `[i32; 3]`
+    //~| found `[_; 3]`
     //~| expected i32
     //~| found array of 3 elements
 
-    let x: &[i32] = &[1i32, 2, 3];
+    let x: &[i32] = &[1, 2, 3];
     let _y: &i32 = x;
     //~^ ERROR mismatched types
     //~| expected `&i32`
index 01481af817b7e5caa4bc303c4b1742a1db947603..3cb608a9c5ed29e4ba11be0a4a9d2929c59677c4 100644 (file)
@@ -20,8 +20,8 @@ pub fn main() {
     let x: isize;
     let y: isize;
     unsafe {
-        asm!("mov $1, $0" : "=r"(x) : "=r"(5_usize)); //~ ERROR operand constraint contains '='
-        asm!("mov $1, $0" : "=r"(y) : "+r"(5_usize)); //~ ERROR operand constraint contains '+'
+        asm!("mov $1, $0" : "=r"(x) : "=r"(5)); //~ ERROR operand constraint contains '='
+        asm!("mov $1, $0" : "=r"(y) : "+r"(5)); //~ ERROR operand constraint contains '+'
     }
     foo(x);
     foo(y);
index 02d06c4e1bf806adc18ac37dee7f3a2a10192405..43a0ad6b5f6bf71ea08efb88f8439b31972a0d64 100644 (file)
 
 // ignore-android
 
-#![feature(asm)]
+#![feature(asm, rustc_attrs)]
 
 #![allow(dead_code, non_upper_case_globals)]
 
 #[cfg(any(target_arch = "x86",
           target_arch = "x86_64"))]
-pub fn main() {
+#[rustc_error]
+pub fn main() { //~ ERROR compilation successful
     // assignment not dead
     let mut x: isize = 0;
     unsafe {
@@ -33,7 +34,3 @@ pub fn main() {
     }
     assert_eq!(x, 13);
 }
-
-// At least one error is needed so that compilation fails
-#[static_assert]
-static b: bool = false; //~ ERROR static assertion failed
index ff56fb14f7d5753cc2b42845b0fe60482dfcf481..8c8451623d511ee2384a54982d873c064893ae7f 100644 (file)
@@ -21,7 +21,7 @@ pub fn main() {
     x = 1; //~ NOTE prior assignment occurs here
     foo(x);
     unsafe {
-        asm!("mov $1, $0" : "=r"(x) : "r"(5_usize));
+        asm!("mov $1, $0" : "=r"(x) : "r"(5));
         //~^ ERROR re-assignment of immutable variable `x`
     }
     foo(x);
index 17c19c77ab9abd6ebe988e00b0b72132ef849870..9cf43bebe65ab858393f57817450ed8c28f29b1d 100644 (file)
@@ -19,7 +19,7 @@
 pub fn main() {
     let x: isize;
     unsafe {
-        asm!("mov $1, $0" : "r"(x) : "r"(5_usize)); //~ ERROR output operand constraint lacks '='
+        asm!("mov $1, $0" : "r"(x) : "r"(5)); //~ ERROR output operand constraint lacks '='
     }
     foo(x);
 }
index d32ea327d0a8cfceeaec66c6cecffeee40de157a..4518ce36b6da13140019cfdc9a7d5cac12fc25f4 100644 (file)
@@ -15,7 +15,7 @@ struct cat {
 }
 
 impl cat {
-    pub fn speak(&self) { self.meows += 1_usize; }
+    pub fn speak(&self) { self.meows += 1; }
 }
 
 fn cat(in_x : usize, in_y : isize) -> cat {
@@ -26,6 +26,6 @@ fn cat(in_x : usize, in_y : isize) -> cat {
 }
 
 fn main() {
-  let nyan : cat = cat(52_usize, 99);
+  let nyan : cat = cat(52, 99);
   nyan.speak = || println!("meow"); //~ ERROR attempted to take value of method
 }
index 58a8314af211cd581dd2666a0d07f53d2d641614..de315a41361a7900667705cb9eb7882a7c871548 100644 (file)
@@ -11,7 +11,7 @@
 // Tests that a function with a ! annotation always actually fails
 
 fn bad_bang(i: usize) -> ! {
-    return 7_usize; //~ ERROR `return` in a function declared as diverging [E0166]
+    return 7; //~ ERROR `return` in a function declared as diverging [E0166]
 }
 
 fn main() { bad_bang(5); }
index 03c24c2fa3d3e2f15d8eea4caf1f18afaf7fd895..f0ecf31fd10a2532f93c470f1a5ca4aff4bfabd4 100644 (file)
@@ -11,7 +11,7 @@
 // Tests that a function with a ! annotation always actually fails
 
 fn bad_bang(i: usize) -> ! { //~ ERROR computation may converge in a function marked as diverging
-    if i < 0_usize { } else { panic!(); }
+    if i < 0 { } else { panic!(); }
 }
 
 fn main() { bad_bang(5); }
index 7e3c356b87029d0fc7f3169b22ee2160f796a4aa..a9e5c957b89d4735827153a24af639f83f7c058f 100644 (file)
@@ -8,10 +8,10 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-static i: String = 10i32;
+static i: String = 10;
 //~^ ERROR mismatched types
 //~| expected `collections::string::String`
-//~| found `i32`
+//~| found `_`
 //~| expected struct `collections::string::String`
-//~| found i32
+//~| found integral variable
 fn main() { println!("{}", i); }
index a97cf5d41e809493b774a9fef6f1da5abae75c6c..2129d4fbd505578ff2242fc7685c04eaa7e0704c 100644 (file)
@@ -9,7 +9,7 @@
 // except according to those terms.
 
 fn foo<T:'static>() {
-    1_usize.bar::<T>(); //~ ERROR `core::marker::Send` is not implemented
+    1.bar::<T>(); //~ ERROR `core::marker::Send` is not implemented
 }
 
 trait bar {
index 2217cf5e4dacb3ba867db23d7e470020c01644b9..d5dd9e00902f9d40b53fc5cfe1776f254d1c93bf 100644 (file)
@@ -8,6 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// error-pattern:`&&` cannot be applied to type `i32`
+// error-pattern:`&&` cannot be applied to type `_`
 
-fn main() { let x = 1i32 && 2i32; }
+fn main() { let x = 1 && 2; }
index a82aa12dc80c27543b775b21636fbc55e1472717..00f51973a41ad407b6a228b0ea63138a500abc60 100644 (file)
@@ -21,25 +21,25 @@ fn to_fn_mut<A,F:FnMut<A>>(f: F) -> F { f }
 fn main() {
     // By-ref captures
     {
-        let mut x = 0_usize;
+        let mut x = 0;
         let _f = to_fn(|| x = 42); //~ ERROR cannot assign
 
-        let mut y = 0_usize;
+        let mut y = 0;
         let _g = to_fn(|| set(&mut y)); //~ ERROR cannot borrow
 
-        let mut z = 0_usize;
+        let mut z = 0;
         let _h = to_fn_mut(|| { set(&mut z); to_fn(|| z = 42); }); //~ ERROR cannot assign
     }
 
     // By-value captures
     {
-        let mut x = 0_usize;
+        let mut x = 0;
         let _f = to_fn(move || x = 42); //~ ERROR cannot assign
 
-        let mut y = 0_usize;
+        let mut y = 0;
         let _g = to_fn(move || set(&mut y)); //~ ERROR cannot borrow
 
-        let mut z = 0_usize;
+        let mut z = 0;
         let _h = to_fn_mut(move || { set(&mut z); to_fn(move || z = 42); }); //~ ERROR cannot assign
     }
 }
index 40e077bd1b55d5fa17df67aa2937f8e97211765a..b1abbad525356a5ff43f6a894b765ff3d5a20290 100644 (file)
@@ -16,7 +16,7 @@
 struct Bar(isize, isize);
 
 fn main() {
-    let x = (box 1, 2);
+    let x: (Box<_>, _) = (box 1, 2);
     let r = &x.0;
     let y = x; //~ ERROR cannot move out of `x` because it is borrowed
 
index 4d1939be5b9f7350eeeb6772b458d21badf7227d..7913f9ac90300c80f9a54abf4e6dc5a62432fe79 100644 (file)
@@ -23,7 +23,7 @@ fn add(v: &usize, w: usize) -> usize {
 }
 
 fn implicit() {
-    let mut a = box 1;
+    let mut a: Box<_> = box 1;
 
     // Note the danger here:
     //
@@ -36,7 +36,7 @@ fn implicit() {
 }
 
 fn explicit() {
-    let mut a = box 1;
+    let mut a: Box<_> = box 1;
     add(
         &*a,
         rewrite(&mut a)); //~ ERROR cannot borrow
index 9eda3689334c19f4176be63c228ea93157ac9e62..e24d4e87add83613a27f3d3acc7480cd79c84fd7 100644 (file)
@@ -23,7 +23,7 @@ fn add(v: &usize, w: Box<usize>) -> usize {
 }
 
 fn implicit() {
-    let mut a = box 1;
+    let mut a: Box<_> = box 1;
 
     // Note the danger here:
     //
@@ -36,7 +36,7 @@ fn implicit() {
 }
 
 fn explicit() {
-    let mut a = box 1;
+    let mut a: Box<_> = box 1;
     add(
         &*a,
         a); //~ ERROR cannot move
index 794e0fc6e3aba95ab10168acd24d51a96b0d0ffd..3662e23a4122f71da9c7e74be2b7aa23773cb9b6 100644 (file)
@@ -18,7 +18,7 @@ fn foo(&mut self) {
 }
 
 pub fn main() {
-    let a = box A;
+    let a: Box<_> = box A;
     a.foo();
     //~^ ERROR cannot borrow immutable `Box` content `*a` as mutable
 }
index 9c10f01e027557c7e9885d43574a62044cc5f27a..8bbecfd48c6dca78c5b74dd6762f232319edb426 100644 (file)
 use std::collections::HashMap;
 
 fn main() {
-    let tmp;
+    let tmp: Box<_>;
     let mut buggy_map: HashMap<usize, &usize> = HashMap::new();
-    buggy_map.insert(42, &*box 1); //~ ERROR borrowed value does not live long enough
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    buggy_map.insert(42, &*Box::new(1)); //~ ERROR borrowed value does not live long enough
 
     // but it is ok if we use a temporary
     tmp = box 2;
index 648d0d81ffbc0ef28fd99d0da26338f68e6cb177..59514f75a77d8b07bb39f68791677173a108fbd4 100644 (file)
@@ -31,100 +31,100 @@ struct D {
 }
 
 fn copy_after_move() {
-    let a = box A { x: box 0, y: 1 };
+    let a: Box<_> = box A { x: box 0, y: 1 };
     let _x = a.x;
     let _y = a.y; //~ ERROR use of moved
     //~^^ NOTE `a` moved here (through moving `a.x`)
 }
 
 fn move_after_move() {
-    let a = box B { x: box 0, y: box 1 };
+    let a: Box<_> = box B { x: box 0, y: box 1 };
     let _x = a.x;
     let _y = a.y; //~ ERROR use of moved
     //~^^ NOTE `a` moved here (through moving `a.x`)
 }
 
 fn borrow_after_move() {
-    let a = box A { x: box 0, y: 1 };
+    let a: Box<_> = box A { x: box 0, y: 1 };
     let _x = a.x;
     let _y = &a.y; //~ ERROR use of moved
     //~^^ NOTE `a` moved here (through moving `a.x`)
 }
 
 fn move_after_borrow() {
-    let a = box B { x: box 0, y: box 1 };
+    let a: Box<_> = box B { x: box 0, y: box 1 };
     let _x = &a.x;
     let _y = a.y; //~ ERROR cannot move
 }
 
 fn copy_after_mut_borrow() {
-    let mut a = box A { x: box 0, y: 1 };
+    let mut a: Box<_> = box A { x: box 0, y: 1 };
     let _x = &mut a.x;
     let _y = a.y; //~ ERROR cannot use
 }
 
 fn move_after_mut_borrow() {
-    let mut a = box B { x: box 0, y: box 1 };
+    let mut a: Box<_> = box B { x: box 0, y: box 1 };
     let _x = &mut a.x;
     let _y = a.y; //~ ERROR cannot move
 }
 
 fn borrow_after_mut_borrow() {
-    let mut a = box A { x: box 0, y: 1 };
+    let mut a: Box<_> = box A { x: box 0, y: 1 };
     let _x = &mut a.x;
     let _y = &a.y; //~ ERROR cannot borrow
 }
 
 fn mut_borrow_after_borrow() {
-    let mut a = box A { x: box 0, y: 1 };
+    let mut a: Box<_> = box A { x: box 0, y: 1 };
     let _x = &a.x;
     let _y = &mut a.y; //~ ERROR cannot borrow
 }
 
 fn copy_after_move_nested() {
-    let a = box C { x: box A { x: box 0, y: 1 }, y: 2 };
+    let a: Box<_> = box C { x: box A { x: box 0, y: 1 }, y: 2 };
     let _x = a.x.x;
     let _y = a.y; //~ ERROR use of collaterally moved
 }
 
 fn move_after_move_nested() {
-    let a = box D { x: box A { x: box 0, y: 1 }, y: box 2 };
+    let a: Box<_> = box D { x: box A { x: box 0, y: 1 }, y: box 2 };
     let _x = a.x.x;
     let _y = a.y; //~ ERROR use of collaterally moved
 }
 
 fn borrow_after_move_nested() {
-    let a = box C { x: box A { x: box 0, y: 1 }, y: 2 };
+    let a: Box<_> = box C { x: box A { x: box 0, y: 1 }, y: 2 };
     let _x = a.x.x;
     let _y = &a.y; //~ ERROR use of collaterally moved
 }
 
 fn move_after_borrow_nested() {
-    let a = box D { x: box A { x: box 0, y: 1 }, y: box 2 };
+    let a: Box<_> = box D { x: box A { x: box 0, y: 1 }, y: box 2 };
     let _x = &a.x.x;
     let _y = a.y; //~ ERROR cannot move
 }
 
 fn copy_after_mut_borrow_nested() {
-    let mut a = box C { x: box A { x: box 0, y: 1 }, y: 2 };
+    let mut a: Box<_> = box C { x: box A { x: box 0, y: 1 }, y: 2 };
     let _x = &mut a.x.x;
     let _y = a.y; //~ ERROR cannot use
 }
 
 fn move_after_mut_borrow_nested() {
-    let mut a = box D { x: box A { x: box 0, y: 1 }, y: box 2 };
+    let mut a: Box<_> = box D { x: box A { x: box 0, y: 1 }, y: box 2 };
     let _x = &mut a.x.x;
     let _y = a.y; //~ ERROR cannot move
 }
 
 fn borrow_after_mut_borrow_nested() {
-    let mut a = box C { x: box A { x: box 0, y: 1 }, y: 2 };
+    let mut a: Box<_> = box C { x: box A { x: box 0, y: 1 }, y: 2 };
     let _x = &mut a.x.x;
     let _y = &a.y; //~ ERROR cannot borrow
 }
 
 fn mut_borrow_after_borrow_nested() {
-    let mut a = box C { x: box A { x: box 0, y: 1 }, y: 2 };
+    let mut a: Box<_> = box C { x: box A { x: box 0, y: 1 }, y: 2 };
     let _x = &a.x.x;
     let _y = &mut a.y; //~ ERROR cannot borrow
 }
index 9ea5fbbdb1af08e72e83750025961b6652fbfe72..7626f354eb46415a13575402bf74991f11b65bc5 100644 (file)
@@ -11,7 +11,6 @@
 // Ensure that invoking a closure counts as a unique immutable borrow
 
 #![feature(unboxed_closures)]
-#![feature(box_syntax)]
 
 type Fn<'a> = Box<FnMut() + 'a>;
 
@@ -19,11 +18,12 @@ struct Test<'a> {
     f: Box<FnMut() + 'a>
 }
 
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 fn call<F>(mut f: F) where F: FnMut(Fn) {
-    f(box || {
+    f(Box::new(|| {
     //~^ ERROR: cannot borrow `f` as mutable more than once
-        f(box || {})
-    });
+        f((Box::new(|| {})))
+    }));
 }
 
 fn test1() {
@@ -58,11 +58,12 @@ fn test6() {
 fn test7() {
     fn foo<F>(_: F) where F: FnMut(Box<FnMut(isize)>, isize) {}
     let mut f = |g: Box<FnMut(isize)>, b: isize| {};
-    f(box |a| {
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    f(Box::new(|a| {
         foo(f);
         //~^ ERROR cannot move `f` into closure because it is borrowed
         //~| ERROR cannot move out of captured outer variable in an `FnMut` closure
-    }, 3);
+    }), 3);
 }
 
 fn main() {}
index 851b11fac2b9d1949f9eb09f3e5a15a82c5afe33..aaa0766121543fc5c4b0f2a000fb424b2d2ff106 100644 (file)
@@ -52,7 +52,7 @@ fn e() {
 }
 
 fn f() {
-    let mut x = box 3;
+    let mut x: Box<_> = box 3;
     let c1 = || get(&*x);
     *x = 5; //~ ERROR cannot assign
 }
@@ -62,7 +62,7 @@ struct Foo {
         f: Box<isize>
     }
 
-    let mut x = box Foo { f: box 3 };
+    let mut x: Box<_> = box Foo { f: box 3 };
     let c1 = || get(&*x.f);
     *x.f = 5; //~ ERROR cannot assign to `*x.f`
 }
@@ -72,7 +72,7 @@ struct Foo {
         f: Box<isize>
     }
 
-    let mut x = box Foo { f: box 3 };
+    let mut x: Box<_> = box Foo { f: box 3 };
     let c1 = || get(&*x.f);
     let c2 = || *x.f = 5; //~ ERROR cannot borrow `x` as mutable
 }
index 8ab4e257b0626d35a76eca6239519d5e2072e8f4..29546abe0bb20bb66b40b284ea23a686840e61af 100644 (file)
@@ -50,7 +50,7 @@ struct Foo {
         f: Box<isize>
     }
 
-    let mut x = box Foo { f: box 3 };
+    let mut x: Box<_> = box Foo { f: box 3 };
     let c1 = to_fn_mut(|| set(&mut *x.f));
     let c2 = to_fn_mut(|| set(&mut *x.f));
     //~^ ERROR cannot borrow `x` as mutable more than once
index 32cd364d1f2d644ad18917d46514eeaa30e795b1..bb474342a7c6f5bcb61fbab51b66e4ba8105f189 100644 (file)
@@ -25,7 +25,7 @@ fn drop(&mut self) {
 }
 
 fn main() {
-  let mut ptr = box Foo { x: 0 };
+  let mut ptr: Box<_> = box Foo { x: 0 };
   let mut test = |foo: &Foo| {
     ptr = box Foo { x: ptr.x + 1 };
   };
index 492fd4a2c849a8ba9d9f7a9c2c1de65fbbe2b32c..b6b260065557a16baac6f2de819475bba376c8a4 100644 (file)
@@ -28,7 +28,7 @@ fn main() {
     for &a in &f.a {  //~ ERROR cannot move out
     }
 
-    let x = Some(box 1);
+    let x: Option<Box<_>> = Some(box 1);
     for &a in x.iter() {    //~ ERROR cannot move out
     }
 }
index cc562afa9f818ecbe89946d1c0d64378020f1a69..deae1fbad20c8484f65d2d6b47b9d7c3ac78b71f 100644 (file)
@@ -18,7 +18,7 @@ struct B<'a> { a: Box<&'a mut isize> }
 
 fn borrow_in_var_from_var() {
     let mut x: isize = 1;
-    let y = box &mut x;
+    let y: Box<_> = box &mut x;
     let p = &y;
     let q = &***p;
     **y = 2; //~ ERROR cannot assign to `**y` because it is borrowed
@@ -28,7 +28,7 @@ fn borrow_in_var_from_var() {
 
 fn borrow_in_var_from_field() {
     let mut x = A { a: 1 };
-    let y = box &mut x.a;
+    let y: Box<_> = box &mut x.a;
     let p = &y;
     let q = &***p;
     **y = 2; //~ ERROR cannot assign to `**y` because it is borrowed
index 0c717d2ee5ffff4a9a194c1cdcbed3187aef57b3..0e1712137d34e27c554732cd7aa48e869ef3ee16 100644 (file)
@@ -11,7 +11,7 @@
 #![feature(box_syntax)]
 
 fn main() {
-    let x = Some(box 1);
+    let x: Option<Box<_>> = Some(box 1);
     match x {
       Some(ref _y) => {
         let _a = x; //~ ERROR cannot move
index b4e5ae1c25bf799b13c00d3048d52e17c96a341c..a389a4a5593f07ca879ecbb53f9b6d200636da51 100644 (file)
@@ -11,7 +11,7 @@
 #![feature(box_syntax)]
 
 fn main() {
-    let x = Some(box 1);
+    let x: Option<Box<_>> = Some(box 1);
     match x {
       Some(ref y) => {
         let _b = *y; //~ ERROR cannot move out
index ca8efb5dc967d7f5286982ec741c73a7b20e62c3..0efe8622621785c0e762210c11463bd3b51db05c 100644 (file)
@@ -30,7 +30,7 @@ fn pre_freeze_cond() {
     // In this instance, the freeze is conditional and starts before
     // the mut borrow.
 
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     let _w;
     if cond() {
         _w = &v;
@@ -42,7 +42,7 @@ fn pre_freeze_else() {
     // In this instance, the freeze and mut borrow are on separate sides
     // of the if.
 
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     let _w;
     if cond() {
         _w = &v;
index 5418a531fe68a19dd7e74652ddba41f46cb19331..f841fedf75af913cd03a0e26fe7f17c3b3dfaf5b 100644 (file)
@@ -28,7 +28,7 @@ fn inc(v: &mut Box<isize>) {
 fn loop_overarching_alias_mut() {
     // In this instance, the borrow encompasses the entire loop.
 
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     let mut x = &mut v;
     **x += 1;
     loop {
@@ -39,7 +39,7 @@ fn loop_overarching_alias_mut() {
 fn block_overarching_alias_mut() {
     // In this instance, the borrow encompasses the entire closure call.
 
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     let mut x = &mut v;
     for _ in 0..3 {
         borrow(&*v); //~ ERROR cannot borrow
@@ -50,8 +50,8 @@ fn block_overarching_alias_mut() {
 fn loop_aliased_mut() {
     // In this instance, the borrow is carried through the loop.
 
-    let mut v = box 3;
-    let mut w = box 4;
+    let mut v: Box<_> = box 3;
+    let mut w: Box<_> = box 4;
     let mut _x = &w;
     loop {
         borrow_mut(&mut *v); //~ ERROR cannot borrow
@@ -62,8 +62,8 @@ fn loop_aliased_mut() {
 fn while_aliased_mut() {
     // In this instance, the borrow is carried through the loop.
 
-    let mut v = box 3;
-    let mut w = box 4;
+    let mut v: Box<_> = box 3;
+    let mut w: Box<_> = box 4;
     let mut _x = &w;
     while cond() {
         borrow_mut(&mut *v); //~ ERROR cannot borrow
@@ -75,8 +75,8 @@ fn while_aliased_mut() {
 fn loop_aliased_mut_break() {
     // In this instance, the borrow is carried through the loop.
 
-    let mut v = box 3;
-    let mut w = box 4;
+    let mut v: Box<_> = box 3;
+    let mut w: Box<_> = box 4;
     let mut _x = &w;
     loop {
         borrow_mut(&mut *v);
@@ -89,8 +89,8 @@ fn loop_aliased_mut_break() {
 fn while_aliased_mut_break() {
     // In this instance, the borrow is carried through the loop.
 
-    let mut v = box 3;
-    let mut w = box 4;
+    let mut v: Box<_> = box 3;
+    let mut w: Box<_> = box 4;
     let mut _x = &w;
     while cond() {
         borrow_mut(&mut *v);
@@ -101,8 +101,8 @@ fn while_aliased_mut_break() {
 }
 
 fn while_aliased_mut_cond(cond: bool, cond2: bool) {
-    let mut v = box 3;
-    let mut w = box 4;
+    let mut v: Box<_> = box 3;
+    let mut w: Box<_> = box 4;
     let mut x = &mut w;
     while cond {
         **x += 1;
index 177976c15f0f46831762f717273b6f699c3227fd..6da8f088b3279005474b3368b9d6cd4e5f745784 100644 (file)
@@ -29,7 +29,7 @@ fn inc(v: &mut Box<isize>) {
 fn pre_freeze() {
     // In this instance, the freeze starts before the mut borrow.
 
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     let _w = &v;
     borrow_mut(&mut *v); //~ ERROR cannot borrow
 }
@@ -37,7 +37,7 @@ fn pre_freeze() {
 fn post_freeze() {
     // In this instance, the const alias starts after the borrow.
 
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     borrow_mut(&mut *v);
     let _w = &v;
 }
index 7f676f5166f7f77fb77129553870257313bc66ac..57b584a89599f0a88512b043d7ec66dc34047eff 100644 (file)
@@ -17,7 +17,7 @@ fn borrow<F>(v: &isize, f: F) where F: FnOnce(&isize) {
 }
 
 fn box_imm() {
-    let v = box 3;
+    let v: Box<_> = box 3;
     let _w = &v;
     thread::spawn(move|| {
         println!("v={}", *v);
@@ -26,7 +26,7 @@ fn box_imm() {
 }
 
 fn box_imm_explicit() {
-    let v = box 3;
+    let v: Box<_> = box 3;
     let _w = &v;
     thread::spawn(move|| {
         println!("v={}", *v);
index a52a4484b20d123440a7c602d20c1c8d9ed6eee9..32d8088549d4fb9fd113ffe82313bee07ab7c4d0 100644 (file)
@@ -15,7 +15,7 @@ fn borrow<F>(v: &isize, f: F) where F: FnOnce(&isize) {
 }
 
 fn box_imm() {
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     borrow(&*v,
            |w| { //~ ERROR cannot borrow `v` as mutable
             v = box 4;
index a1708e7f497286c81a4d6007aafb13c7ea4420c0..bad521210439ff2f68f3773bea6e627feeb15ad6 100644 (file)
@@ -14,7 +14,7 @@ fn to_fn_mut<A,F:FnMut<A>>(f: F) -> F { f }
 fn to_fn_once<A,F:FnOnce<A>>(f: F) -> F { f }
 
 pub fn main() {
-    let bar = box 3;
+    let bar: Box<_> = box 3;
     let _g = to_fn_mut(|| {
         let _h = to_fn_once(move || -> isize { *bar }); //~ ERROR cannot move out of
     });
index 2d82c8be519712feea5960cd3ee185ed1def58dc..e4b9fb2671124d64e3dc20d8fd98840b6c0957a8 100644 (file)
@@ -17,7 +17,7 @@ enum Foo {
 }
 
 fn blah() {
-    let f = &Foo::Foo1(box 1u32, box 2u32);
+    let f = &Foo::Foo1(box 1, box 2);
     match *f {             //~ ERROR cannot move out of
         Foo::Foo1(num1,         //~ NOTE attempting to move value to here
                   num2) => (),  //~ NOTE and here
index 3d8d599970f2c57715347b74d249b8e1134ec7fe..c02c6a7151428fbedb7e79b8e3b2ff89cde5308d 100644 (file)
@@ -14,7 +14,7 @@
 #![feature(box_syntax)]
 
 fn main() {
-    let a = box box 2;
+    let a: Box<Box<_>> = box box 2;
     let b = &a;
 
     let z = *a; //~ ERROR: cannot move out of `*a` because it is borrowed
index 43bf3f25d1ab9ff4d8380bb8750cb7f857b62679..c46bcbb32b9cf13bd796b10637762629bd7af739 100644 (file)
@@ -15,7 +15,7 @@ fn call_f<F:FnOnce() -> isize>(f: F) -> isize {
 }
 
 fn main() {
-    let t = box 3;
+    let t: Box<_> = box 3;
 
     call_f(move|| { *t + 1 });
     call_f(move|| { *t + 1 }); //~ ERROR capture of moved value
index 9db05d76284e8d23cdc1660fb9e834e3310a9f2f..f417416e7b53e6c860c13f70722845dc9573fa8a 100644 (file)
@@ -15,9 +15,9 @@
 fn borrow<T>(_: &T) { }
 
 fn different_vars_after_borrows() {
-    let x1 = box 1;
+    let x1: Box<_> = box 1;
     let p1 = &x1;
-    let x2 = box 2;
+    let x2: Box<_> = box 2;
     let p2 = &x2;
     thread::spawn(move|| {
         drop(x1); //~ ERROR cannot move `x1` into closure because it is borrowed
@@ -28,9 +28,9 @@ fn different_vars_after_borrows() {
 }
 
 fn different_vars_after_moves() {
-    let x1 = box 1;
+    let x1: Box<_> = box 1;
     drop(x1);
-    let x2 = box 2;
+    let x2: Box<_> = box 2;
     drop(x2);
     thread::spawn(move|| {
         drop(x1); //~ ERROR capture of moved value: `x1`
@@ -39,7 +39,7 @@ fn different_vars_after_moves() {
 }
 
 fn same_var_after_borrow() {
-    let x = box 1;
+    let x: Box<_> = box 1;
     let p = &x;
     thread::spawn(move|| {
         drop(x); //~ ERROR cannot move `x` into closure because it is borrowed
@@ -49,7 +49,7 @@ fn same_var_after_borrow() {
 }
 
 fn same_var_after_move() {
-    let x = box 1;
+    let x: Box<_> = box 1;
     drop(x);
     thread::spawn(move|| {
         drop(x); //~ ERROR capture of moved value: `x`
index 6985d203fb163cc554940e8646d4d56ffeebdb83..8cb7423f3cb5efc1aa4bf349ba25c0b1821f0c31 100644 (file)
@@ -19,7 +19,7 @@ enum cycle {
     empty
 }
 fn main() {
-    let mut x = box cycle::node(node_ {a: box cycle::empty});
+    let mut x: Box<_> = box cycle::node(node_ {a: box cycle::empty});
     // Create a cycle!
     match *x {
       cycle::node(ref mut y) => {
index e9d8544a06a90e3247ed00eced1c778bf52dabfc..58668b73cbffbc609681893e986472ba282117de 100644 (file)
@@ -25,7 +25,7 @@ fn index(&self, &i: &usize) -> &T {
 }
 
 fn main() {
-    let v = MyVec { data: vec!(box 1, box 2, box 3) };
+    let v = MyVec::<Box<_>> { data: vec!(box 1, box 2, box 3) };
     let good = &v[0]; // Shouldn't fail here
     let bad = v[0];
     //~^ ERROR cannot move out of indexed content
index 216373707241efe7318e41825a6079c0c22eff6a..61bf2c11a1f72d1b96d371f762d352e61947ae1d 100644 (file)
@@ -11,7 +11,7 @@
 #![allow(dead_code)]
 fn main() {
     // Original borrow ends at end of function
-    let mut x = 1_usize;
+    let mut x = 1;
     let y = &mut x;
     let z = &x; //~ ERROR cannot borrow
 }
@@ -21,7 +21,7 @@ fn foo() {
     match true {
         true => {
             // Original borrow ends at end of match arm
-            let mut x = 1_usize;
+            let mut x = 1;
             let y = &x;
             let z = &mut x; //~ ERROR cannot borrow
         }
@@ -33,7 +33,7 @@ fn foo() {
 fn bar() {
     // Original borrow ends at end of closure
     || {
-        let mut x = 1_usize;
+        let mut x = 1;
         let y = &mut x;
         let z = &mut x; //~ ERROR cannot borrow
     };
index 49a1b782a3db443aeff1c72640ea17e74c722f2c..f36dc0ca43fa25beaa03a6ac3bd03bbbcbaa1f07 100644 (file)
@@ -13,7 +13,7 @@
 fn borrow(_v: &isize) {}
 
 fn local() {
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     borrow(&*v);
 }
 
@@ -32,27 +32,27 @@ struct H { h: Box<isize> }
 }
 
 fn aliased_imm() {
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     let _w = &v;
     borrow(&*v);
 }
 
 fn aliased_mut() {
-    let mut v = box 3;
+    let mut v: Box<_> = box 3;
     let _w = &mut v;
     borrow(&*v); //~ ERROR cannot borrow `*v`
 }
 
 fn aliased_other() {
-    let mut v = box 3;
-    let mut w = box 4;
+    let mut v: Box<_> = box 3;
+    let mut w: Box<_> = box 4;
     let _x = &mut w;
     borrow(&*v);
 }
 
 fn aliased_other_reassign() {
-    let mut v = box 3;
-    let mut w = box 4;
+    let mut v: Box<_> = box 3;
+    let mut w: Box<_> = box 4;
     let mut _x = &mut w;
     _x = &mut v;
     borrow(&*v); //~ ERROR cannot borrow `*v`
diff --git a/src/test/compile-fail/cfg-attr-unknown-attribute-macro-expansion.rs b/src/test/compile-fail/cfg-attr-unknown-attribute-macro-expansion.rs
new file mode 100644 (file)
index 0000000..afcb896
--- /dev/null
@@ -0,0 +1,20 @@
+// Copyright 2015 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.
+
+macro_rules! foo {
+    () => {
+        #[cfg_attr(all(), unknown)] //~ ERROR `unknown` is currently unknown
+        fn foo() {}
+    }
+}
+
+foo!();
+
+fn main() {}
index ada45e8c1fc8b1528803fd00c5ab35f58266a4d8..46b100a4d399e35593ef3cda5b34899e5796dbcd 100644 (file)
@@ -27,5 +27,5 @@ fn cat(in_x : usize) -> cat {
 }
 
 fn main() {
-  let nyan = cat(0_usize);
+  let nyan = cat(0);
 }
index f25b2e65388ee190801e27ce09f55646d6f9be46..ab76af1cbe600d91168633f3b66f3b5db04d6ee7 100644 (file)
@@ -16,7 +16,7 @@ impl cat {
     fn sleep(&self) { loop{} }
     fn meow(&self) {
       println!("Meow");
-      meows += 1_usize; //~ ERROR unresolved name
+      meows += 1; //~ ERROR unresolved name
       sleep();     //~ ERROR unresolved name
     }
 
index aac180f9ad7bf63ca00a2c5f560d5bd1bbed0723..bb4d1693af7e35902839a9d920b85b4b7f5af701 100644 (file)
 // Tests that we forbid coercion from `[T; n]` to `&[T]`
 
 fn main() {
-    let _: &[i32] = [0i32];
+    let _: &[i32] = [0];
     //~^ ERROR mismatched types
     //~| expected `&[i32]`
-    //~| found `[i32; 1]`
+    //~| found `[_; 1]`
     //~| expected &-ptr
     //~| found array of 1 elements
 }
diff --git a/src/test/compile-fail/coherence-impls-builtin.rs b/src/test/compile-fail/coherence-impls-builtin.rs
deleted file mode 100644 (file)
index 3e132dc..0000000
+++ /dev/null
@@ -1,43 +0,0 @@
-// Copyright 2015 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(optin_builtin_traits)]
-
-use std::marker::Send;
-
-enum TestE {
-  A
-}
-
-struct MyType;
-
-struct NotSync;
-impl !Sync for NotSync {}
-
-unsafe impl Send for TestE {}
-unsafe impl Send for MyType {}
-unsafe impl Send for (MyType, MyType) {}
-//~^ ERROR builtin traits can only be implemented on structs or enums
-
-unsafe impl Send for &'static NotSync {}
-//~^ ERROR builtin traits can only be implemented on structs or enums
-
-unsafe impl Send for [MyType] {}
-//~^ ERROR builtin traits can only be implemented on structs or enums
-
-unsafe impl Send for &'static [NotSync] {}
-//~^ ERROR builtin traits can only be implemented on structs or enums
-//~^^ ERROR conflicting implementations for trait `core::marker::Send`
-
-fn is_send<T: Send>() {}
-
-fn main() {
-    is_send::<(MyType, TestE)>();
-}
diff --git a/src/test/compile-fail/coherence-impls-copy.rs b/src/test/compile-fail/coherence-impls-copy.rs
new file mode 100644 (file)
index 0000000..3034be1
--- /dev/null
@@ -0,0 +1,39 @@
+// Copyright 2015 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(optin_builtin_traits)]
+
+use std::marker::Copy;
+
+enum TestE {
+  A
+}
+
+struct MyType;
+
+struct NotSync;
+impl !Sync for NotSync {}
+
+impl Copy for TestE {}
+impl Copy for MyType {}
+impl Copy for (MyType, MyType) {}
+//~^ ERROR E0206
+
+impl Copy for &'static NotSync {}
+//~^ ERROR E0206
+
+impl Copy for [MyType] {}
+//~^ ERROR E0206
+
+impl Copy for &'static [NotSync] {}
+//~^ ERROR E0206
+
+fn main() {
+}
diff --git a/src/test/compile-fail/coherence-impls-send.rs b/src/test/compile-fail/coherence-impls-send.rs
new file mode 100644 (file)
index 0000000..b05c1ff
--- /dev/null
@@ -0,0 +1,40 @@
+// Copyright 2015 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(optin_builtin_traits)]
+
+use std::marker::Copy;
+
+enum TestE {
+  A
+}
+
+struct MyType;
+
+struct NotSync;
+impl !Sync for NotSync {}
+
+unsafe impl Send for TestE {}
+unsafe impl Send for MyType {}
+unsafe impl Send for (MyType, MyType) {}
+//~^ ERROR E0321
+
+unsafe impl Send for &'static NotSync {}
+//~^ ERROR E0321
+
+unsafe impl Send for [MyType] {}
+//~^ ERROR E0321
+
+unsafe impl Send for &'static [NotSync] {}
+//~^ ERROR E0321
+//~| ERROR conflicting implementations
+
+fn main() {
+}
diff --git a/src/test/compile-fail/coherence-impls-sized.rs b/src/test/compile-fail/coherence-impls-sized.rs
new file mode 100644 (file)
index 0000000..a9a3eba
--- /dev/null
@@ -0,0 +1,33 @@
+// Copyright 2015 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(optin_builtin_traits)]
+
+use std::marker::Copy;
+
+enum TestE {
+  A
+}
+
+struct MyType;
+
+struct NotSync;
+impl !Sync for NotSync {}
+
+impl Sized for TestE {} //~ ERROR E0322
+impl Sized for MyType {} //~ ERROR E0322
+impl Sized for (MyType, MyType) {} //~ ERROR E0322
+impl Sized for &'static NotSync {} //~ ERROR E0322
+impl Sized for [MyType] {} //~ ERROR E0322
+//~^ ERROR E0277
+impl Sized for &'static [NotSync] {} //~ ERROR E0322
+
+fn main() {
+}
index d7cd68e73c3498acc75b0557ceca6224e450e455..97dffec2dd9bd4758db4a11f9f89107d00581b72 100644 (file)
 
 struct TheType;
 
-impl TheTrait<usize> for isize { } //~ ERROR E0117
+impl TheTrait<usize> for isize { }
+//~^ ERROR E0117
 
 impl TheTrait<TheType> for isize { }
 
 impl TheTrait<isize> for TheType { }
 
-impl !Send for Vec<isize> { } //~ ERROR E0117
-//~^ ERROR conflicting
+impl !Send for Vec<isize> { }
+//~^ ERROR E0117
+//~| ERROR E0119
 
 fn main() { }
index fa63b16afa6d0835e459e555b3d325efc12d36f8..5ccfb1ddec78adb5d3403a409a001a766942856e 100644 (file)
@@ -8,7 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-const A: usize = { 1_usize; 2 };
+const A: usize = { 1; 2 };
 //~^ ERROR: blocks in constants are limited to items and tail expressions
 
 const B: usize = { { } 2 };
@@ -19,7 +19,7 @@ macro_rules! foo {
 }
 const C: usize = { foo!(); 2 };
 
-const D: usize = { let x = 4_usize; 2 };
+const D: usize = { let x = 4; 2 };
 //~^ ERROR: blocks in constants are limited to items and tail expressions
 
 pub fn main() {
diff --git a/src/test/compile-fail/const-len-underflow-separate-spans.rs b/src/test/compile-fail/const-len-underflow-separate-spans.rs
new file mode 100644 (file)
index 0000000..cd021a0
--- /dev/null
@@ -0,0 +1,23 @@
+// Copyright 2012-2013 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.
+
+// Check that an constant-evaluation underflow highlights the correct
+// spot (where the underflow occurred), while also providing the
+// overall context for what caused the evaluation.
+
+const ONE: usize = 1;
+const TWO: usize = 2;
+const LEN: usize = ONE - TWO;
+//~^ ERROR array length constant evaluation error: attempted to sub with overflow [E0250]
+
+fn main() {
+    let a: [i8; LEN] = unimplemented!();
+    //~^ NOTE for array length here
+}
diff --git a/src/test/compile-fail/const-len-underflow-subspans.rs b/src/test/compile-fail/const-len-underflow-subspans.rs
new file mode 100644 (file)
index 0000000..a31da11
--- /dev/null
@@ -0,0 +1,20 @@
+// Copyright 2012-2013 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.
+
+// Check that an constant-evaluation underflow highlights the correct
+// spot (where the underflow occurred).
+
+const ONE: usize = 1;
+const TWO: usize = 2;
+
+fn main() {
+    let a: [i8; ONE - TWO] = unimplemented!();
+    //~^ ERROR array length constant evaluation error: attempted to sub with overflow [E0250]
+}
index 6bd21101a609df402b94dd01bb93a5a36892a5d7..871f52cbebddc35fa026b3f2ca19c55986428014 100644 (file)
 // Test that cross-borrowing (implicitly converting from `Box<T>` to `&T`) is
 // forbidden when `T` is a trait.
 
-#![feature(box_syntax)]
-
 struct Foo;
 trait Trait { fn foo(&self) {} }
 impl Trait for Foo {}
 
 pub fn main() {
-    let x: Box<Trait> = box Foo;
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let x: Box<Trait> = Box::new(Foo);
     let _y: &Trait = x; //~  ERROR mismatched types
                         //~| expected `&Trait`
                         //~| found `Box<Trait>`
index abcbf567d44360f6584efcbfb0da509295d86501..5ca0700ce6edaa8425da266aec76db4953bc71f5 100644 (file)
@@ -25,7 +25,7 @@
 struct A<T>
     where T : Trait,
           T : Add<T::Item>
-    //~^ ERROR illegal recursive type
+    //~^ ERROR unsupported cyclic reference between types/traits detected
 {
     data: T
 }
diff --git a/src/test/compile-fail/cycle-trait-default-type-trait.rs b/src/test/compile-fail/cycle-trait-default-type-trait.rs
new file mode 100644 (file)
index 0000000..e6caeb3
--- /dev/null
@@ -0,0 +1,18 @@
+// Copyright 2015 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.
+
+// Test a cycle where a type parameter on a trait has a default that
+// again references the trait.
+
+trait Foo<X = Box<Foo>> {
+    //~^ ERROR unsupported cyclic reference
+}
+
+fn main() { }
index 6ebd9a1bcb6e2548cb89a11d173d923911cfc98c..c9bfde3f4ed12bb9ad233976cd0ec992be83611e 100644 (file)
 // a direct participant in the cycle.
 
 trait A: B {
+    //~^ ERROR unsupported cyclic reference
 }
 
-trait B: C { }
+trait B: C {
+    //~^ ERROR unsupported cyclic reference
+}
 
 trait C: B { }
     //~^ ERROR unsupported cyclic reference
index 1401494d987a28af300ad026f11f02a1c5b7afa8..22fc4a94cd25ab87254b9d754aeadc724ae59f61 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(custom_attribute)]
+
 #[phase(blah)]
 //~^ ERROR #[phase] is deprecated
 extern crate foo;
index c0bcbb284a15e961093cc1bb9021f5b8cc6390f0..72d06274de471af216a2a87f4c33d45f6720eb4e 100644 (file)
@@ -8,12 +8,12 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#[derive(Copy(Bad))]
-//~^ ERROR unexpected value in deriving, expected a trait
+#[derive(Send)]
+//~^ ERROR this unsafe trait should be implemented explicitly
 struct Test;
 
 #[derive(Sync)]
-//~^ ERROR Sync is an unsafe trait and it should be implemented explicitly
+//~^ ERROR this unsafe trait should be implemented explicitly
 struct Test1;
 
 pub fn main() {}
index 6b85656bdd9e63e1561ecc2287b654f6560083cd..e223499469355c30b0e92c719e200257c15bf99c 100644 (file)
@@ -8,7 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#[derive(Eqr)] //~ ERROR unknown `derive` trait: `Eqr`
+#[derive(Eqr)]
+//~^ ERROR `#[derive]` for custom traits is not stable enough for use and is subject to change
 struct Foo;
 
 pub fn main() {}
index 966e28a789cc88e7a99fba06719c2a34c33b9017..5b215f3ccd9618f1b76ea1f0b51b59622294564f 100644 (file)
@@ -22,10 +22,10 @@ impl S { }
 impl T for S { }
 
 #[derive(PartialEq)] //~ ERROR: `derive` may only be applied to structs and enums
-static s: usize = 0_usize;
+static s: usize = 0;
 
 #[derive(PartialEq)] //~ ERROR: `derive` may only be applied to structs and enums
-const c: usize = 0_usize;
+const c: usize = 0;
 
 #[derive(PartialEq)] //~ ERROR: `derive` may only be applied to structs and enums
 mod m { }
index 0836cd1695de38e62625eca6a46143a950d20949..22f615cafd71eec06ce67f396d45542e0e1eb466 100644 (file)
@@ -14,8 +14,8 @@
 
 fn main() {
     let b = {
-        let a = Box::new(RefCell::new(4i8));
-        *a.borrow() + 1i8    //~ ERROR `*a` does not live long enough
+        let a = Box::new(RefCell::new(4));
+        *a.borrow() + 1    //~ ERROR `*a` does not live long enough
     };
     println!("{}", b);
 }
index 7dbb8fc92e345bd3021f2485628f9dcd7ab332a1..8441f3a99e1aa6b3430191b4672c1303de85d3c4 100644 (file)
@@ -10,8 +10,6 @@
 
 // Forbid assignment into a dynamically sized type.
 
-#![feature(box_syntax)]
-
 struct Fat<T: ?Sized> {
     f1: isize,
     f2: &'static str,
@@ -43,7 +41,8 @@ fn to_val(&self) -> isize {
 pub fn main() {
     // Assignment.
     let f5: &mut Fat<ToBar> = &mut Fat { f1: 5, f2: "some str", ptr: Bar1 {f :42} };
-    let z: Box<ToBar> = box Bar1 {f: 36};
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let z: Box<ToBar> = Box::new(Bar1 {f: 36});
     f5.ptr = *z;
     //~^ ERROR the trait `core::marker::Sized` is not implemented
 }
index 152864b601c20818da6b5f6a8eff691d58a97305..d3029bc6a99801a785754a1a9b8ac6bf92e05ec0 100644 (file)
@@ -10,8 +10,6 @@
 
 // Forbid assignment into a dynamically sized type.
 
-#![feature(box_syntax)]
-
 struct Fat<T: ?Sized> {
     f1: isize,
     f2: &'static str,
@@ -43,7 +41,8 @@ fn to_val(&self) -> isize {
 pub fn main() {
     // Assignment.
     let f5: &mut Fat<ToBar> = &mut Fat { f1: 5, f2: "some str", ptr: Bar1 {f :42} };
-    let z: Box<ToBar> = box Bar1 {f: 36};
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let z: Box<ToBar> = Box::new(Bar1 {f: 36});
     f5.ptr = Bar1 {f: 36};
     //~^ ERROR mismatched types
     //~| expected `ToBar`
diff --git a/src/test/compile-fail/duplicate-trait-bounds.rs b/src/test/compile-fail/duplicate-trait-bounds.rs
deleted file mode 100644 (file)
index d9aa9d9..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-// 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.
-
-trait Foo {}
-
-fn foo<T: Foo + Foo>() {} //~ ERROR `Foo` already appears in the list of bounds
-
-fn main() {}
index 9b7df81a5dcbd666e0e489327f6dc9d97516f519..8791481d9e75e63b42ac90350468f0b3d5dc5244 100644 (file)
@@ -9,6 +9,6 @@
 // except according to those terms.
 
 // compile-flags: --extern std=
-// error-pattern: is not a file
+// error-pattern: can't find crate for `std`
 
 fn main() {}
index 92b7b601e4dc36430bf5447ed5f17209916e2176..ed1327f31185e8d565dd95307800193381e584a5 100644 (file)
@@ -9,8 +9,8 @@
 // except according to those terms.
 
 enum test {
-    div_zero = 1/0, //~ERROR expected constant: attempted to divide by zero
-    rem_zero = 1%0  //~ERROR expected constant: attempted remainder with a divisor of zero
+    div_zero = 1/0, //~ERROR constant evaluation error: attempted to divide by zero
+    rem_zero = 1%0  //~ERROR constant evaluation error: attempted remainder with a divisor of zero
 }
 
 fn main() {}
diff --git a/src/test/compile-fail/feature-gate-allow-internal-unstable-nested-macro.rs b/src/test/compile-fail/feature-gate-allow-internal-unstable-nested-macro.rs
new file mode 100644 (file)
index 0000000..c9251c9
--- /dev/null
@@ -0,0 +1,23 @@
+// Copyright 2015 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.
+
+macro_rules! bar {
+    () => {
+        // more layers don't help:
+        #[allow_internal_unstable]
+        macro_rules! baz { //~ ERROR allow_internal_unstable side-steps
+            () => {}
+        }
+    }
+}
+
+bar!();
+
+fn main() {}
diff --git a/src/test/compile-fail/feature-gate-allow-internal-unstable.rs b/src/test/compile-fail/feature-gate-allow-internal-unstable.rs
new file mode 100644 (file)
index 0000000..8a2d8dd
--- /dev/null
@@ -0,0 +1,16 @@
+// Copyright 2015 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.
+
+#[allow_internal_unstable] //~ ERROR allow_internal_unstable side-steps
+macro_rules! foo {
+    () => {}
+}
+
+fn main() {}
diff --git a/src/test/compile-fail/feature-gate-intrinsics-and-lang-items.rs b/src/test/compile-fail/feature-gate-intrinsics-and-lang-items.rs
deleted file mode 100644 (file)
index 986d52b..0000000
+++ /dev/null
@@ -1,23 +0,0 @@
-// 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.
-
-#[lang="foo"]   //~ ERROR language items are subject to change
-trait Foo {}
-
-extern "rust-intrinsic" {   //~ ERROR intrinsics are subject to change
-    fn bar();
-}
-
-extern "rust-intrinsic" fn baz() {  //~ ERROR intrinsics are subject to change
-}
-
-fn main() {
-}
-
diff --git a/src/test/compile-fail/feature-gate-intrinsics.rs b/src/test/compile-fail/feature-gate-intrinsics.rs
new file mode 100644 (file)
index 0000000..a4c09b2
--- /dev/null
@@ -0,0 +1,19 @@
+// 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 "rust-intrinsic" {   //~ ERROR intrinsics are subject to change
+    fn bar();
+}
+
+extern "rust-intrinsic" fn baz() {  //~ ERROR intrinsics are subject to change
+}
+
+fn main() {
+}
diff --git a/src/test/compile-fail/feature-gate-lang-items.rs b/src/test/compile-fail/feature-gate-lang-items.rs
new file mode 100644 (file)
index 0000000..0435ff4
--- /dev/null
@@ -0,0 +1,15 @@
+// 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.
+
+#[lang="foo"]   //~ ERROR language items are subject to change
+trait Foo {}
+
+fn main() {
+}
diff --git a/src/test/compile-fail/feature-gate-static-assert.rs b/src/test/compile-fail/feature-gate-static-assert.rs
new file mode 100644 (file)
index 0000000..2574039
--- /dev/null
@@ -0,0 +1,14 @@
+// Copyright 2015 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.
+
+#[static_assert] //~ ERROR `#[static_assert]` is an experimental feature
+static X: bool = true;
+
+fn main() {}
index 1e15e67876ed44f140e63b877fae4e5158baba79..54bdaf011c875c63de26a56c6ec368cb0ecfca7d 100644 (file)
@@ -21,7 +21,7 @@
 // test. Not ideal, but oh well :(
 
 fn main() {
-    let a = &[1i32, 2, 3];
+    let a = &[1, 2, 3];
     println!("{}", {
         extern "rust-intrinsic" { //~ ERROR intrinsics are subject to change
             fn atomic_fence();
diff --git a/src/test/compile-fail/gated-link-args.rs b/src/test/compile-fail/gated-link-args.rs
new file mode 100644 (file)
index 0000000..c8845ce
--- /dev/null
@@ -0,0 +1,19 @@
+// Copyright 2015 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.
+
+// Test that `#[link_args]` attribute is gated by `link_args`
+// feature gate.
+
+#[link_args = "aFdEfSeVEEE"]
+extern {}
+//~^ ERROR the `link_args` attribute is not portable across platforms
+//~| HELP add #![feature(link_args)] to the crate attributes to enable
+
+fn main() { }
diff --git a/src/test/compile-fail/gated-link-llvm-intrinsics.rs b/src/test/compile-fail/gated-link-llvm-intrinsics.rs
new file mode 100644 (file)
index 0000000..716ea9f
--- /dev/null
@@ -0,0 +1,19 @@
+// Copyright 2015 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 {
+    #[link_name = "llvm.sqrt.f32"]
+    fn sqrt(x: f32) -> f32;
+    //~^ ERROR linking to LLVM intrinsics is experimental
+    //~| HELP add #![feature(link_llvm_intrinsics)] to the crate attributes
+}
+
+fn main(){
+}
index f6e11ffd9e5239c92f732a01c6cbd0969afd6726..d716c53e1d18ce68c4db2f1a79f42b7c9802cae4 100644 (file)
@@ -8,8 +8,12 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+// Test that `#[plugin_registrar]` attribute is gated by `plugin_registrar`
+// feature gate.
+
 // the registration function isn't typechecked yet
 #[plugin_registrar]
-pub fn registrar() {} //~ ERROR compiler plugins are experimental
-
+pub fn registrar() {}
+//~^ ERROR compiler plugins are experimental
+//~| HELP add #![feature(plugin_registrar)] to the crate attributes to enable
 fn main() {}
diff --git a/src/test/compile-fail/gated-thread-local.rs b/src/test/compile-fail/gated-thread-local.rs
new file mode 100644 (file)
index 0000000..f355c65
--- /dev/null
@@ -0,0 +1,25 @@
+// Copyright 2015 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.
+
+// Test that `#[thread_local]` attribute is gated by `thread_local`
+// feature gate.
+//
+// (Note that the `thread_local!` macro is explicitly *not* gated; it
+// is given permission to expand into this unstable attribute even
+// when the surrounding context does not have permission to use it.)
+
+#[thread_local] //~ ERROR `#[thread_local]` is an experimental feature
+static FOO: i32 = 3;
+
+pub fn main() {
+    FOO.with(|x| {
+        println!("x: {}", x);
+    });
+}
diff --git a/src/test/compile-fail/gated-unsafe-destructor.rs b/src/test/compile-fail/gated-unsafe-destructor.rs
new file mode 100644 (file)
index 0000000..6024fef
--- /dev/null
@@ -0,0 +1,23 @@
+// Copyright 2015 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.
+
+// Test that `#[unsafe_destructor]` attribute is gated by `unsafe_destructor`
+// feature gate.
+
+struct D<'a>(&'a u32);
+
+#[unsafe_destructor]
+impl<'a> Drop for D<'a> {
+    //~^ ERROR `#[unsafe_destructor]` allows too many unsafe patterns
+    fn drop(&mut self) { }
+}
+//~^ HELP: add #![feature(unsafe_destructor)] to the crate attributes to enable
+
+pub fn main() { }
index 1e04e685e41b8b3434ca2b62dfd92671eea445eb..105f885f2875f4934aa01ecddc3c5bb66d5c0231 100644 (file)
@@ -9,6 +9,7 @@
 // except according to those terms.
 
 // error-pattern: too big for the current
+#![allow(exceeding_bitshifts)]
 
 fn main() {
    let fat : [u8; (1<<61)+(1<<31)] = [0; (1u64<<61) as usize +(1u64<<31) as usize];
index f38172db4447b58ae06dcd7a694877079348486f..67834a9996948f5ca756b67d4b019d0d0ec7e340 100644 (file)
 mod circ1 {
     pub use circ2::f2;
     pub fn f1() { println!("f1"); }
-    pub fn common() -> usize { return 0_usize; }
+    pub fn common() -> usize { return 0; }
 }
 
 mod circ2 {
     pub use circ1::f1;
     pub fn f2() { println!("f2"); }
-    pub fn common() -> usize { return 1_usize; }
+    pub fn common() -> usize { return 1; }
 }
 
 mod test {
index b28f2a746fdc40c5d64345bef176d52d33ef0e53..70c362303ae30cba82ac7837aa7f326f32cabf0b 100644 (file)
@@ -9,5 +9,5 @@
 // except according to those terms.
 
 fn main() {
-    (return)[0_usize]; //~ ERROR the type of this value must be known in this context
+    (return)[0]; //~ ERROR the type of this value must be known in this context
 }
index d39efa3c2ab78f909815c6db507a9a0be4a6419a..559e0e9a292a6dda32676241228923421dcede21 100644 (file)
@@ -32,13 +32,13 @@ fn to_option(&self) -> Option<Option<T>> {
 }
 
 fn function<T:ToOpt + Clone>(counter: usize, t: T) {
-    if counter > 0_usize {
-        function(counter - 1_usize, t.to_option());
+    if counter > 0 {
+        function(counter - 1, t.to_option());
         // FIXME(#4287) Error message should be here. It should be
         // a type error to instantiate `test` at a type other than T.
     }
 }
 
 fn main() {
-    function(22_usize, 22_usize);
+    function(22, 22);
 }
index 5bcba350b2ecba893f97825acf2c751d0f1b21f8..e5120840f7672a6d19ad8fae9faa4d87f29504df 100644 (file)
@@ -8,9 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// error-pattern: illegal recursive type
-
-
 type x = Vec<x>;
+//~^ ERROR unsupported cyclic reference
 
 fn main() { let b: x = Vec::new(); }
diff --git a/src/test/compile-fail/internal-unstable-noallow.rs b/src/test/compile-fail/internal-unstable-noallow.rs
new file mode 100644 (file)
index 0000000..4e29619
--- /dev/null
@@ -0,0 +1,30 @@
+// Copyright 2015 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.
+
+// this has to be separate to internal-unstable.rs because these tests
+// have error messages pointing deep into the internals of the
+// cross-crate macros, and hence need to use error-pattern instead of
+// the // ~ form.
+
+// aux-build:internal_unstable.rs
+// error-pattern:use of unstable library feature 'function'
+// error-pattern:use of unstable library feature 'struct_field'
+// error-pattern:compilation successful
+#![feature(rustc_attrs)]
+
+#[macro_use]
+extern crate internal_unstable;
+
+#[rustc_error]
+fn main() {
+    call_unstable_noallow!();
+
+    construct_unstable_noallow!(0);
+}
diff --git a/src/test/compile-fail/internal-unstable-thread-local.rs b/src/test/compile-fail/internal-unstable-thread-local.rs
new file mode 100644 (file)
index 0000000..ff15849
--- /dev/null
@@ -0,0 +1,23 @@
+// Copyright 2015 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.
+
+// aux-build:internal_unstable.rs
+
+#![feature(rustc_attrs)]
+#![allow(dead_code)]
+
+extern crate internal_unstable;
+
+
+thread_local!(static FOO: () = ());
+thread_local!(static BAR: () = internal_unstable::unstable()); //~ WARN use of unstable
+
+#[rustc_error]
+fn main() {} //~ ERROR
diff --git a/src/test/compile-fail/internal-unstable.rs b/src/test/compile-fail/internal-unstable.rs
new file mode 100755 (executable)
index 0000000..8674e8a
--- /dev/null
@@ -0,0 +1,51 @@
+// Copyright 2015 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.
+
+// aux-build:internal_unstable.rs
+
+#![feature(rustc_attrs, allow_internal_unstable)]
+
+#[macro_use]
+extern crate internal_unstable;
+
+macro_rules! foo {
+    ($e: expr, $f: expr) => {{
+        $e;
+        $f;
+        internal_unstable::unstable(); //~ WARN use of unstable
+    }}
+}
+
+#[allow_internal_unstable]
+macro_rules! bar {
+    ($e: expr) => {{
+        foo!($e,
+             internal_unstable::unstable());
+        internal_unstable::unstable();
+    }}
+}
+
+#[rustc_error]
+fn main() { //~ ERROR
+    // ok, the instability is contained.
+    call_unstable_allow!();
+    construct_unstable_allow!(0);
+
+    // bad.
+    pass_through_allow!(internal_unstable::unstable()); //~ WARN use of unstable
+
+    pass_through_noallow!(internal_unstable::unstable()); //~ WARN use of unstable
+
+
+
+    println!("{:?}", internal_unstable::unstable()); //~ WARN use of unstable
+
+    bar!(internal_unstable::unstable()); //~ WARN use of unstable
+}
index 45f6e55914a1b07ba3a8c28cd3e87dc4858ee94f..9711d760ae666ccb54409aa5fdb6dd90f43f3478 100644 (file)
@@ -8,13 +8,12 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 fn test<'x>(x: &'x isize) {
-    drop::<Box<for<'z> FnMut(&'z isize) -> &'z isize>>(box |z| {
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    drop::<Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
         x
         //~^ ERROR cannot infer an appropriate lifetime
-    });
+    }));
 }
 
 fn main() {}
index 736f9630127121e23bd24340114c5700f4102656..08e8effc626f5bd68b7e6bda91e97b9fb3fa3aa5 100644 (file)
@@ -11,7 +11,7 @@
 #![feature(box_syntax)]
 
 fn main() {
-    let x = box 1;
+    let x: Box<_> = box 1;
     let f = move|| {
         let _a = x;
         drop(x);
index a95bcc73a9c473adf98a2ac38839dfdeaf42ee73..7313d357ffc1a09f2a068e53e1667be3e953f38c 100644 (file)
@@ -21,7 +21,7 @@ fn drop(&mut self) {
 }
 
 fn main() {
-    let mut ptr = box Foo { x: 0 };
+    let mut ptr: Box<_> = box Foo { x: 0 };
     let mut test = |foo: &Foo| {
         println!("access {}", foo.x);
         ptr = box Foo { x: ptr.x + 1 };
index 4ff574e939df649794a2b31bdd4f49a374ed3c05..f682d618ab646131735f3cf47ff98976be17369c 100644 (file)
@@ -15,6 +15,7 @@ struct Test {
 }
 
 fn main() {
-    let closure: Box<Fn()+'static> = box || ();
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let closure: Box<Fn()+'static> = Box::new(|| ());
     let test = box Test { func: closure }; //~ ERROR mismatched types
 }
index d307352517feaf5e95c51d8cbb268c0e74c2fcde..998576097a0a06887275de88b1d82149f2fcae6e 100644 (file)
@@ -9,7 +9,7 @@
 // except according to those terms.
 
 fn blah() -> i32 { //~ ERROR not all control paths return a value
-    1i32
+    1
 
     ; //~ HELP consider removing this semicolon:
 }
index df4dab2552e7de8922613d5f6a683a4a338778b3..7bd072c6268cdfcc7520130b545a62fc46a8a95b 100644 (file)
@@ -14,7 +14,7 @@ fn to_fn_once<A,F:FnOnce<A>>(f: F) -> F { f }
 
 fn main() {
     let r = {
-        let x = box 42;
+        let x: Box<_> = box 42;
         let f = to_fn_once(move|| &x); //~ ERROR: `x` does not live long enough
         f()
     };
index 40d446b91a5a8b659d56cb79dcbec7b202c8249d..5565a9a5761166d0a52fb7649d241990b546c492 100644 (file)
@@ -14,7 +14,7 @@ fn to_fn_once<A,F:FnOnce<A>>(f: F) -> F { f }
 fn do_it(x: &isize) { }
 
 fn main() {
-    let x = box 22;
+    let x: Box<_> = box 22;
     let f = to_fn_once(move|| do_it(&*x));
     to_fn_once(move|| {
         f();
index 06f14158b91577f7b4219f5b2bcc767e231fc511..50c4ac94d903267b8d07b2c90f9a878bf5293ae0 100644 (file)
@@ -24,7 +24,7 @@ fn check<'r, I: Iterator<Item=usize>, T: Itble<'r, usize, I>>(cont: &T) -> bool
 {
     let cont_iter = cont.iter();
 //~^ ERROR cannot infer an appropriate lifetime for autoref due to conflicting requirements
-    let result = cont_iter.fold(Some(0u16), |state, val| {
+    let result = cont_iter.fold(Some(0), |state, val| {
         state.map_or(None, |mask| {
             let bit = 1 << val;
             if mask & bit == 0 {Some(mask|bit)} else {None}
@@ -34,10 +34,10 @@ fn check<'r, I: Iterator<Item=usize>, T: Itble<'r, usize, I>>(cont: &T) -> bool
 }
 
 fn main() {
-    check((3_usize, 5_usize));
+    check((3, 5));
 //~^ ERROR mismatched types
 //~| expected `&_`
-//~| found `(usize, usize)`
+//~| found `(_, _)`
 //~| expected &-ptr
 //~| found tuple
 }
index 16128e52d64d1d9804e481c89269cf444541e8bc..a29a83c43063214f6bb0c2ebae731c2b7327f575 100644 (file)
@@ -14,17 +14,17 @@ pub fn main() {
     // The expected arm type `Option<T>` has one type parameter, while
     // the actual arm `Result<T, E>` has two. typeck should not be
     // tricked into looking up a non-existing second type parameter.
-    let _x: usize = match Some(1_usize) {
+    let _x: usize = match Some(1) {
         Ok(u) => u,
         //~^ ERROR mismatched types
-        //~| expected `core::option::Option<usize>`
+        //~| expected `core::option::Option<_>`
         //~| found `core::result::Result<_, _>`
         //~| expected enum `core::option::Option`
         //~| found enum `core::result::Result`
 
         Err(e) => panic!(e)
         //~^ ERROR mismatched types
-        //~| expected `core::option::Option<usize>`
+        //~| expected `core::option::Option<_>`
         //~| found `core::result::Result<_, _>`
         //~| expected enum `core::option::Option`
         //~| found enum `core::result::Result`
index d7ff6f2fe63ce38f423aad11654552febbbba6b6..d7bb806999c74abe7291eac8f090a492a53ac417 100644 (file)
@@ -22,11 +22,11 @@ fn main() {
     //~| expected u8
     //~| found array of 1 elements
 
-    let local = [0u8];
+    let local = [0];
     let _v = &local as *mut u8;
     //~^ ERROR mismatched types
     //~| expected `*mut u8`
-    //~| found `&[u8; 1]`
+    //~| found `&[_; 1]`
     //~| expected u8,
     //~| found array of 1 elements
 }
index a213234b89b0ff247c73f9ac27cf1fc0dfce01d3..64334fe4392f8774962a9c301aa109bc50bb0c1e 100644 (file)
@@ -18,11 +18,10 @@ trait ListItem<'a> : MarkerTrait {
 
 struct List<'a, T: ListItem<'a>> {
 //~^ ERROR the parameter type `T` may not live long enough
-//~^^ HELP consider adding an explicit lifetime bound
-//~^^^ NOTE ...so that the reference type `&'a [T]` does not outlive the data it points at
+//~^^ NOTE ...so that the reference type `&'a [T]` does not outlive the data it points at
     slice: &'a [T]
 }
-
+//~^ HELP consider adding an explicit lifetime bound
 impl<'a, T: ListItem<'a>> Collection for List<'a, T> {
     fn len(&self) -> usize {
         0
index 543063b3fc968a225f2eb99ef54ef7d2b4c3041d..f40d51f1d2fd3c59c3aef358a2ca1de3b5aef372 100644 (file)
 struct Foo { a: isize, b: isize }
 
 fn main() {
-    let mut x = box Foo { a: 1, b: 2 };
+    let mut x: Box<_> = box Foo { a: 1, b: 2 };
     let (a, b) = (&mut x.a, &mut x.b);
     //~^ ERROR cannot borrow `x` (here through borrowing `x.b`) as mutable more than once at a time
     //~^^ NOTE previous borrow of `x` occurs here (through borrowing `x.a`)
 
-    let mut foo = box Foo { a: 1, b: 2 };
+    let mut foo: Box<_> = box Foo { a: 1, b: 2 };
     let (c, d) = (&mut foo.a, &foo.b);
     //~^ ERROR cannot borrow `foo` (here through borrowing `foo.b`) as immutable
     //~^^ NOTE previous borrow of `foo` occurs here (through borrowing `foo.a`)
index 65731379094a9d1002508944b0d734c07dc9556a..a481fec6bf96839cb011e0dcc6f50ab1657ecee1 100644 (file)
@@ -16,7 +16,7 @@ struct Foo {
 }
 
 fn main() {
-    let x = 1_usize;
+    let x = 1;
     let y: Foo;
 
     // `x { ... }` should not be interpreted as a struct literal here
index 9f76f360f26ba7db9cf81f7def9321c8110111ad..68ddef671887852f14b200910d6a2529ccf9be92 100644 (file)
@@ -8,18 +8,20 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 fn main() {
     let _foo = &[1_usize, 2] as [usize];
     //~^ ERROR cast to unsized type: `&[usize; 2]` as `[usize]`
     //~^^ HELP consider using an implicit coercion to `&[usize]` instead
-    let _bar = box 1_usize as std::fmt::Debug;
+
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let _bar = Box::new(1_usize) as std::fmt::Debug;
     //~^ ERROR cast to unsized type: `Box<usize>` as `core::fmt::Debug`
     //~^^ HELP did you mean `Box<core::fmt::Debug>`?
+
     let _baz = 1_usize as std::fmt::Debug;
     //~^ ERROR cast to unsized type: `usize` as `core::fmt::Debug`
     //~^^ HELP consider using a box or reference as appropriate
+
     let _quux = [1_usize, 2] as [usize];
     //~^ ERROR cast to unsized type: `[usize; 2]` as `[usize]`
     //~^^ HELP consider using a box or reference as appropriate
index 172f37af834400ba766388c9a2c8a54b4d8b779d..8ebf80a8db0dc5be49c5d6fc655d30a5dbaefce0 100644 (file)
 // Test that moves of unsized values within closures are caught
 // and rejected.
 
-#![feature(box_syntax)]
-
 fn main() {
-    (|| box *[0_usize].as_slice())();
-    //~^ ERROR cannot move out of borrowed content
-    //~^^ ERROR cannot move a value of type [usize]
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    (|| Box::new(*[0].as_slice()))();
+    //~^ ERROR the trait `core::marker::Sized` is not implemented for the type `[_]`
 }
index b7f58791bfcc8d32a6968938c8b5222beaccc1db..4e63f667d26fa413e83cc5d3c8ba988093c856a3 100644 (file)
@@ -13,7 +13,7 @@
 const A3: usize = 1;
 
 fn main() {
-    match 1_usize {
+    match 1 {
         A1 => {} //~ ERROR: static variables cannot be referenced in a pattern
         A2 => {} //~ ERROR: static variables cannot be referenced in a pattern
         A3 => {}
index 8035cffabda9717aa51317533ca9ac4b19944c0c..80e5f2b6e2157917e943bc88a1397a720c917abd 100644 (file)
 #[cfg(target_pointer_width = "64")]
 fn main() {
     let n = 0_usize;
-    let a = box [&n; 0xF000000000000000_usize];
+    let a: Box<_> = box [&n; 0xF000000000000000_usize];
     println!("{}", a[0xFFFFFF_usize]);
 }
 
 #[cfg(target_pointer_width = "32")]
 fn main() {
     let n = 0_usize;
-    let a = box [&n; 0xFFFFFFFF_usize];
+    let a: Box<_> = box [&n; 0xFFFFFFFF_usize];
     println!("{}", a[0xFFFFFF_usize]);
 }
index bd0474084981f1164d795c996d9865c9c05f9499..657b31fa83c7f829419e5bf2aa88d9062c217e43 100644 (file)
@@ -8,10 +8,10 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-pub static X: usize = 1_usize;
+pub static X: usize = 1;
 
 fn main() {
-    match 1_usize {
+    match 1 {
         self::X => { },
         //~^ ERROR static variables cannot be referenced in a pattern, use a `const` instead
         _       => { },
index d5fb22bdebdb477d5c03cb68f3abdf80e40aaf01..60ab616d5983bf25a4dcad218fa39f5a321caf18 100644 (file)
@@ -16,7 +16,7 @@ fn _create_render(_: &()) ->
     AbstractRenderer
 //~^ ERROR: the trait `core::marker::Sized` is not implemented
 {
-    match 0_usize {
+    match 0 {
         _ => unimplemented!()
     }
 }
index 54c51405bd73f8ad7f13068a7441b541fe189463..e3e56c7f97ad5ba400b76d5c622f5c694873b6db 100644 (file)
@@ -13,5 +13,5 @@ enum Foo {
 }
 
 fn main() {
-    let f = Foo::Variant(42_usize); //~ ERROR uses it like a function
+    let f = Foo::Variant(42); //~ ERROR uses it like a function
 }
index 20323e99003332bda38454e693b148ed2cf09bcc..271c31bd375484c6ef7c763e8c67f5079433ce75 100644 (file)
 
 use std::any::Any;
 use std::any::TypeId;
+use std::marker::MarkerTrait;
 
-pub trait Pt {}
-pub trait Rt {}
+pub trait Pt : MarkerTrait {}
+pub trait Rt : MarkerTrait {}
 
 trait Private<P: Pt, R: Rt> {
     fn call(&self, p: P, r: R);
 }
-pub trait Public: Private<
+pub trait Public: Private< //~ ERROR private trait in exported type parameter bound
     <Self as Public>::P,
-//~^ ERROR illegal recursive type; insert an enum or struct in the cycle, if this is desired
     <Self as Public>::R
 > {
     type P;
index dd3844b1a0ef07bae34d0d8d7e60fc1f3aba007c..41e82d0cd8912f1085856e03ce07fb66298d6a99 100644 (file)
@@ -28,7 +28,7 @@ fn poke(&self, s: &mut usize)  {
 }
 
 fn main() {
-    let s = &mut 1_usize;
+    let s = &mut 1;
 
     MyPtr(s).poke(s);
     //~^ ERROR cannot borrow `*s` as mutable more than once at a time
index 13908bda9d83bf1e2d61f8d3304cc8144db12f97..5eb3c439df2f3170d5a2cafb8bb01f5f308777c7 100644 (file)
@@ -8,24 +8,24 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 use std::cell::RefCell;
 
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+
 fn main() {
-    let mut y = 1_usize;
+    let mut y = 1;
     let c = RefCell::new(vec![]);
-    c.push(box || y = 0);
-    c.push(box || y = 0);
+    c.push(Box::new(|| y = 0));
+    c.push(Box::new(|| y = 0));
 //~^ ERROR cannot borrow `y` as mutable more than once at a time
 }
 
 fn ufcs() {
-    let mut y = 1_usize;
+    let mut y = 1;
     let c = RefCell::new(vec![]);
 
-    Push::push(&c, box || y = 0);
-    Push::push(&c, box || y = 0);
+    Push::push(&c, Box::new(|| y = 0));
+    Push::push(&c, Box::new(|| y = 0));
 //~^ ERROR cannot borrow `y` as mutable more than once at a time
 }
 
index 8fb543fb96703cda1a50fc7c0731dfc11288656f..ebda2481803a7cef57f87661218d5831fa63fdef 100644 (file)
@@ -19,7 +19,7 @@ fn foo<T>(&self, _: &T) {}
 
 #[inline(never)]
 fn foo(b: &Bar) {
-    b.foo(&0usize)
+    b.foo(&0)
     //~^ ERROR the trait `Foo` is not implemented for the type `Bar`
 }
 
index 0850705aee6cb1529f9dd323c6ab961e49a686d5..5c11787d46780bf5cf2740ed22ab54b3f1b661ee 100644 (file)
@@ -12,5 +12,7 @@
 
 fn main() {
     let a: [isize; TUP.1];
-    //~^ ERROR expected constant expr for array length: tuple index out of bounds
+    //~^ ERROR array length constant evaluation error: tuple index out of bounds
+    //~| ERROR attempted out-of-bounds tuple index
+    //~| ERROR attempted out-of-bounds tuple index
 }
index 93a3fc87eb0107198dd7f55571b281816f568024..d896f76865910820a5a4ddb401b650b90f9f6858 100644 (file)
@@ -13,5 +13,7 @@ struct MyStruct { field: usize }
 
 fn main() {
     let a: [isize; STRUCT.nonexistent_field];
-    //~^ ERROR expected constant expr for array length: nonexistent struct field
+    //~^ ERROR array length constant evaluation error: nonexistent struct field
+    //~| ERROR attempted access of field `nonexistent_field`
+    //~| ERROR attempted access of field `nonexistent_field`
 }
index 2d73b98ec1e607d201c17318d507f78a9aca760e..6c9b0004f7754874e0f143038a15f8f8dd33b018 100644 (file)
@@ -14,9 +14,9 @@
 fn main() {
     if let Some(homura) = Some("madoka") { //~  ERROR missing an else clause
                                            //~| expected `()`
-                                           //~| found `i32`
+                                           //~| found `_`
                                            //~| expected ()
-                                           //~| found i32
-        765i32
+                                           //~| found integral variable
+        765
     };
 }
index 929c8ec0fd684eef81bed84c67e68fe818c201cd..fe7807042e55b706c3b8e2177a02d5b135012cb1 100644 (file)
@@ -25,11 +25,11 @@ fn mut_ref() -> &'static mut T {
 }
 
 fn mut_ptr() -> *mut T {
-    unsafe { 0u8 as *mut T }
+    unsafe { 0 as *mut T }
 }
 
 fn const_ptr() -> *const T {
-    unsafe { 0u8 as *const T }
+    unsafe { 0 as *const T }
 }
 
 pub fn main() {
index 505885e6c41f9bdf7f3d309b79684c1ee44cf57d..8b109b0a5c04d9b7eae68158ee5e16e0ccbbb1d3 100644 (file)
@@ -15,7 +15,7 @@
 fn fail_len(v: Vec<isize> ) -> usize {
     let mut i = 3;
     panic!();
-    for x in &v { i += 1_usize; }
+    for x in &v { i += 1; }
     //~^ ERROR: unreachable statement
     return i;
 }
diff --git a/src/test/compile-fail/issue-22912.rs b/src/test/compile-fail/issue-22912.rs
new file mode 100644 (file)
index 0000000..f4536ce
--- /dev/null
@@ -0,0 +1,41 @@
+// Copyright 2015 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.
+
+pub struct PublicType;
+struct PrivateType;
+
+pub trait PublicTrait {
+    type Item;
+}
+
+trait PrivateTrait {
+    type Item;
+}
+
+impl PublicTrait for PublicType {
+    type Item = PrivateType;  //~ ERROR private type in exported type signature
+}
+
+// OK
+impl PublicTrait for PrivateType {
+    type Item = PrivateType;
+}
+
+// OK
+impl PrivateTrait for PublicType {
+    type Item = PrivateType;
+}
+
+// OK
+impl PrivateTrait for PrivateType {
+    type Item = PrivateType;
+}
+
+fn main() {}
diff --git a/src/test/compile-fail/issue-23080-2.rs b/src/test/compile-fail/issue-23080-2.rs
new file mode 100644 (file)
index 0000000..ff5ac9d
--- /dev/null
@@ -0,0 +1,29 @@
+// Copyright 2015 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-tidy-linelength
+
+#![feature(optin_builtin_traits)]
+
+use std::marker::MarkerTrait;
+
+unsafe trait Trait: MarkerTrait {
+//~^ error: traits with default impls (`e.g. unsafe impl Trait for ..`) must have no methods or associated items
+    type Output;
+}
+
+unsafe impl Trait for .. {}
+
+fn call_method<T: Trait>(x: T) {}
+
+fn main() {
+    // ICE
+    call_method(());
+}
diff --git a/src/test/compile-fail/issue-23080.rs b/src/test/compile-fail/issue-23080.rs
new file mode 100644 (file)
index 0000000..99373a6
--- /dev/null
@@ -0,0 +1,31 @@
+// Copyright 2015 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-tidy-linelength
+
+#![feature(optin_builtin_traits)]
+
+unsafe trait Trait {
+//~^ error: traits with default impls (`e.g. unsafe impl Trait for ..`) must have no methods or associated items
+    fn method(&self) {
+        println!("Hello");
+    }
+}
+
+unsafe impl Trait for .. {}
+
+fn call_method<T: Trait>(x: T) {
+    x.method();
+}
+
+fn main() {
+    // ICE
+    call_method(());
+}
index 6e6c19a5bf6b08428a8024e7312b50edf5b2e927..085b4e76afbf71650fece23c0481522a9d9de5da 100644 (file)
@@ -8,8 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 mod my_mod {
     pub struct MyStruct {
         priv_field: isize
@@ -26,10 +24,15 @@ fn main() {
     let my_struct = my_mod::MyStruct();
     let _woohoo = (&my_struct).priv_field;
     //~^ ERROR field `priv_field` of struct `my_mod::MyStruct` is private
-    let _woohoo = (box my_struct).priv_field;
+
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let _woohoo = (Box::new(my_struct)).priv_field;
     //~^ ERROR field `priv_field` of struct `my_mod::MyStruct` is private
+
     (&my_struct).happyfun();               //~ ERROR method `happyfun` is private
-    (box my_struct).happyfun();            //~ ERROR method `happyfun` is private
+
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    (Box::new(my_struct)).happyfun();          //~ ERROR method `happyfun` is private
     let nope = my_struct.priv_field;
     //~^ ERROR field `priv_field` of struct `my_mod::MyStruct` is private
 }
diff --git a/src/test/compile-fail/issue-3953.rs b/src/test/compile-fail/issue-3953.rs
deleted file mode 100644 (file)
index 0f1dd2d..0000000
+++ /dev/null
@@ -1,34 +0,0 @@
-// 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.
-
-// ignore-tidy-linelength
-
-use std::cmp::PartialEq;
-
-trait Hahaha: PartialEq + PartialEq {
-    //~^ ERROR trait `PartialEq` already appears in the list of bounds
-}
-
-struct Lol(isize);
-
-impl Hahaha for Lol { }
-
-impl PartialEq for Lol {
-    fn eq(&self, other: &Lol) -> bool { **self != **other }
-    fn ne(&self, other: &Lol) -> bool { **self == **other }
-}
-
-fn main() {
-    if Lol(2) == Lol(4) {
-        println!("2 == 4");
-    } else {
-        println!("2 != 4");
-    }
-}
index d0da51373d926fe599ee84da402673be3913f5d9..55a793f7480a42e1db237844f544e8271d6c0a10 100644 (file)
@@ -9,12 +9,14 @@
 // except according to those terms.
 
 #![feature(unboxed_closures)]
-#![feature(box_syntax)]
 
 fn id<T>(t: T) -> T { t }
 
 fn f<'r, T>(v: &'r T) -> Box<FnMut() -> T + 'r> {
-    id(box || *v) //~ ERROR cannot infer
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    id(Box::new(|| *v))
+        //~^ ERROR `v` does not live long enough
+        //~| ERROR cannot move out of borrowed content
 }
 
 fn main() {
index 6d4777be40b640829dd9bff83ec5c5d1a285b9a0..a1804b5a2689d92978d5a406bf73a3e3c26657fa 100644 (file)
@@ -11,7 +11,7 @@
 fn bar(int_param: usize) {}
 
 fn main() {
-    let foo: [u8; 4] = [1u8; 4_usize];
+    let foo: [u8; 4] = [1; 4];
     bar(foo);
     //~^ ERROR mismatched types
     //~| expected `usize`
index 4d721ad76666dab6c2482a1e207cb0ce31542522..c27362eea3e3c6cea897f9fe8ac073de693fc3d6 100644 (file)
@@ -8,13 +8,12 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 trait Foo { fn foo(&self) {} }
 impl Foo for u8 {}
 
 fn main() {
-    let r: Box<Foo> = box 5;
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let r: Box<Foo> = Box::new(5);
     let _m: Box<Foo> = r as Box<Foo>;
     //~^ ERROR `core::marker::Sized` is not implemented for the type `Foo`
 }
index 30d3ab17a463e6622480b0e22fbf7478b7b225a1..08c5cae9f5f79b1ece1168829e748fa7ac4a551c 100644 (file)
@@ -8,13 +8,15 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(rustc_attrs)]
 #![allow(dead_code)]
 
 // Matching against NaN should result in a warning
 
 use std::f64::NAN;
 
-fn main() {
+#[rustc_error]
+fn main() { //~ ERROR compilation successful
     let x = NAN;
     match x {
         NAN => {},
@@ -27,7 +29,3 @@ fn main() {
     };
     //~^^^ WARNING unmatchable NaN in pattern, use the is_nan method in a guard instead
 }
-
-// At least one error is needed so that compilation fails
-#[static_assert]
-static B: bool = false; //~ ERROR static assertion failed
index b6643f439529b2a76c6b62a73ea4676dce30dc17..9c019f6ec47fb91a1d17733f737fd44083f7cc58 100644 (file)
@@ -32,17 +32,17 @@ trait UnusedTrait : MarkerTrait {
 
 impl CtxtFn for usize {
     fn f8(self, i: usize) -> usize {
-        i * 4_usize
+        i * 4
     }
 
     fn f9(i: usize) -> usize {
-        i * 4_usize
+        i * 4
     }
 }
 
 impl OtherTrait for usize {
     fn f9(i: usize) -> usize {
-        i * 8_usize
+        i * 8
     }
 }
 
index 7bb4aac23d65cebe30bb5c1857b80dd29c0dfd88..400806c3a5fa6cbfe7110e1b887212ac5be62181 100644 (file)
@@ -23,16 +23,16 @@ fn main() {
         _ => ()
     }
 
-    match &Some(42i32) {
+    match &Some(42) {
         Some(x) => (),
         //~^ ERROR mismatched types
-        //~| expected `&core::option::Option<i32>`
+        //~| expected `&core::option::Option<_>`
         //~| found `core::option::Option<_>`
         //~| expected &-ptr
         //~| found enum `core::option::Option`
         None => ()
         //~^ ERROR mismatched types
-        //~| expected `&core::option::Option<i32>`
+        //~| expected `&core::option::Option<_>`
         //~| found `core::option::Option<_>`
         //~| expected &-ptr
         //~| found enum `core::option::Option`
index b575144f637f1e73629df653cb0ae1ea8a3974c2..fd0789421e0045fb4a5c45f25076c139a8ac7e2c 100644 (file)
@@ -21,7 +21,7 @@ impl<T:Copy> Foo for T {
 fn take_param<T:Foo>(foo: &T) { }
 
 fn main() {
-    let x = box 3;
+    let x: Box<_> = box 3;
     take_param(&x);
     //~^ ERROR the trait `core::marker::Copy` is not implemented
 }
index 0072b1228af486d49b47c8e20f3c41c8dd8b83bc..52ca24d0f547a7fe20a4177bdd25f5f19453c630 100644 (file)
@@ -24,12 +24,12 @@ impl<T:Copy> Foo for T {
 fn take_param<T:Foo>(foo: &T) { }
 
 fn a() {
-    let x = box 3;
+    let x: Box<_> = box 3;
     take_param(&x); //~ ERROR `core::marker::Copy` is not implemented
 }
 
 fn b() {
-    let x = box 3;
+    let x: Box<_> = box 3;
     let y = &x;
     let z = &x as &Foo; //~ ERROR `core::marker::Copy` is not implemented
 }
index e6041cddeadb58adb75ac51e95abb70d7faf5352..c370aa4b8fb1aa6b6d7a6643c2dc8da19f9db319 100644 (file)
@@ -16,7 +16,7 @@ fn foo(_x: Rc<usize>) {}
 fn bar<F:FnOnce() + Send>(_: F) { }
 
 fn main() {
-    let x = Rc::new(3_usize);
+    let x = Rc::new(3);
     bar(move|| foo(x));
     //~^ ERROR `core::marker::Send` is not implemented
 }
index fac518c7635692822d1e0e8746d3a8613663baea..0a8e4514b4334294289cafd117bfa309e3ae7a28 100644 (file)
@@ -24,7 +24,7 @@ fn iter(&'r self) -> Range<usize> {
 fn check<'r, I: Iterator<Item=usize>, T: Itble<'r, usize, I>>(cont: &T) -> bool {
 //~^ HELP: consider using an explicit lifetime parameter as shown: fn check<'r, I: Iterator<Item = usize>, T: Itble<'r, usize, I>>(cont: &'r T)
     let cont_iter = cont.iter(); //~ ERROR: cannot infer
-    let result = cont_iter.fold(Some(0u16), |state, val| {
+    let result = cont_iter.fold(Some(0), |state, val| {
         state.map_or(None, |mask| {
             let bit = 1 << val;
             if mask & bit == 0 {Some(mask|bit)} else {None}
index 35f93c13fb5e23792d071df8a27293f168a4fb5d..555cc2b9a7aad95c8c43b10932550e08154b65c8 100644 (file)
@@ -11,5 +11,4 @@
 extern {
     #[linkage = "extern_weak"] static foo: isize;
     //~^ ERROR: the `linkage` attribute is experimental and not portable
-    //~^^ ERROR: the `linkage` attribute is experimental and not portable
 }
index f304c26efb5417fccc7b3c60124e18059390bb8e..8441fb3ade9a8ea9cc002d3e309338c0386b9803 100644 (file)
@@ -63,6 +63,6 @@ fn field_match_in_let(f: Bar) -> bool {
 fn main() {
     field_read(Foo { x: 1, b: false, marker: std::marker::NoCopy });
     field_match_in_patterns(XYZ::Z);
-    field_match_in_let(Bar { x: 42_usize, b: true, _guard: () });
+    field_match_in_let(Bar { x: 42, b: true, _guard: () });
     let _ = Baz { x: 0 };
 }
index 57252dd58d7144a3d46eb407e494208916eb6d5d..a4eb1630afe19c00f993df2f6aa67a1ea1270e85 100644 (file)
@@ -10,7 +10,7 @@
 //
 // regression test for #8005
 
-macro_rules! test { () => { fn foo() -> i32 { 1i32; } } }
+macro_rules! test { () => { fn foo() -> i32 { 1; } } }
                                            //~^ ERROR not all control paths return a value
                                            //~^^ HELP consider removing this semicolon
 
index 985eb1cd7babcb556487c770e122cb82f1dc83e2..6fcab380030331417ffe56711e8eb3630ce9a15f 100644 (file)
@@ -11,7 +11,7 @@
 #![feature(box_syntax)]
 
 fn main() {
-    let x = box 5;
+    let x: Box<_> = box 5;
     let y = x;
     println!("{}", *x); //~ ERROR use of moved value: `*x`
     y.clone();
index 13dbab12b774270a7242aba28419b6c85a961044..e8d9f444cefc6d687dee1f6ba169d3d08c7533f4 100644 (file)
@@ -16,5 +16,5 @@
 extern crate macro_non_reexport_2;
 
 fn main() {
-    assert_eq!(reexported!(), 3_usize);  //~ ERROR macro undefined
+    assert_eq!(reexported!(), 3);  //~ ERROR macro undefined
 }
index dc8f4fadc76c0a3185d14d80f3e2aaade7d38c34..26de51a7cf8c321e4273f19b75527acb1b4f27f7 100644 (file)
@@ -18,5 +18,5 @@
 extern crate macro_reexport_1;
 
 fn main() {
-    assert_eq!(reexported!(), 3_usize);  //~ ERROR macro undefined
+    assert_eq!(reexported!(), 3);  //~ ERROR macro undefined
 }
diff --git a/src/test/compile-fail/malformed-derive-entry.rs b/src/test/compile-fail/malformed-derive-entry.rs
new file mode 100644 (file)
index 0000000..62dbc21
--- /dev/null
@@ -0,0 +1,25 @@
+// Copyright 2015 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.
+
+#[derive(Copy(Bad))]
+//~^ ERROR malformed `derive` entry
+struct Test1;
+
+#[derive(Copy="bad")]
+//~^ ERROR malformed `derive` entry
+struct Test2;
+
+#[derive()]
+//~^ WARNING empty trait list
+struct Test3;
+
+#[derive]
+//~^ WARNING empty trait list
+struct Test4;
index 254a797ef1cd0a54462062b634db348fcf9d0e2b..214a5e5e3eb115c4878422d3d978bd5b803059ea 100644 (file)
@@ -8,6 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(plugin)]
 #![plugin] //~ ERROR malformed plugin attribute
 
 fn main() {}
index 884087b7bc534204f97f9c0513fc1102077962f6..1b112608beeb2003fc00091222574b4a2c55f305 100644 (file)
@@ -8,6 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(plugin)]
 #![plugin="bleh"] //~ ERROR malformed plugin attribute
 
 fn main() {}
index 4885bb901df681fd68abd6daeb35db9aea4b5642..0c948831de217a6ce30c9af993fe7b7dc6c19820 100644 (file)
@@ -8,6 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(plugin)]
 #![plugin(foo="bleh")] //~ ERROR malformed plugin attribute
 
 fn main() {}
index 6e8719eeaceda58e6ffce825b5805468cdc8f542..e298a0f62cd81882ab9e47920f4ac74347b58e82 100644 (file)
@@ -26,6 +26,7 @@ impl<K, V> Map<K, V> for HashMap<K, V> {}
 fn main() {
     let x: Box<HashMap<isize, isize>> = box HashMap::new();
     let x: Box<Map<isize, isize>> = x;
-    let y: Box<Map<usize, isize>> = box x;
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let y: Box<Map<usize, isize>> = Box::new(x);
     //~^ ERROR the trait `Map<usize, isize>` is not implemented
 }
index 7b6868af805e52cea3e31325ae456cee3ce3209a..57a96bb9a26ea4febfddf3fd54dc250e5b414194 100644 (file)
@@ -23,9 +23,9 @@ fn main() {
                  //~| found `Foo`
                  //~| expected &-ptr
                  //~| found struct `Foo`
-    Foo::bar(&42i32); //~  ERROR mismatched types
+    Foo::bar(&42); //~  ERROR mismatched types
                       //~| expected `&Foo`
-                      //~| found `&i32`
+                      //~| found `&_`
                       //~| expected struct `Foo`
-                      //~| found i32
+                      //~| found integral variable
 }
index 5d29d0e1fd083914964e45c8bb686ab5da2a082f..068bfa3cd7c7b0728cdee3600590a4d9182e5292 100644 (file)
@@ -11,7 +11,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let x = box 1;
+    let x: Box<_> = box 1;
 
     let v = (1, 2);
 
index 23af25797975f3720843c415adf2ef098ffbd48a..984963b2f830ee2246e297175db744f6d1d3eb47 100644 (file)
@@ -11,7 +11,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let x = box 1;
+    let x: Box<_> = box 1;
 
     let v = (1, 2);
 
index 7e3a85569d413f5ea39a489fa54df1c095de9434..b7393666719630029aa400475ed9bb880ac0acae 100644 (file)
@@ -13,7 +13,7 @@
 struct Foo(Box<isize>);
 
 fn main() {
-    let x = (box 1,);
+    let x: (Box<_>,) = (box 1,);
     let y = x.0;
     let z = x.0; //~ ERROR use of moved value: `x.0`
 
index f410541f0b7e93a15eefae799cf4e74a71771e62..5af326b4298499ed42bfdd5bb505e75657b104d9 100644 (file)
@@ -12,7 +12,6 @@
 // bound must be noncopyable. For details see
 // http://smallcultfollowing.com/babysteps/blog/2013/04/30/the-case-of-the-recurring-closure/
 
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 struct R<'a> {
@@ -41,7 +40,8 @@ fn innocent_looking_victim() {
 }
 
 fn conspirator<F>(mut f: F) where F: FnMut(&mut R, bool) {
-    let mut r = R {c: box f};
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let mut r = R {c: Box::new(f)};
     f(&mut r, false) //~ ERROR use of moved value
 }
 
index 2cf6e67a90958baa9742be4d6004340c5bf4f774..6829cd574e1b00114c716a17c851bf14ec930405 100644 (file)
@@ -13,7 +13,7 @@
 fn f(_: &mut isize) {}
 
 fn main() {
-    let mut x = box 3;
+    let mut x: Box<_> = box 3;
     f(x)    //~ ERROR mismatched types
 }
 
index 6de69a9adb0c9a3b56d32b3397176a8d2eb201d1..9eb24c81960cacc29e81d41f3101a56ef298b8b6 100644 (file)
@@ -9,21 +9,21 @@
 // except according to those terms.
 
 fn main() {
-    let foo = &mut 1i32;
+    let foo = &mut 1;
 
     // (separate lines to ensure the spans are accurate)
 
      let &_ //~  ERROR mismatched types
-            //~| expected `&mut i32`
+            //~| expected `&mut _`
             //~| found `&_`
             //~| values differ in mutability
         = foo;
     let &mut _ = foo;
 
-    let bar = &1i32;
+    let bar = &1;
     let &_ = bar;
     let &mut _ //~  ERROR mismatched types
-               //~| expected `&i32`
+               //~| expected `&_`
                //~| found `&mut _`
                //~| values differ in mutability
          = bar;
index b6744d4b33a1021d7b133dbdd4a9e618cc6cc7ae..46af3a862c28f623c9801e974f7675e46275b134 100644 (file)
@@ -29,6 +29,6 @@ fn cat(in_x : usize, in_y : isize) -> cat {
 }
 
 fn main() {
-  let nyan : cat = cat(52_usize, 99);
+  let nyan : cat = cat(52, 99);
   nyan.eat();
 }
index 94b1047f85ed3720f95b32bace33af613f42ed3d..c163dc2b4d228d770398740842ca6ba649e2e7c0 100644 (file)
@@ -21,6 +21,6 @@ fn cat(in_x : usize, in_y : isize) -> cat {
 }
 
 fn main() {
-  let nyan : cat = cat(52_usize, 99);
+  let nyan : cat = cat(52, 99);
   nyan.how_hungry = 0; //~ ERROR cannot assign
 }
index 14d2c8d0326a1546920049d9556ad53cf874bbe9..59e910ec6afdabbca9766d8f5bdaf1368bd94d87 100644 (file)
@@ -13,6 +13,7 @@
 fn main() {
     fn bar(n: isize) {
         let _x: [isize; n];
-        //~^ ERROR expected constant expr for array length: non-constant path in constant expr
+        //~^ ERROR no type for local variable
+        //~| ERROR array length constant evaluation error: non-constant path in constant expr
     }
 }
index 0eb91e0419a1da232d991ef9da75f0f093a431ed..3ed91459ae94c70ae7e24b9da9a94a9e1706daee 100644 (file)
@@ -27,7 +27,7 @@ fn struct_with_a_nested_enum_and_vector() {
         Foo { first: true, second: None } => (),
         Foo { first: true, second: Some(_) } => (),
         Foo { first: false, second: None } => (),
-        Foo { first: false, second: Some([1_usize, 2_usize, 3_usize, 4_usize]) } => ()
+        Foo { first: false, second: Some([1, 2, 3, 4]) } => ()
     }
 }
 
index d85f58edc90d451d7f913936d2bbf8bd9e0b73f2..7a7912b06f88715ac012be4a7536dffef15bd6e6 100644 (file)
@@ -8,6 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(static_assert)]
 #![allow(dead_code)]
 
 #[static_assert]
index 4b261d89888dcd3b02060865863568edab2cad6a..59508d6ac95f9645d2c3a67af396e0eaf29d1e98 100644 (file)
@@ -12,4 +12,4 @@
 
 enum blah { a(isize, isize, usize), b(isize, isize), }
 
-fn main() { match blah::a(1, 1, 2_usize) { blah::a(_, x, y) | blah::b(x, y) => { } } }
+fn main() { match blah::a(1, 1, 2) { blah::a(_, x, y) | blah::b(x, y) => { } } }
diff --git a/src/test/compile-fail/phantom-oibit.rs b/src/test/compile-fail/phantom-oibit.rs
new file mode 100644 (file)
index 0000000..c912d08
--- /dev/null
@@ -0,0 +1,41 @@
+// Copyright 2015 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.
+
+// Ensure that OIBIT checks `T` when it encounters a `PhantomData<T>` field, instead of checking
+// the `PhantomData<T>` type itself (which almost always implements a "default" trait
+// (`impl Trait for ..`))
+
+#![feature(optin_builtin_traits)]
+
+use std::marker::{MarkerTrait, PhantomData};
+
+unsafe trait Zen: MarkerTrait {}
+
+unsafe impl Zen for .. {}
+
+unsafe impl<'a, T: 'a> Zen for &'a T where T: Sync {}
+
+struct Guard<'a, T: 'a> {
+    _marker: PhantomData<&'a T>,
+}
+
+struct Nested<T>(T);
+
+fn is_zen<T: Zen>(_: T) {}
+
+fn not_sync<T>(x: Guard<T>) {
+    is_zen(x)  //~ error: the trait `core::marker::Sync` is not implemented for the type `T`
+}
+
+fn nested_not_sync<T>(x: Nested<Guard<T>>) {
+    is_zen(x)  //~ error: the trait `core::marker::Sync` is not implemented for the type `T`
+}
+
+fn main() {}
index ccda5cbdceba6b2e156dcf775ba51a2641026a46..efa352e386d4d679806231a779fe891bd5610990 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(plugin)]
+
 #[plugin]  //~ ERROR #[plugin] on `extern crate` is deprecated
 //~^ HELP use a crate attribute instead, i.e. #![plugin(std)]
 extern crate std;
index df570fd46479296c9c92a71c0a0656df847de92c..a7f6a514b96af53082fcc7d33396c0d7c0b25061 100644 (file)
@@ -9,7 +9,6 @@
 // except according to those terms.
 
 // aux-build:privacy-tuple-struct.rs
-// ignore-fast
 
 extern crate "privacy-tuple-struct" as other;
 
index ccbdd52a98328dc769f1b9268852d2e50a313c4a..16510c2c8c99cb01f07743f86cbd0c1508a5ca3f 100644 (file)
@@ -30,6 +30,6 @@ pub fn cat(in_x : usize, in_y : isize) -> cat {
 }
 
 fn main() {
-  let nyan : kitties::cat = kitties::cat(52_usize, 99);
+  let nyan : kitties::cat = kitties::cat(52, 99);
   nyan.nap();
 }
index 243d835d46e6213d7f8bf9143872d899b5404223..fb4491a63757b4e27b93f6d24db04fd3dfc113db 100644 (file)
@@ -13,7 +13,7 @@
 use cci_class::kitties::cat;
 
 fn main() {
-  let nyan : cat = cat(52_usize, 99);
-  assert!((nyan.meows == 52_usize));
+  let nyan : cat = cat(52, 99);
+  assert!((nyan.meows == 52));
   //~^ ERROR field `meows` of struct `cci_class::kitties::cat` is private
 }
index a8b6e399418f7ef430f333d95aaa993894594ecb..e7b34d6d1bc38609bbb11d562d6409046d19b5e7 100644 (file)
@@ -20,7 +20,7 @@ pub fn main() {
     //~^ ERROR the trait `core::num::Int` is not implemented for the type `f32`
 
     // Unsized type.
-    let arr: &[_] = &[1u32, 2, 3];
+    let arr: &[_] = &[1, 2, 3];
     let range = *arr..;
     //~^ ERROR the trait `core::marker::Sized` is not implemented
 }
index 2da414befd8979312cc7b1c3e18466197d5f9f7a..1bb2bb5a15450f3aa774ded692b1ac6f0e610626 100644 (file)
 // Test that attempts to implicitly coerce a value into an
 // object respect the lifetime bound on the object type.
 
-#![feature(box_syntax)]
-
 trait Foo : ::std::marker::MarkerTrait {}
 impl<'a> Foo for &'a [u8] {}
 
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+
 fn a(v: &[u8]) -> Box<Foo + 'static> {
-    let x: Box<Foo + 'static> = box v; //~ ERROR does not fulfill the required lifetime
+    let x: Box<Foo + 'static> = Box::new(v);
+    //~^ ERROR cannot infer an appropriate lifetime due to conflicting
     x
 }
 
 fn b(v: &[u8]) -> Box<Foo + 'static> {
-    box v //~ ERROR does not fulfill the required lifetime
+    Box::new(v)
+        //~^ ERROR cannot infer an appropriate lifetime due to conflicting
 }
 
 fn c(v: &[u8]) -> Box<Foo> {
     // same as previous case due to RFC 599
 
-    box v //~ ERROR does not fulfill the required lifetime
+    Box::new(v)
+        //~^ ERROR cannot infer an appropriate lifetime due to conflicting
 }
 
 fn d<'a,'b>(v: &'a [u8]) -> Box<Foo+'b> {
-    box v //~ ERROR does not fulfill the required lifetime
+    Box::new(v)
+        //~^ ERROR cannot infer an appropriate lifetime due to conflicting
 }
 
 fn e<'a:'b,'b>(v: &'a [u8]) -> Box<Foo+'b> {
-    box v // OK, thanks to 'a:'b
+    Box::new(v) // OK, thanks to 'a:'b
 }
 
 fn main() { }
index 45e468b3ab06676c446ac7d1de41d822573c7270..04ee0526403fbe9dfedf2c8ca39205e2e2a8f9fb 100644 (file)
@@ -15,18 +15,18 @@ struct dog {
 impl dog {
     pub fn chase_cat(&mut self) {
         let p: &'static mut usize = &mut self.cats_chased; //~ ERROR cannot infer
-        *p += 1_usize;
+        *p += 1;
     }
 
     pub fn chase_cat_2(&mut self) {
         let p: &mut usize = &mut self.cats_chased;
-        *p += 1_usize;
+        *p += 1;
     }
 }
 
 fn dog() -> dog {
     dog {
-        cats_chased: 0_usize
+        cats_chased: 0
     }
 }
 
index 8cc2dd6afc645bc4203de7a03dd814c20bc0ee77..28491f1155c367b204ae52d128c2d4ca1698c3cf 100644 (file)
@@ -18,7 +18,7 @@ impl dog {
     pub fn chase_cat(&mut self) {
         let _f = || {
             let p: &'static mut usize = &mut self.food; //~ ERROR cannot infer
-            *p = 3_usize;
+            *p = 3;
         };
     }
 }
index 979c1e997d03c8b694c2bcb78605f5fcade1e610..72a024e563c6f6bc06caa285fe9b20879752c471 100644 (file)
@@ -10,6 +10,8 @@
 
 #![feature(box_syntax)]
 
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+
 use std::marker::MarkerTrait;
 
 trait X : MarkerTrait {}
@@ -24,48 +26,48 @@ trait Iter {
 fn bad1<T: Iter>(v: T) -> Box<X+'static>
 {
     let item = v.into_item();
-    box item //~ ERROR associated type `<T as Iter>::Item` may not live long enough
+    Box::new(item) //~ ERROR associated type `<T as Iter>::Item` may not live long enough
 }
 
 fn bad2<T: Iter>(v: T) -> Box<X+'static>
     where Box<T::Item> : X
 {
-    let item = box v.into_item();
-    box item //~ ERROR associated type `<T as Iter>::Item` may not live long enough
+    let item: Box<_> = box v.into_item();
+    Box::new(item) //~ ERROR associated type `<T as Iter>::Item` may not live long enough
 }
 
 fn bad3<'a, T: Iter>(v: T) -> Box<X+'a>
 {
     let item = v.into_item();
-    box item //~ ERROR associated type `<T as Iter>::Item` may not live long enough
+    Box::new(item) //~ ERROR associated type `<T as Iter>::Item` may not live long enough
 }
 
 fn bad4<'a, T: Iter>(v: T) -> Box<X+'a>
     where Box<T::Item> : X
 {
-    let item = box v.into_item();
-    box item //~ ERROR associated type `<T as Iter>::Item` may not live long enough
+    let item: Box<_> = box v.into_item();
+    Box::new(item) //~ ERROR associated type `<T as Iter>::Item` may not live long enough
 }
 
 fn ok1<'a, T: Iter>(v: T) -> Box<X+'a>
     where T::Item : 'a
 {
     let item = v.into_item();
-    box item // OK, T::Item : 'a is declared
+    Box::new(item) // OK, T::Item : 'a is declared
 }
 
 fn ok2<'a, T: Iter>(v: &T, w: &'a T::Item) -> Box<X+'a>
     where T::Item : Clone
 {
     let item = Clone::clone(w);
-    box item // OK, T::Item : 'a is implied
+    Box::new(item) // OK, T::Item : 'a is implied
 }
 
 fn ok3<'a, T: Iter>(v: &'a T) -> Box<X+'a>
     where T::Item : Clone + 'a
 {
     let item = Clone::clone(v.as_item());
-    box item // OK, T::Item : 'a was declared
+    Box::new(item) // OK, T::Item : 'a was declared
 }
 
 fn meh1<'a, T: Iter>(v: &'a T) -> Box<X+'a>
@@ -78,7 +80,7 @@ fn meh1<'a, T: Iter>(v: &'a T) -> Box<X+'a>
     // T::Item`. But we're not that smart at present.
 
     let item = Clone::clone(v.as_item());
-    box item //~ ERROR associated type `<T as Iter>::Item` may not live
+    Box::new(item) //~ ERROR associated type `<T as Iter>::Item` may not live
 }
 
 fn main() {}
index 655ac6f66c97db2ac173069431fcb36ce6203896..eebf93bc89377995173e7a3098eb7b4790203f53 100644 (file)
@@ -8,32 +8,32 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 
 trait X { fn foo(&self) {} }
 
 fn p1<T>(v: T) -> Box<X+'static>
     where T : X
 {
-    box v //~ ERROR parameter type `T` may not live long enough
+    Box::new(v) //~ ERROR parameter type `T` may not live long enough
 }
 
 fn p2<T>(v: Box<T>) -> Box<X+'static>
     where Box<T> : X
 {
-    box v //~ ERROR parameter type `T` may not live long enough
+    Box::new(v) //~ ERROR parameter type `T` may not live long enough
 }
 
 fn p3<'a,T>(v: T) -> Box<X+'a>
     where T : X
 {
-    box v //~ ERROR parameter type `T` may not live long enough
+    Box::new(v) //~ ERROR parameter type `T` may not live long enough
 }
 
 fn p4<'a,T>(v: Box<T>) -> Box<X+'a>
     where Box<T> : X
 {
-    box v //~ ERROR parameter type `T` may not live long enough
+    Box::new(v) //~ ERROR parameter type `T` may not live long enough
 }
 
 fn main() {}
index 4c361427bf37c6e0507bccfc84527363118ed9d1..ad2dc28afef02f3be21e4ca19cf918fa33fba6c9 100644 (file)
@@ -14,8 +14,8 @@ enum ast<'a> {
 }
 
 fn build() {
-    let x = ast::num(3_usize);
-    let y = ast::num(4_usize);
+    let x = ast::num(3);
+    let y = ast::num(4);
     let z = ast::add(&x, &y);
     compute(&z);
 }
index 58386c319f8abaaf107f3b7b5d339cd282a3725b..f114a8bc7ce668bfe6a35ac4e3141cf41709bed1 100644 (file)
@@ -8,7 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 
 fn ignore<T>(t: T) {}
 
@@ -16,17 +16,17 @@ fn nested<'x>(x: &'x isize) {
     let y = 3;
     let mut ay = &y;
 
-    ignore::<Box<for<'z> FnMut(&'z isize)>>(box |z| {
+    ignore::<Box<for<'z> FnMut(&'z isize)>>(Box::new(|z| {
         ay = x; //~ ERROR cannot infer
         ay = &y;
         ay = z;
-    });
+    }));
 
-    ignore::< Box<for<'z> FnMut(&'z isize) -> &'z isize>>(box |z| {
+    ignore::< Box<for<'z> FnMut(&'z isize) -> &'z isize>>(Box::new(|z| {
         if false { return x; }  //~ ERROR cannot infer an appropriate lifetime for automatic
         if false { return ay; }
         return z;
-    });
+    }));
 }
 
 fn main() {}
index da839d72172619e19ecf7be11edc97235752b54e..ae9ceb600d45c1bb5be47b430b21453dd0746229 100644 (file)
@@ -9,8 +9,8 @@
 // except according to those terms.
 
 fn main() {
-    let a0 = 0u8;
-    let f = 1u8;
+    let a0 = 0;
+    let f = 1;
     let mut a1 = &a0;
     match (&a1,) {
         (&ref b0,) => {
index 7ea4d1c7507afc5ae434ac63d07a753f10d489ba..3c137133c9867ca077ec86420b3d0c6e3716cce6 100644 (file)
@@ -8,17 +8,17 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 
 fn borrowed_proc<'a>(x: &'a isize) -> Box<FnMut()->(isize) + 'a> {
     // This is legal, because the region bound on `proc`
     // states that it captures `x`.
-    box move|| { *x }
+    Box::new(move|| { *x })
 }
 
 fn static_proc(x: &isize) -> Box<FnMut()->(isize) + 'static> {
     // This is illegal, because the region bound on `proc` is 'static.
-    box move|| { *x } //~ ERROR cannot infer
+    Box::new(move|| { *x }) //~ ERROR captured variable `x` does not outlive the enclosing closure
 }
 
 fn main() { }
index aa20efa5a12b157822f468aa47f73f795654d87c..1e2224eafaeb057567115767d28744583d64cb76 100644 (file)
@@ -15,7 +15,7 @@
 fn main() {
     // Unboxed closure case
     {
-        let mut x = 0_usize;
+        let mut x = 0;
         let mut f = || &mut x; //~ ERROR cannot infer
         let x = f();
         let y = f();
index 97b51fdb3250800ce687bac0731d5f1088e76424..a30d8471a31788e6136a8498f009b8539722a075 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 struct closure_box<'a> {
@@ -20,9 +19,10 @@ fn box_it<'r>(x: Box<FnMut() + 'r>) -> closure_box<'r> {
 }
 
 fn main() {
-    let cl_box = {
+    let mut cl_box = {
         let mut i = 3;
-        box_it(box || i += 1) //~ ERROR cannot infer
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        box_it(Box::new(|| i += 1)) //~ ERROR `i` does not live long enough
     };
     cl_box.cl.call_mut(());
 }
index b45a37d26e58a2d0c41f7df1fd60dcd9924110f3..01439ce5e68775f83454622d295e33ac0aa92ac2 100644 (file)
@@ -34,7 +34,7 @@ fn get_v(gc: Box<get_ctxt>) -> usize {
 }
 
 fn main() {
-    let ctxt = ctxt { v: 22_usize };
+    let ctxt = ctxt { v: 22 };
     let hc = has_ctxt { c: &ctxt };
-    assert_eq!(get_v(box hc as Box<get_ctxt>), 22_usize);
+    assert_eq!(get_v(box hc as Box<get_ctxt>), 22);
 }
diff --git a/src/test/compile-fail/reserved-attr-on-macro.rs b/src/test/compile-fail/reserved-attr-on-macro.rs
new file mode 100644 (file)
index 0000000..db8f82a
--- /dev/null
@@ -0,0 +1,18 @@
+// Copyright 2015 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.
+
+#[rustc_attribute_should_be_reserved] //~ ERROR attributes with the prefix `rustc_` are reserved
+macro_rules! foo {
+    () => (());
+}
+
+fn main() {
+    foo!();
+}
old mode 100755 (executable)
new mode 100644 (file)
index abbcd7e..fe03ca8
 fn main() {
     let bad = {
         let x = 1;
-        let y = &x;
+        let y = &x; //~ ERROR `x` does not live long enough
 
-        thread::scoped(|| { //~ ERROR cannot infer an appropriate lifetime
+        thread::scoped(|| {
+            //~^ ERROR `y` does not live long enough
             let _z = y;
         })
     };
diff --git a/src/test/compile-fail/single-derive-attr.rs b/src/test/compile-fail/single-derive-attr.rs
new file mode 100644 (file)
index 0000000..0b1b314
--- /dev/null
@@ -0,0 +1,15 @@
+// Copyright 2015 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.
+
+#[derive_Clone]
+//~^ ERROR attributes of the form `#[derive_*]` are reserved
+struct Test;
+
+pub fn main() {}
index 349e5f4cb5105c433ab38fb9e4fd52c2bf7c933e..d0cfbfbbcccc21adaea08611ed774546c0eba768 100644 (file)
@@ -8,6 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(static_assert)]
 #![allow(dead_code)]
 
 #[static_assert]
index d5e70205e9536f5ffa22f71232c8f5d0fc8b256c..35f840dab0c0cb6a0d7aa7446def00b272269145 100644 (file)
@@ -8,6 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(static_assert)]
 #![allow(dead_code)]
 
 #[static_assert]
index 200aa9891935a3cee037a9c55cdb39a5392385a5..eca22bfdda07a8a1579af54dd3cb380d5d450c6d 100644 (file)
@@ -13,7 +13,7 @@
 fn f<T:'static>(_: T) {}
 
 fn main() {
-    let x = box 3;
+    let x: Box<_> = box 3;
     f(x);
     let x = &3; //~ ERROR borrowed value does not live long enough
     f(x);
index c276228b18ee3552cadd01ab33491abcb2828759..ea6d63ca540ef8a422a2edd344790a770b5f811e 100644 (file)
@@ -26,40 +26,40 @@ fn main() {
     let pt = PointF {
         //~^ ERROR structure constructor specifies a structure of type
         //~| expected f32
-        //~| found i32
-        x: 1i32,
-        y: 2i32,
+        //~| found integral variable
+        x: 1,
+        y: 2,
     };
 
     let pt2 = Point::<f32> {
         //~^ ERROR structure constructor specifies a structure of type
         //~| expected f32
-        //~| found i32
-        x: 3i32,
-        y: 4i32,
+        //~| found integral variable
+        x: 3,
+        y: 4,
     };
 
     let pair = PairF {
         //~^ ERROR structure constructor specifies a structure of type
         //~| expected f32
-        //~| found i32
-        x: 5i32,
-        y: 6i32,
+        //~| found integral variable
+        x: 5,
+        y: 6,
     };
 
     let pair2 = PairF::<i32> {
         //~^ ERROR structure constructor specifies a structure of type
         //~| expected f32
-        //~| found i32
-        x: 7i32,
-        y: 8i32,
+        //~| found integral variable
+        x: 7,
+        y: 8,
     };
 
     let pt3 = PointF::<i32> {
         //~^ ERROR wrong number of type arguments
         //~| ERROR structure constructor specifies a structure of type
-        x: 9i32,
-        y: 10i32,
+        x: 9,
+        y: 10,
     };
 }
 
index 9c1d318d5889990efb92f1d33bf6abcd0be641be..5c1270aa0e43d8f25adb1d42969871318dfc4c97 100644 (file)
@@ -12,6 +12,6 @@
 
 fn f() -> isize { return g(); }
 
-fn g() -> usize { return 0_usize; }
+fn g() -> usize { return 0; }
 
 fn main() { let y = f(); }
index 1ddfc5b7ccd487d9369e73b06df65189f4fc6292..b25af522b2476e35759af8a255ade6225020a8c0 100644 (file)
@@ -8,8 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 struct Struct {
     person: &'static str
 }
@@ -25,7 +23,8 @@ fn f(&self, x: &'static str) {
 }
 
 fn main() {
-    let s: Box<Trait<isize>> = box Struct { person: "Fred" };
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let s: Box<Trait<isize>> = Box::new(Struct { person: "Fred" });
     //~^ ERROR the trait `Trait<isize>` is not implemented for the type `Struct`
     s.f(1);
 }
index 7b426a4c0331545da4961f70a408d13627fdb7cd..bbe256d1c8fd20cd36d5e0ce303556a72ecea839 100644 (file)
@@ -8,8 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 struct Struct {
     person: &'static str
 }
@@ -27,6 +25,7 @@ fn f(&self, x: &'static str) {
 fn main() {
     let person = "Fred".to_string();
     let person: &str = &person;  //~ ERROR `person` does not live long enough
-    let s: Box<Trait<&'static str>> = box Struct { person: person };
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let s: Box<Trait<&'static str>> = Box::new(Struct { person: person });
 }
 
diff --git a/src/test/compile-fail/traits-assoc-type-in-supertrait-bad.rs b/src/test/compile-fail/traits-assoc-type-in-supertrait-bad.rs
new file mode 100644 (file)
index 0000000..971869b
--- /dev/null
@@ -0,0 +1,26 @@
+// Copyright 2015 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.
+
+// Test case where an associated type is referenced from within the
+// supertrait definition, and the impl makes the wrong
+// associations. Issue #20220.
+
+use std::vec::IntoIter;
+
+pub trait Foo: Iterator<Item=<Self as Foo>::Key> {
+    type Key;
+}
+
+impl Foo for IntoIter<i32> { //~ ERROR type mismatch
+    type Key = u32;
+}
+
+fn main() {
+}
diff --git a/src/test/compile-fail/traits-issue-23003-overflow.rs b/src/test/compile-fail/traits-issue-23003-overflow.rs
new file mode 100644 (file)
index 0000000..ea41775
--- /dev/null
@@ -0,0 +1,38 @@
+// Copyright 2015 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.
+
+// A variant of traits-issue-23003 in which an infinite series of
+// types are required. This currently creates an overflow. This test
+// is included to ensure that some controlled failure, at least,
+// results -- but it might be that we should adjust the rules somewhat
+// to make this legal. -nmatsakis
+
+use std::marker::PhantomData;
+
+trait Async {
+    type Cancel;
+}
+
+struct Receipt<A:Async> {
+    marker: PhantomData<A>,
+}
+
+struct Complete<B> {
+    core: Option<B>,
+}
+
+impl<B> Async for Complete<B> {
+    type Cancel = Receipt<Complete<Option<B>>>;
+}
+
+fn foo(r: Receipt<Complete<()>>) { }
+//~^ ERROR overflow
+
+fn main() { }
index 0a5aa1b7bd34695cebb9a8451c45d0d5e25eb52f..8fe1f4d2371c42120120c57cf985d960692c75a6 100644 (file)
@@ -33,7 +33,7 @@ fn test<T,U>(_: T, _: U)
 }
 
 fn a() {
-    test(22_i32, std::default::Default::default()); //~ ERROR type annotations required
+    test(22, std::default::Default::default()); //~ ERROR type annotations required
 }
 
 fn main() {}
diff --git a/src/test/compile-fail/traits-repeated-supertrait-ambig.rs b/src/test/compile-fail/traits-repeated-supertrait-ambig.rs
new file mode 100644 (file)
index 0000000..d61ac6f
--- /dev/null
@@ -0,0 +1,53 @@
+// Copyright 2015 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.
+
+// Test a case of a trait which extends the same supertrait twice, but
+// with difference type parameters. Test then that when we don't give
+// enough information to pick between these, no selection is made. In
+// this particular case, the two choices are i64/u64 -- so when we use
+// an integer literal, we wind up falling this literal back to i32.
+// See also `run-pass/trait-repeated-supertrait.rs`.
+
+trait CompareTo<T> {
+    fn same_as(&self, t: T) -> bool;
+}
+
+trait CompareToInts : CompareTo<i64> + CompareTo<u64> {
+}
+
+impl CompareTo<i64> for i64 {
+    fn same_as(&self, t: i64) -> bool { *self == t }
+}
+
+impl CompareTo<u64> for i64 {
+    fn same_as(&self, t: u64) -> bool { *self == (t as i64) }
+}
+
+impl CompareToInts for i64 { }
+
+fn with_obj(c: &CompareToInts) -> bool {
+    c.same_as(22) //~ ERROR `CompareTo<i32>` is not implemented
+}
+
+fn with_trait<C:CompareToInts>(c: &C) -> bool {
+    c.same_as(22) //~ ERROR `CompareTo<i32>` is not implemented
+}
+
+fn with_ufcs1<C:CompareToInts>(c: &C) -> bool {
+    CompareToInts::same_as(c, 22) //~ ERROR `CompareTo<i32>` is not implemented
+}
+
+fn with_ufcs2<C:CompareToInts>(c: &C) -> bool {
+    CompareTo::same_as(c, 22) //~ ERROR `CompareTo<i32>` is not implemented
+}
+
+fn main() {
+    assert_eq!(22_i64.same_as(22), true); //~ ERROR `CompareTo<i32>` is not implemented
+}
index 54b8d551f202e5fee102e8f95591805b10bcc945..c2c41fbbb2aaf16857a721a4a2dd90ec859dfafe 100644 (file)
 struct Point(i32, i32);
 
 fn main() {
-    let origin = Point(0i32, 0i32);
+    let origin = Point(0, 0);
     origin.0;
     origin.1;
     origin.2;
     //~^ ERROR attempted out-of-bounds tuple index `2` on type `Point`
-    let tuple = (0i32, 0i32);
+    let tuple = (0, 0);
     tuple.0;
     tuple.1;
     tuple.2;
-    //~^ ERROR attempted out-of-bounds tuple index `2` on type `(i32, i32)`
+    //~^ ERROR attempted out-of-bounds tuple index `2` on type `(_, _)`
 }
index 3bf0896d990af6fdea1ab8521cf65648695cc6ef..627300a037720b92ba9a45e7981b1f9a985638ee 100644 (file)
 
 // Checking that the compiler reports multiple type errors at once
 
-fn main() { let a: bool = 1i32; let b: i32 = true; }
+fn main() { let a: bool = 1; let b: i32 = true; }
 //~^ ERROR mismatched types
 //~| expected `bool`
-//~| found `i32`
+//~| found `_`
 //~| expected bool
-//~| found i32
+//~| found integral variable
 //~| ERROR mismatched types
 //~| expected `i32`
 //~| found `bool`
index de9623de7cd3a551c56e74a21d878e6a4baa8c55..88d8788d63a3de54bdcdc0f8dc3b1313558f709a 100644 (file)
@@ -23,7 +23,7 @@ fn broken_add<T>(&self, rhs: T) -> Self {
 impl<T: Int> BrokenAdd for T {}
 
 pub fn main() {
-    let foo: u8 = 0u8;
+    let foo: u8 = 0;
     let x: u8 = foo.broken_add("hello darkness my old friend".to_string());
     println!("{}", x);
 }
diff --git a/src/test/compile-fail/typeck-default-trait-impl-cross-crate-coherence.rs b/src/test/compile-fail/typeck-default-trait-impl-cross-crate-coherence.rs
new file mode 100644 (file)
index 0000000..3a29bb9
--- /dev/null
@@ -0,0 +1,34 @@
+// Copyright 2015 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.
+
+// aux-build:typeck-default-trait-impl-cross-crate-coherence-lib.rs
+
+// Test that we do not consider associated types to be sendable without
+// some applicable trait bound (and we don't ICE).
+
+#![feature(optin_builtin_traits)]
+
+extern crate "typeck-default-trait-impl-cross-crate-coherence-lib" as lib;
+
+use lib::DefaultedTrait;
+
+struct A;
+impl DefaultedTrait for (A,) { } //~ ERROR E0321
+
+struct B;
+impl !DefaultedTrait for (B,) { } //~ ERROR E0321
+
+struct C;
+struct D<T>(T);
+impl DefaultedTrait for Box<C> { } //~ ERROR E0321
+impl DefaultedTrait for lib::Something<C> { } //~ ERROR E0321
+impl DefaultedTrait for D<C> { } // OK
+
+fn main() { }
index 10ba8c74164830efeed897659da41a04faa5e99b..a345bd1b65c0ea1f1f7c83ac410dd066e7dfb78c 100644 (file)
@@ -13,6 +13,6 @@
 #![feature(optin_builtin_traits)]
 
 impl Copy for .. {}
-//~^ ERROR cannot create default implementations for traits outside the crate they're defined in; define a new trait instead.
+//~^ ERROR E0318
 
 fn main() {}
index 5bfad94867e2544c4291236bb0d11c17dcda23a9..d4f3cdfd8b7e248eefedc4d3896d13a0101ff235 100644 (file)
@@ -21,7 +21,7 @@ fn test2() -> (_, _) { (5, 5) }
 static TEST3: _ = "test";
 //~^ ERROR the type placeholder `_` is not allowed within types on item signatures
 
-static TEST4: _ = 145u16;
+static TEST4: _ = 145;
 //~^ ERROR the type placeholder `_` is not allowed within types on item signatures
 
 static TEST5: (_, _) = (1, 2);
@@ -74,7 +74,7 @@ fn fn_test2() -> (_, _) { (5, 5) }
     static FN_TEST3: _ = "test";
     //~^ ERROR the type placeholder `_` is not allowed within types on item signatures
 
-    static FN_TEST4: _ = 145u16;
+    static FN_TEST4: _ = 145;
     //~^ ERROR the type placeholder `_` is not allowed within types on item signatures
 
     static FN_TEST5: (_, _) = (1, 2);
index 800126450c9726887796a01a8c5343225e3982ab..564b1b4669f7d0235ea2ed45c1a124b6577485cc 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 // Tests that we can't move out of an unboxed closure environment
@@ -19,31 +18,33 @@ fn to_fn<A,F:Fn<A>>(f: F) -> F { f }
 fn to_fn_mut<A,F:FnMut<A>>(f: F) -> F { f }
 fn to_fn_once<A,F:FnOnce<A>>(f: F) -> F { f }
 
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+
 fn main() {
     // By-ref cases
     {
-        let x = box 0_usize;
+        let x = Box::new(0);
         let f = to_fn(|| drop(x)); //~ ERROR cannot move
     }
     {
-        let x = box 0_usize;
+        let x = Box::new(0);
         let f = to_fn_mut(|| drop(x)); //~ ERROR cannot move
     }
     {
-        let x = box 0_usize;
+        let x = Box::new(0);
         let f = to_fn_once(|| drop(x)); // OK -- FnOnce
     }
     // By-value cases
     {
-        let x = box 0_usize;
+        let x = Box::new(0);
         let f = to_fn(move || drop(x)); //~ ERROR cannot move
     }
     {
-        let x = box 0_usize;
+        let x = Box::new(0);
         let f = to_fn_mut(move || drop(x)); //~ ERROR cannot move
     }
     {
-        let x = box 0_usize;
+        let x = Box::new(0);
         let f = to_fn_once(move || drop(x)); // this one is ok
     }
 }
index b40a91181adde2b63c9ededa0260da8c553ec8a9..5be2738b47eff1c1296ea1829755ded3fab1d51a 100644 (file)
@@ -17,7 +17,7 @@
 fn set(x: &mut usize) { *x = 0; }
 
 fn main() {
-    let x = 0_usize;
+    let x = 0;
     move || x = 1; //~ ERROR cannot assign
     move || set(&mut x); //~ ERROR cannot borrow
     move || x = 1; //~ ERROR cannot assign
index 59c8495371852c809d39db541b7d4a5f5ede996e..eee1b6ce30b5e7467aa53ef15c5700b248f71b08 100644 (file)
@@ -14,7 +14,7 @@
 // reference cannot escape the region of that variable.
 fn main() {
     let _f = {
-        let x = 0_usize;
-        || x //~ ERROR cannot infer an appropriate lifetime due to conflicting requirements
+        let x = 0;
+        || x //~ ERROR `x` does not live long enough
     };
 }
index 1191cfa2600b8a231f1d5d3c5dc4e148e492fcf5..372f3277931e1ff7eab1deaa6cce0605a78f6b29 100644 (file)
@@ -14,7 +14,7 @@
 // cause borrow conflicts.
 
 fn main() {
-    let mut x = 0_usize;
+    let mut x = 0;
     let f = || x += 1;
     let _y = x; //~ ERROR cannot use `x` because it was mutably borrowed
 }
index 650bb17bb7758f9ce60d81d2dcc7ec38ff7cab7b..35052ec0bd507b2334336590723c349eb6680fd5 100644 (file)
@@ -20,21 +20,21 @@ fn to_fn<A,F:Fn<A>>(f: F) -> F { f }
 fn to_fn_mut<A,F:FnMut<A>>(f: F) -> F { f }
 
 fn a() {
-    let n = 0u8;
+    let n = 0;
     let mut f = to_fn_mut(|| { //~ ERROR closure cannot assign
         n += 1;
     });
 }
 
 fn b() {
-    let mut n = 0u8;
+    let mut n = 0;
     let mut f = to_fn_mut(|| {
         n += 1; // OK
     });
 }
 
 fn c() {
-    let n = 0u8;
+    let n = 0;
     let mut f = to_fn_mut(move || {
         // If we just did a straight-forward desugaring, this would
         // compile, but we do something a bit more subtle, and hence
@@ -44,21 +44,21 @@ fn c() {
 }
 
 fn d() {
-    let mut n = 0u8;
+    let mut n = 0;
     let mut f = to_fn_mut(move || {
         n += 1; // OK
     });
 }
 
 fn e() {
-    let n = 0u8;
+    let n = 0;
     let mut f = to_fn(move || {
         n += 1; //~ ERROR cannot assign
     });
 }
 
 fn f() {
-    let mut n = 0u8;
+    let mut n = 0;
     let mut f = to_fn(move || {
         n += 1; //~ ERROR cannot assign
     });
index 2345a86595e2da0223b60d29f68147c5964c3bdc..432c7fa5d1b2025c9d8d2605e7bb31052ac80fd2 100644 (file)
@@ -16,7 +16,7 @@ fn call<F>(f: F) where F : Fn() {
 }
 
 fn main() {
-    let mut counter = 0_u32;
+    let mut counter = 0;
     call(|| {
         counter += 1;
         //~^ ERROR cannot assign to data in a captured outer variable in an `Fn` closure
index 88535ee04fb5b847fd23c21f4433d4d0331cdcf7..2ec10d08bb41d5ff92087c2eae36c4a410fd15a9 100644 (file)
@@ -8,8 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 #[derive(Debug)]
 struct r {
   b: bool,
@@ -20,7 +18,8 @@ fn drop(&mut self) {}
 }
 
 fn main() {
-    let i = box r { b: true };
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let i = Box::new(r { b: true });
     let _j = i.clone(); //~ ERROR not implement
     println!("{:?}", i);
 }
index 046337c33f0131dc4c2b4f5f5c58e26ec269a63a..86fe4da3429d084f23d164d47fe024fc4811ae79 100644 (file)
@@ -8,15 +8,14 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 use std::rc::Rc;
 
 fn f<T:Send>(__isize: T) {
 }
 
 fn main() {
-    let i = box Rc::new(100);
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let i = Box::new(Rc::new(100));
     f(i);
     //~^ ERROR `core::marker::Send` is not implemented
 }
index 91a41ad6a4986d81e8d91f0dad2bd50642c5642a..938abbf2c2018952a44739b07b3a7c027c866598 100644 (file)
@@ -10,8 +10,6 @@
 
 #![feature(unsafe_destructor)]
 
-#![feature(box_syntax)]
-
 use std::cell::Cell;
 
 #[derive(Debug)]
@@ -36,8 +34,9 @@ fn clone<T: Clone>(t: &T) -> T { t.clone() }
 fn main() {
     let i1 = &Cell::new(0);
     let i2 = &Cell::new(1);
-    let r1 = vec!(box r { i: i1 });
-    let r2 = vec!(box r { i: i2 });
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let r1 = vec!(Box::new(r { i: i1 }));
+    let r2 = vec!(Box::new(r { i: i2 }));
     f(clone(&r1), clone(&r2));
     //~^ ERROR the trait `core::clone::Clone` is not implemented for the type
     //~^^ ERROR the trait `core::clone::Clone` is not implemented for the type
index eb5ffeaf888866712075f36d91c00ecafd816718..bc93b86a391191229ae64e45f89aaf94eb469799 100644 (file)
@@ -15,4 +15,4 @@
 
 enum foo { a(Box<foo>, isize), b(usize), }
 
-fn main() { match foo::b(1_usize) { foo::b(_) | foo::a(box _, 1) => { } foo::a(_, 1) => { } } }
+fn main() { match foo::b(1) { foo::b(_) | foo::a(box _, 1) => { } foo::a(_, 1) => { } } }
index 97908118e3518fa82ba54d64a8f2c076b7ce8fa9..4ea7051775e132edf7e53eae6d1081adcfda8a40 100644 (file)
@@ -10,7 +10,7 @@
 
 
 fn f(p: *const u8) {
-    *p = 0u8; //~ ERROR dereference of unsafe pointer requires unsafe function or block
+    *p = 0; //~ ERROR dereference of unsafe pointer requires unsafe function or block
     return;
 }
 
diff --git a/src/test/compile-fail/unsized4.rs b/src/test/compile-fail/unsized4.rs
deleted file mode 100644 (file)
index f8b8ad2..0000000
+++ /dev/null
@@ -1,19 +0,0 @@
-// 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.
-
-// Test that bounds are sized-compatible.
-
-trait T : Sized {}
-fn f<Y: ?Sized + T>() {
-//~^ERROR incompatible bounds on `Y`, bound `T` does not allow unsized type
-}
-
-pub fn main() {
-}
index 1998f8ab15529e5cc110fcd28462a8e6ab0d4b74..26d22b072eb48ce3eda25139d5348ebe21141180 100644 (file)
@@ -34,8 +34,8 @@ fn push(&mut self, n: Box<ToString+'static>) {
 }
 
 fn main() {
-    let n = box Number { n: 42 };
-    let mut l = box List { list: Vec::new() };
+    let n: Box<_> = box Number { n: 42 };
+    let mut l: Box<_> = box List { list: Vec::new() };
     l.push(n);
     let x = n.to_string();
     //~^ ERROR: use of moved value: `n`
index 0254f56bd1a944b86b1e8db2f55722105416c7d9..e5473f12bf2d6f52ab97270a5399b410bd9c406a 100644 (file)
@@ -33,19 +33,19 @@ fn baz<'a, T>(_x: &'a T) -> Baked<'a> {
 
 fn main() {
     {
-        let a = AffineU32(1_u32);
+        let a = AffineU32(1);
         let x = foo(&a);
         drop(a); //~ ERROR cannot move out of `a`
         drop(x);
     }
     {
-        let a = AffineU32(1_u32);
+        let a = AffineU32(1);
         let x = bar(&a);
         drop(a); //~ ERROR cannot move out of `a`
         drop(x);
     }
     {
-        let a = AffineU32(1_u32);
+        let a = AffineU32(1);
         let x = baz(&a);
         drop(a); //~ ERROR cannot move out of `a`
         drop(x);
index cc6ff2d8ebcc204b2e9965fc00cb22911a82f6e7..654272f5bc6eba34b09220e9eff6adbd080ebcad 100644 (file)
@@ -23,7 +23,7 @@ fn gimme_an_a<A:TraitA>(&self, a: A) -> isize {
 }
 
 fn call_it<B:TraitB>(b: B)  -> isize {
-    let y = 4_usize;
+    let y = 4;
     b.gimme_an_a(y) //~ ERROR the trait `TraitA` is not implemented
 }
 
index 26117e7a13b6f2f1666499e755c988011375de16..63132d91327ca5f4bf74cbc87566239c2c1375e3 100644 (file)
@@ -139,13 +139,13 @@ fn assoc_enum<T: TraitWithAssocType>(arg: Enum<T>) {
 }
 
 fn main() {
-    assoc_struct(Struct { b: -1i32, b1: 0i64 });
-    assoc_local(1i32);
-    assoc_arg::<i32>(2i64);
-    assoc_return_value(3i32);
-    assoc_tuple((4i32, 5i64));
-    assoc_enum(Enum::Variant1(6i32, 7i64));
-    assoc_enum(Enum::Variant2(8i64, 9i32));
+    assoc_struct(Struct { b: -1, b1: 0 });
+    assoc_local(1);
+    assoc_arg::<i32>(2);
+    assoc_return_value(3);
+    assoc_tuple((4, 5));
+    assoc_enum(Enum::Variant1(6, 7));
+    assoc_enum(Enum::Variant2(8, 9));
 }
 
 fn zzz() { () }
index 2cfc6855e5bc6c9e4b4e08d8a38c4250ad261026..4430ea9380d43585a8c11ef49edbaf7febd4a074 100644 (file)
@@ -78,7 +78,7 @@ fn main() {
     let stack_val_interior_ref_2: &f64 = &stack_val.y;
     let ref_to_unnamed: &SomeStruct = &SomeStruct { x: 11, y: 24.5 };
 
-    let unique_val = box SomeStruct { x: 13, y: 26.5 };
+    let unique_val: Box<_> = box SomeStruct { x: 13, y: 26.5 };
     let unique_val_ref: &SomeStruct = &*unique_val;
     let unique_val_interior_ref_1: &int = &unique_val.x;
     let unique_val_interior_ref_2: &f64 = &unique_val.y;
index 972d6ab12e13fea6c3049e0041a2eaf66f39e9b3..9c6e197e65e23ebd495db0996f15fe8ed50c762e 100644 (file)
@@ -57,9 +57,9 @@ fn drop(&mut self) {}
 
 fn main() {
 
-    let unique = box StructWithSomePadding { x: 99, y: 999, z: 9999, w: 99999 };
+    let unique: Box<_> = box StructWithSomePadding { x: 99, y: 999, z: 9999, w: 99999 };
 
-    let unique_dtor = box StructWithDestructor { x: 77, y: 777, z: 7777, w: 77777 };
+    let unique_dtor: Box<_> = box StructWithDestructor { x: 77, y: 777, z: 7777, w: 77777 };
     zzz(); // #break
 }
 
index b92f5de21b5753d0b815d0db6022ae61c04a0f7d..448e157a251b211494910338d7a26a639e0c5ff1 100644 (file)
@@ -60,7 +60,7 @@ fn some_generic_fun<T1, T2>(a: T1, b: T2) -> (T2, T1) {
 
 fn main() {
     some_generic_fun(0.5f64, 10);
-    some_generic_fun(&29, box 110);
+    some_generic_fun(&29, Box::new(110));
 }
 
 fn zzz() { () }
diff --git a/src/test/debuginfo/constant-debug-locs.rs b/src/test/debuginfo/constant-debug-locs.rs
new file mode 100644 (file)
index 0000000..24332e3
--- /dev/null
@@ -0,0 +1,67 @@
+// Copyright 2013-2015 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-android: FIXME(#10381)
+// min-lldb-version: 310
+
+// compile-flags:-g
+
+#![allow(unused_variables)]
+#![allow(dead_code)]
+#![omit_gdb_pretty_printer_section]
+
+// This test makes sure that the compiler doesn't crash when trying to assign
+// debug locations to const-expressions.
+
+use std::sync::MUTEX_INIT;
+use std::cell::UnsafeCell;
+
+const CONSTANT: u64 = 3 + 4;
+
+struct Struct {
+    a: isize,
+    b: usize,
+}
+const STRUCT: Struct = Struct { a: 1, b: 2 };
+
+struct TupleStruct(u32);
+const TUPLE_STRUCT: TupleStruct = TupleStruct(4);
+
+enum Enum {
+    Variant1(char),
+    Variant2 { a: u8 },
+    Variant3
+}
+
+const VARIANT1: Enum = Enum::Variant1('v');
+const VARIANT2: Enum = Enum::Variant2 { a: 2 };
+const VARIANT3: Enum = Enum::Variant3;
+
+const STRING: &'static str = "String";
+
+const VEC: [u32; 8] = [0; 8];
+
+const NESTED: (Struct, TupleStruct) = (STRUCT, TUPLE_STRUCT);
+
+const UNSAFE_CELL: UnsafeCell<bool> = UnsafeCell { value: false };
+
+fn main() {
+    let mut _constant = CONSTANT;
+    let mut _struct = STRUCT;
+    let mut _tuple_struct = TUPLE_STRUCT;
+    let mut _variant1 = VARIANT1;
+    let mut _variant2 = VARIANT2;
+    let mut _variant3 = VARIANT3;
+    let mut _string = STRING;
+    let mut _vec = VEC;
+    let mut _nested = NESTED;
+    let mut _extern = MUTEX_INIT;
+    let mut _unsafe_cell = UNSAFE_CELL;
+}
diff --git a/src/test/debuginfo/cross-crate-spans.rs b/src/test/debuginfo/cross-crate-spans.rs
new file mode 100644 (file)
index 0000000..3aef943
--- /dev/null
@@ -0,0 +1,74 @@
+// Copyright 2013-2015 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.
+
+#![omit_gdb_pretty_printer_section]
+
+// ignore-android: FIXME(#10381)
+// min-lldb-version: 310
+
+// aux-build:cross_crate_spans.rs
+extern crate cross_crate_spans;
+
+// compile-flags:-g
+
+
+// === GDB TESTS ===================================================================================
+
+// gdb-command:break cross_crate_spans.rs:21
+// gdb-command:run
+
+// gdb-command:print result
+// gdb-check:$1 = {17, 17}
+// gdb-command:print a_variable
+// gdb-check:$2 = 123456789
+// gdb-command:print another_variable
+// gdb-check:$3 = 123456789.5
+// gdb-command:continue
+
+// gdb-command:print result
+// gdb-check:$4 = {1212, 1212}
+// gdb-command:print a_variable
+// gdb-check:$5 = 123456789
+// gdb-command:print another_variable
+// gdb-check:$6 = 123456789.5
+// gdb-command:continue
+
+
+
+// === LLDB TESTS ==================================================================================
+
+// lldb-command:b cross_crate_spans.rs:21
+// lldb-command:run
+
+// lldb-command:print result
+// lldb-check:[...]$0 = (17, 17)
+// lldb-command:print a_variable
+// lldb-check:[...]$1 = 123456789
+// lldb-command:print another_variable
+// lldb-check:[...]$2 = 123456789.5
+// lldb-command:continue
+
+// lldb-command:print result
+// lldb-check:[...]$3 = (1212, 1212)
+// lldb-command:print a_variable
+// lldb-check:[...]$4 = 123456789
+// lldb-command:print another_variable
+// lldb-check:[...]$5 = 123456789.5
+// lldb-command:continue
+
+
+// This test makes sure that we can break in functions inlined from other crates.
+
+fn main() {
+
+    let _ = cross_crate_spans::generic_function(17u32);
+    let _ = cross_crate_spans::generic_function(1212i16);
+
+}
diff --git a/src/test/debuginfo/extern-c-fn.rs b/src/test/debuginfo/extern-c-fn.rs
new file mode 100644 (file)
index 0000000..9e73417
--- /dev/null
@@ -0,0 +1,68 @@
+// 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.
+
+// min-lldb-version: 310
+
+// compile-flags:-g
+
+// === GDB TESTS ===================================================================================
+// gdb-command:run
+
+// gdb-command:print s
+// gdb-check:$1 = [...]"abcd"
+// gdb-command:print len
+// gdb-check:$2 = 20
+// gdb-command:print local0
+// gdb-check:$3 = 19
+// gdb-command:print local1
+// gdb-check:$4 = true
+// gdb-command:print local2
+// gdb-check:$5 = 20.5
+
+// gdb-command:continue
+
+// === LLDB TESTS ==================================================================================
+// lldb-command:run
+
+// lldb-command:print len
+// lldb-check:[...]$0 = 20
+// lldb-command:print local0
+// lldb-check:[...]$1 = 19
+// lldb-command:print local1
+// lldb-check:[...]$2 = true
+// lldb-command:print local2
+// lldb-check:[...]$3 = 20.5
+
+// lldb-command:continue
+
+#![allow(unused_variables)]
+#![allow(dead_code)]
+#![omit_gdb_pretty_printer_section]
+
+
+#[no_mangle]
+pub unsafe extern "C" fn fn_with_c_abi(s: *const u8, len: i32) -> i32 {
+    let local0 = len - 1;
+    let local1 = len > 2;
+    let local2 = (len as f64) + 0.5;
+
+    zzz(); // #break
+
+    return 0;
+}
+
+fn main() {
+    unsafe {
+        fn_with_c_abi(b"abcd\0".as_ptr(), 20);
+    }
+}
+
+#[inline(never)]
+fn zzz() {()}
index 8c4eeb27c0f6d5b69c2aefd6e1b10d54233168ed..8b698d900af0428cb2ec8ce8fbb90a71cc80d3fd 100644 (file)
@@ -142,7 +142,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, 2_u16);
     let _ = stack.self_by_val(-3, -4_i16);
 
-    let owned = box Struct { x: 1234.5f64 };
+    let owned: Box<_> = box Struct { x: 1234.5f64 };
     let _ = owned.self_by_ref(-5, -6_i32);
     let _ = owned.self_by_val(-7, -8_i64);
     let _ = owned.self_owned(-9, -10.5_f32);
index 7ad668791d3b899b1ff6f4756c7f2c5fdfdbb5f4..638d73f0d4e3c09e222663576a4a4fb22f8d5bac 100644 (file)
@@ -144,7 +144,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, -2);
     let _ = stack.self_by_val(-3, -4);
 
-    let owned = box Enum::Variant1{ x: 1799, y: 1799 };
+    let owned: Box<_> = box Enum::Variant1{ x: 1799, y: 1799 };
     let _ = owned.self_by_ref(-5, -6);
     let _ = owned.self_by_val(-7, -8);
     let _ = owned.self_owned(-9, -10);
index 6b56a7998c919880a2ba618b9bcd9859a735c361..784d60eec9a1ad953787b9cb7ee984a0710067bf 100644 (file)
@@ -143,7 +143,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, -2);
     let _ = stack.self_by_val(-3, -4);
 
-    let owned = box Struct { x: 1234.5f64 };
+    let owned: Box<_> = box Struct { x: 1234.5f64 };
     let _ = owned.self_by_ref(-5, -6);
     let _ = owned.self_by_val(-7, -8);
     let _ = owned.self_owned(-9, -10);
index e32288a8e7d0362df7765afe467ea62dd3370bd1..a91586a6aa6bee4e335b0a27433c34f2788f7e0c 100644 (file)
@@ -143,7 +143,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, -2);
     let _ = stack.self_by_val(-3, -4);
 
-    let owned = box Struct { x: 200 };
+    let owned: Box<_> = box Struct { x: 200 };
     let _ = owned.self_by_ref(-5, -6);
     let _ = owned.self_by_val(-7, -8);
     let _ = owned.self_owned(-9, -10);
index 6e9a695720a141b68d0288b26c8c9d4074cfc96b..e2c827ee5170f0f8af4b08fbd025a56862556734 100644 (file)
@@ -149,7 +149,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, -2);
     let _ = stack.self_by_val(-3, -4);
 
-    let owned = box Struct { x: 200 };
+    let owned: Box<_> = box Struct { x: 200 };
     let _ = owned.self_by_ref(-5, -6);
     let _ = owned.self_by_val(-7, -8);
     let _ = owned.self_owned(-9, -10);
index cee04e92c2d24e4de671dbb7a5225a1b17a491c2..e8bc40f1810f3b921df98a481eaf00eaa01d76eb 100644 (file)
@@ -141,7 +141,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, -2);
     let _ = stack.self_by_val(-3, -4);
 
-    let owned = box TupleStruct(200, -200.5);
+    let owned: Box<_> = box TupleStruct(200, -200.5);
     let _ = owned.self_by_ref(-5, -6);
     let _ = owned.self_by_val(-7, -8);
     let _ = owned.self_owned(-9, -10);
index 3b1979337d525fa5d9e1bba910b3fa7a621c19ff..25afd3514b0161bf160f169da040a08232491386 100644 (file)
@@ -128,10 +128,10 @@ fn main() {
         next: Val {
             val: box UniqueNode {
                 next: Empty,
-                value: 1_u16,
+                value: 1,
             }
         },
-        value: 0_u16,
+        value: 0,
     };
 
     let unique_unique: Box<UniqueNode<u32>> = box UniqueNode {
index cb2b04f4d8695df3f9a116ab144278d3646c8b3c..03a799933421c0d35c629f62507033ccea7dd905 100644 (file)
@@ -143,7 +143,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, -2);
     let _ = stack.self_by_val(-3, -4);
 
-    let owned = box Struct { x: 200 };
+    let owned: Box<_> = box Struct { x: 200 };
     let _ = owned.self_by_ref(-5, -6);
     let _ = owned.self_by_val(-7, -8);
     let _ = owned.self_owned(-9, -10);
index b96ec3b7b889cc18f815403a47798b3d6fd3b092..5869625bafe597feeeb2c24470d2b3230d608d16 100644 (file)
@@ -144,7 +144,7 @@ fn main() {
     let _ = stack.self_by_ref(-1, 2_u16);
     let _ = stack.self_by_val(-3, -4_i16);
 
-    let owned = box Struct { x: 879 };
+    let owned: Box<_> = box Struct { x: 879 };
     let _ = owned.self_by_ref(-5, -6_i32);
     let _ = owned.self_by_val(-7, -8_i64);
     let _ = owned.self_owned(-9, -10.5_f32);
index 161392c94c8f01e61435478bc307a83c399a6eea..12c7b146342ffed60f82ab6ddfb25bdb645b419b 100644 (file)
 
 fn main() {
 
-    let vi8x16 = i8x16(0i8, 1i8, 2i8, 3i8, 4i8, 5i8, 6i8, 7i8,
-                      8i8, 9i8, 10i8, 11i8, 12i8, 13i8, 14i8, 15i8);
-
-    let vi16x8 = i16x8(16i16, 17i16, 18i16, 19i16, 20i16, 21i16, 22i16, 23i16);
-    let vi32x4 = i32x4(24i32, 25i32, 26i32, 27i32);
-    let vi64x2 = i64x2(28i64, 29i64);
-
-    let vu8x16 = u8x16(30u8, 31u8, 32u8, 33u8, 34u8, 35u8, 36u8, 37u8,
-                      38u8, 39u8, 40u8, 41u8, 42u8, 43u8, 44u8, 45u8);
-    let vu16x8 = u16x8(46u16, 47u16, 48u16, 49u16, 50u16, 51u16, 52u16, 53u16);
-    let vu32x4 = u32x4(54u32, 55u32, 56u32, 57u32);
-    let vu64x2 = u64x2(58u64, 59u64);
+    let vi8x16 = i8x16(0, 1, 2, 3, 4, 5, 6, 7,
+                      8, 9, 10, 11, 12, 13, 14, 15);
+
+    let vi16x8 = i16x8(16, 17, 18, 19, 20, 21, 22, 23);
+    let vi32x4 = i32x4(24, 25, 26, 27);
+    let vi64x2 = i64x2(28, 29);
+
+    let vu8x16 = u8x16(30, 31, 32, 33, 34, 35, 36, 37,
+                      38, 39, 40, 41, 42, 43, 44, 45);
+    let vu16x8 = u16x8(46, 47, 48, 49, 50, 51, 52, 53);
+    let vu32x4 = u32x4(54, 55, 56, 57);
+    let vu64x2 = u64x2(58, 59);
 
     let vf32x4 = f32x4(60.5f32, 61.5f32, 62.5f32, 63.5f32);
     let vf64x2 = f64x2(64.5f64, 65.5f64);
index 69b5797007bdb8b689708aa6315a5d9a536fc8be..607a237d22e41ee1b4624cb0e1710b253e13864c 100644 (file)
@@ -67,15 +67,15 @@ fn main() {
     // 0b01111100011111000111110001111100 = 2088533116
     // 0b0111110001111100 = 31868
     // 0b01111100 = 124
-    let the_a = box ABC::TheA { x: 0, y: 8970181431921507452 };
+    let the_a: Box<_> = box ABC::TheA { x: 0, y: 8970181431921507452 };
 
     // 0b0001000100010001000100010001000100010001000100010001000100010001 = 1229782938247303441
     // 0b00010001000100010001000100010001 = 286331153
     // 0b0001000100010001 = 4369
     // 0b00010001 = 17
-    let the_b = box ABC::TheB (0, 286331153, 286331153);
+    let the_b: Box<_> = box ABC::TheB (0, 286331153, 286331153);
 
-    let univariant = box Univariant::TheOnlyCase(123234);
+    let univariant: Box<_> = box Univariant::TheOnlyCase(123234);
 
     zzz(); // #break
 }
index 9c9d82249ee317d70764a9f17fdd8067f6a9806e..05872e3fc36b2fb8072e01ab07fe29b931041864 100644 (file)
@@ -98,7 +98,7 @@ fn main() {
     };
 
     let struct_ref = &a_struct;
-    let owned = box 6;
+    let owned: Box<_> = box 6;
 
     let mut closure = || {
         let closure_local = 8;
index 3c442c95e0f59aa0329cc2029ad13207ee0c7c54..295d57f4cfa97fc22acc1926bbba4b5bf40d20d4 100644 (file)
@@ -58,7 +58,7 @@ fn main() {
         c: 4
     };
 
-    let owned = box 5;
+    let owned: Box<_> = box 5;
 
     let closure = move || {
         zzz(); // #break
index e3bd1eade7538d9d3c08b429c1962e2e3e90ac99..57dcac409bab8ad6cd39e22d5081dfccd84708cc 100644 (file)
@@ -90,7 +90,7 @@ fn main() {
     };
 
     let struct_ref = &a_struct;
-    let owned = box 6;
+    let owned: Box<_> = box 6;
 
     {
         let mut first_closure = || {
index ac5ec1236ff9d083294b9503ac261c84022f0436..3e548981f1ed4676f86801259a8573090f35044a 100644 (file)
@@ -9,10 +9,10 @@
 // except according to those terms.
 
 #[path = "circular_modules_hello.rs"]
-mod circular_modules_hello; //~ERROR: circular modules
+mod circular_modules_hello; //~ ERROR: circular modules
 
 pub fn hi_str() -> String {
-  "Hi!".to_string()
+    "Hi!".to_string()
 }
 
 fn main() {
index d709ffdc3fc125c3d29b23dd303937286dfeffa9..7de51c1ea75cab90166e8fed825be1560fa38f65 100644 (file)
@@ -15,5 +15,5 @@
 }
 
 fn main() {
-  let nyan = cat(0us);
+  let nyan = cat(0);
 }
index afff5984b46141d61f0c9b3de054473b83bd0657..9c35d77baf015398f60141bdc76be0adc9a4e506 100644 (file)
@@ -9,6 +9,6 @@
 // except according to those terms.
 
 fn main() {
-    let __isize = 0xff_ffff_ffff_ffff_ffff__isize;
+    let __isize = 0xff_ffff_ffff_ffff_ffff;
     //~^ ERROR int literal is too large
 }
index 597366a1b35dfc8b8ad13d393f1132b56d727828..09de97d71b83e25b76a634c799818d51cc24b27f 100644 (file)
@@ -8,15 +8,9 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// Copyright 2013 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-windows
+// ignore-freebsd
+// ignore-openbsd
 
 #[path = "../compile-fail"]
 mod foo; //~ ERROR: a directory
index fbe03e355eed6e5cba7b267c5e044072aff74b11..4aa01bcde69897b3423fc5b32ff32c269575039b 100644 (file)
@@ -8,36 +8,14 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-static c: char =
-    '\u539_' //~ ERROR: illegal character in numeric character escape
-    //~^ WARNING: \uABCD escapes are deprecated
-;
-
-static c2: char =
-    '\Uffffffff' //~ ERROR: illegal numeric character escape
-    //~^ WARNING: \uABCD escapes are deprecated
-;
-
 static c3: char =
     '\x1' //~ ERROR: numeric character escape is too short
 ;
 
-static c4: char =
-    '\u23q' //~  ERROR: illegal character in numeric character escape
-    //~^ WARNING: \uABCD escapes are deprecated
-;
-//~^^^ ERROR: numeric character escape is too short
-
 static s: &'static str =
     "\x1" //~ ERROR: numeric character escape is too short
 ;
 
-static s2: &'static str =
-    "\u23q" //~ ERROR: illegal character in numeric character escape
-    //~^ ERROR: numeric character escape is too short
-    //~^^ WARNING: \uABCD escapes are deprecated
-;
-
 static c: char =
     '\●' //~ ERROR: unknown character escape
 ;
index 9a490be6a0169963e5d4b8c7ace243f4911b8fa9..62b87e3f480adcf2eea6a3ad8d2f759a0407b86d 100644 (file)
@@ -22,7 +22,7 @@ fn main() {
     1e+; //~ ERROR: expected at least one digit in exponent
     0x539.0; //~ ERROR: hexadecimal float literal is not supported
     99999999999999999999999999999999; //~ ERROR: int literal is too large
-    99999999999999999999999999999999u32; //~ ERROR: int literal is too large
+    99999999999999999999999999999999; //~ ERROR: int literal is too large
     0x; //~ ERROR: no valid digits
     0xu32; //~ ERROR: no valid digits
     0ou32; //~ ERROR: no valid digits
index 8b36e87db3e53741c5b3b14a48f9baf0486b2525..7a7113cd594b5629fed3cf550f3a80dfca258e77 100644 (file)
@@ -26,7 +26,7 @@ fn get_ctxt(&self) -> &'a ctxt { self.c }
 }
 
 fn make_gc() -> @get_ctxt  {
-    let ctxt = ctxt { v: 22us };
+    let ctxt = ctxt { v: 22 };
     let hc = has_ctxt { c: &ctxt };
     return @hc as @get_ctxt;
     //~^ ERROR source contains reference
index 5a55cb4e561309b2781f8b28c7767f5c42e3d3d1..a5d82277d2f94aaa66de840350b9d03503b57efd 100644 (file)
@@ -105,10 +105,11 @@ fn f() {
 fn main() {
     // Taken from http://www.unicode.org/Public/UNIDATA/PropList.txt
     let chars =
-        ['\x0A', '\x0B', '\x0C', '\x0D', '\x20', '\u0085', '\u00A0', '\u1680',
-         '\u2000', '\u2001', '\u2002', '\u2003', '\u2004', '\u2005', '\u2006',
-         '\u2007', '\u2008', '\u2009', '\u200A', '\u2028', '\u2029', '\u202F',
-         '\u205F', '\u3000'];
+        ['\x0A', '\x0B', '\x0C', '\x0D', '\x20', '\u{85}', '\u{A0}',
+         '\u{1680}', '\u{2000}', '\u{2001}', '\u{2002}', '\u{2003}',
+         '\u{2004}', '\u{2005}', '\u{2006}', '\u{2007}', '\u{2008}',
+         '\u{2009}', '\u{200A}', '\u{2028}', '\u{2029}', '\u{202F}',
+         '\u{205F}', '\u{3000}'];
     for c in &chars {
         let ws = c.is_whitespace();
         println!("{} {}" , c , ws);
index c82bdcd8dcb9388efc2fa79409a8be1557686fbe..eb6d2a4a0a17392851e3808808b65721053ac897 100644 (file)
@@ -99,10 +99,11 @@ fn nested() {
 fn main() {
     // Taken from http://www.unicode.org/Public/UNIDATA/PropList.txt
     let chars =
-        ['\x0A', '\x0B', '\x0C', '\x0D', '\x20', '\u0085', '\u00A0', '\u1680',
-         '\u2000', '\u2001', '\u2002', '\u2003', '\u2004', '\u2005', '\u2006',
-         '\u2007', '\u2008', '\u2009', '\u200A', '\u2028', '\u2029', '\u202F',
-         '\u205F', '\u3000'];
+        ['\x0A', '\x0B', '\x0C', '\x0D', '\x20', '\u{85}', '\u{A0}',
+         '\u{1680}', '\u{2000}', '\u{2001}', '\u{2002}', '\u{2003}',
+         '\u{2004}', '\u{2005}', '\u{2006}', '\u{2007}', '\u{2008}',
+         '\u{2009}', '\u{200A}', '\u{2028}', '\u{2029}', '\u{202F}',
+         '\u{205F}', '\u{3000}'];
     for c in &chars {
         let ws = c.is_whitespace();
         println!("{} {}", c , ws);
index 58f6ae960b1895b2835da025c825d8bae1045872..6a9cbef1015424231d94b3a61ec1056e18ee6a93 100644 (file)
@@ -13,5 +13,5 @@
 
 fn a() -> uint {
 
-    1usize
+    1
 }
index 83ee2bd08f4adbcad507ae75e4260aa0a359c6c8..58cd19059c0d7ce63abea716c306fe555e48e323 100644 (file)
@@ -26,12 +26,12 @@ pub fn bar() {
     const FOO: usize = ((5 as usize) - (4 as usize) as usize);
     let _: [(); (FOO as usize)] = ([(() as ())] as [(); 1]);
 
-    let _: [(); (1usize as usize)] = ([(() as ())] as [(); 1]);
+    let _: [(); (1 as usize)] = ([(() as ())] as [(); 1]);
 
     let _ =
         (((&((([(1 as i32), (2 as i32), (3 as i32)] as [i32; 3])) as [i32; 3])
               as &[i32; 3]) as *const _ as *const [i32; 3]) as
-            *const [i32; (3usize as usize)] as *const [i32; 3]);
+            *const [i32; (3 as usize)] as *const [i32; 3]);
 
 
 
index 3aa2f4826b24cdaadd5ac816f3cad62793c3a13e..90757c92c4c998fec6a3fb5f50909ccc84750c22 100644 (file)
@@ -20,9 +20,9 @@ pub fn bar() {
     const FOO: usize = 5 - 4;
     let _: [(); FOO] = [()];
 
-    let _ : [(); 1usize] = [()];
+    let _ : [(); 1] = [()];
 
-    let _ = &([1,2,3]) as *const _ as *const [i32; 3usize];
+    let _ = &([1,2,3]) as *const _ as *const [i32; 3];
 
     format!("test");
 }
index 225ce5a741b7cb4f4e6e484ee5f512cd537f9b61..127700e963abd5a661680bb7175734bea154d7c1 100644 (file)
@@ -26,10 +26,10 @@ pub fn rust_dbg_call(cb: *u8, data: libc::uintptr_t)
 }
 
 extern fn cb(data: libc::uintptr_t) -> libc::uintptr_t {
-    if data == 1_usize {
+    if data == 1 {
         data
     } else {
-        count(data - 1_usize) + count(data - 1_usize)
+        count(data - 1) + count(data - 1)
     }
 }
 
@@ -41,9 +41,9 @@ fn count(n: uint) -> uint {
 }
 
 fn main() {
-    for _ in 0..10_usize {
+    for _ in 0..10 {
         task::spawn(move|| {
-            let result = count(5_usize);
+            let result = count(5);
             println!("result = %?", result);
             panic!();
         });
index 19a57db5ec79d0d01463bdf1e34b11928382de38..e3af5b2bbf57bc5889728b2b3ac9caeb9f6361ef 100644 (file)
@@ -10,9 +10,9 @@
 
 // error-pattern:Number is odd
 fn even(x: uint) -> bool {
-    if x < 2_usize {
+    if x < 2 {
         return false;
-    } else if x == 2_usize { return true; } else { return even(x - 2_usize); }
+    } else if x == 2 { return true; } else { return even(x - 2); }
 }
 
 fn foo(x: uint) {
@@ -23,4 +23,4 @@ fn foo(x: uint) {
     }
 }
 
-fn main() { foo(3_usize); }
+fn main() { foo(3); }
diff --git a/src/test/run-fail/overflowing-add.rs b/src/test/run-fail/overflowing-add.rs
new file mode 100644 (file)
index 0000000..cd13b81
--- /dev/null
@@ -0,0 +1,19 @@
+// Copyright 2015 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.
+
+// error-pattern:thread '<main>' panicked at 'arithmetic operation overflowed'
+// compile-flags: -C debug-assertions
+
+// (Work around constant-evaluation)
+fn value() -> u8 { 200 }
+
+fn main() {
+    let _x = value() + value() + value();
+}
diff --git a/src/test/run-fail/overflowing-mul.rs b/src/test/run-fail/overflowing-mul.rs
new file mode 100644 (file)
index 0000000..5d2f539
--- /dev/null
@@ -0,0 +1,19 @@
+// Copyright 2015 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.
+
+// error-pattern:thread '<main>' panicked at 'arithmetic operation overflowed'
+// compile-flags: -C debug-assertions
+
+// (Work around constant-evaluation)
+fn value() -> u8 { 200 }
+
+fn main() {
+    let x = value() * 4;
+}
diff --git a/src/test/run-fail/overflowing-sub.rs b/src/test/run-fail/overflowing-sub.rs
new file mode 100644 (file)
index 0000000..b089dcc
--- /dev/null
@@ -0,0 +1,19 @@
+// Copyright 2015 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.
+
+// error-pattern:thread '<main>' panicked at 'arithmetic operation overflowed'
+// compile-flags: -C debug-assertions
+
+// (Work around constant-evaluation)
+fn value() -> u8 { 42 }
+
+fn main() {
+    let _x = value() - (value() + 1);
+}
index 89e47bf46ab020c375f1d16a72acb219d9379513..4d0f7c29cb9df4ead4e9e10ff50fb7c2e2d7e386 100644 (file)
@@ -10,9 +10,6 @@
 
 // error-pattern:panicked at 'Box<Any>'
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn main() {
-    panic!(box 612_i64);
+    panic!(Box::new(612_i64));
 }
index 5a5bb53a33a209f12f25f928a01fb662e034e7ff..e18c5d9631a702358a6964b918fe8b2db3bb3267 100644 (file)
@@ -14,7 +14,7 @@
 // ignore-pretty: does not work well with `--test`
 
 #[test]
-#[should_fail(expected = "foobar")]
+#[should_panic(expected = "foobar")]
 fn test_foo() {
     panic!("blah")
 }
index 9f643c09795dfd1c63ca7a45c50ee1959f2c7eae..83b2bb91f0073a59ba3418da547d8df276e47677 100644 (file)
@@ -10,7 +10,4 @@
 
 // error-pattern: panic
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
-fn main() { box panic!(); }
+fn main() { Box::new(panic!()); }
index e1176b1bcdbc931f7ce1806cfad95c9cbb8a53b7..f4ba789d6bf7be1c92b6bb1b7e2114c4936aae4f 100644 (file)
 
 // error-pattern:fail
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn failfn() {
     panic!();
 }
 
 fn main() {
-    box 0;
+    Box::new(0);
     failfn();
 }
diff --git a/src/test/run-make/bare-outfile/Makefile b/src/test/run-make/bare-outfile/Makefile
new file mode 100644 (file)
index 0000000..97d09c8
--- /dev/null
@@ -0,0 +1,4 @@
+-include ../tools.mk
+
+all:
+       $(rustc) -o foo foo.rs
diff --git a/src/test/run-make/bare-outfile/foo.rs b/src/test/run-make/bare-outfile/foo.rs
new file mode 100644 (file)
index 0000000..63e7479
--- /dev/null
@@ -0,0 +1,12 @@
+// Copyright 2015 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() {
+}
diff --git a/src/test/run-make/debug-assertions/Makefile b/src/test/run-make/debug-assertions/Makefile
new file mode 100644 (file)
index 0000000..7129756
--- /dev/null
@@ -0,0 +1,21 @@
+-include ../tools.mk
+
+all:
+       $(RUSTC) debug.rs -C debug-assertions=no
+       $(call RUN,debug) good
+       $(RUSTC) debug.rs -C opt-level=0
+       $(call RUN,debug) bad
+       $(RUSTC) debug.rs -C opt-level=1
+       $(call RUN,debug) good
+       $(RUSTC) debug.rs -C opt-level=2
+       $(call RUN,debug) good
+       $(RUSTC) debug.rs -C opt-level=3
+       $(call RUN,debug) good
+       $(RUSTC) debug.rs -O
+       $(call RUN,debug) good
+       $(RUSTC) debug.rs
+       $(call RUN,debug) bad
+       $(RUSTC) debug.rs -C debug-assertions=yes -O
+       $(call RUN,debug) bad
+       $(RUSTC) debug.rs -C debug-assertions=yes -C opt-level=1
+       $(call RUN,debug) bad
diff --git a/src/test/run-make/debug-assertions/debug.rs b/src/test/run-make/debug-assertions/debug.rs
new file mode 100644 (file)
index 0000000..a0ccc75
--- /dev/null
@@ -0,0 +1,42 @@
+// Copyright 2015 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.
+
+#![deny(warnings)]
+
+use std::env;
+use std::thread;
+
+fn main() {
+    let should_fail = env::args().nth(1) == Some("bad".to_string());
+
+    assert_eq!(thread::spawn(debug_assert_eq).join().is_err(), should_fail);
+    assert_eq!(thread::spawn(debug_assert).join().is_err(), should_fail);
+    assert_eq!(thread::spawn(overflow).join().is_err(), should_fail);
+}
+
+fn debug_assert_eq() {
+    let mut hit1 = false;
+    let mut hit2 = false;
+    debug_assert_eq!({ hit1 = true; 1 }, { hit2 = true; 2 });
+    assert!(!hit1);
+    assert!(!hit2);
+}
+
+fn debug_assert() {
+    let mut hit = false;
+    debug_assert!({ hit = true; false });
+    assert!(!hit);
+}
+
+fn overflow() {
+    fn add(a: u8, b: u8) -> u8 { a + b }
+
+    add(200u8, 200u8);
+}
index b4ec986ef25fd8f50141116a5d4aad171cc7a0be..21e84fb858bcfef907b6023f58fdf3c89e75f66e 100644 (file)
@@ -1,17 +1,17 @@
 digraph block {
     N0[label="entry"];
     N1[label="exit"];
-    N2[label="expr 2usize"];
-    N3[label="expr 0usize"];
-    N4[label="expr 20usize"];
-    N5[label="expr [2usize, 0usize, 20usize]"];
+    N2[label="expr 2"];
+    N3[label="expr 0"];
+    N4[label="expr 20"];
+    N5[label="expr [2, 0, 20]"];
     N6[label="local v"];
-    N7[label="stmt let v = [2usize, 0usize, 20usize];"];
+    N7[label="stmt let v = [2, 0, 20];"];
     N8[label="expr v"];
-    N9[label="expr 20usize"];
-    N10[label="expr v[20usize]"];
-    N11[label="stmt v[20usize];"];
-    N12[label="block { let v = [2usize, 0usize, 20usize]; v[20usize]; }"];
+    N9[label="expr 20"];
+    N10[label="expr v[20]"];
+    N11[label="stmt v[20];"];
+    N12[label="block { let v = [2, 0, 20]; v[20]; }"];
     N0 -> N2;
     N2 -> N3;
     N3 -> N4;
index d65de18b5470ad11e15c4ec283d0a65d5e7426f1..d7349932355b10c92a06c3a1d93af996a6b7e7cb 100644 (file)
@@ -9,6 +9,6 @@
 // except according to those terms.
 
 pub fn expr_index_20() {
-    let v = [2_usize, 0_usize, 20_usize];
-    v[20_usize];
+    let v = [2, 0, 20];
+    v[20];
 }
index cff4d44910b3146d312c11a0d41958d79c3a22c8..1ed816ed7290a87645737874135e5a3169a04de4 100644 (file)
@@ -18,6 +18,8 @@
 use rustc_driver::driver::{compile_input, CompileController};
 use syntax::diagnostics::registry::Registry;
 
+use std::path::PathBuf;
+
 fn main() {
     let src = r#"
     fn main() {}
@@ -29,9 +31,9 @@ fn main() {}
         panic!("expected rustc path");
     }
 
-    let tmpdir = Path::new(&args[1]);
+    let tmpdir = PathBuf::new(&args[1]);
 
-    let mut sysroot = Path::new(&args[3]);
+    let mut sysroot = PathBuf::new(&args[3]);
     sysroot.pop();
     sysroot.pop();
 
@@ -40,7 +42,7 @@ fn main() {}
     compile(src.to_string(), tmpdir.join("out"), sysroot.clone());
 }
 
-fn basic_sess(sysroot: Path) -> Session {
+fn basic_sess(sysroot: PathBuf) -> Session {
     let mut opts = basic_options();
     opts.output_types = vec![OutputTypeExe];
     opts.maybe_sysroot = Some(sysroot);
@@ -51,7 +53,7 @@ fn basic_sess(sysroot: Path) -> Session {
     sess
 }
 
-fn compile(code: String, output: Path, sysroot: Path) {
+fn compile(code: String, output: PathBuf, sysroot: PathBuf) {
     let sess = basic_sess(sysroot);
     let cfg = build_configuration(&sess);
     let control = CompileController::basic();
index 38381da3670c18be3fa9e126ccb3c08e0237f031..2e2b8d2578eaf88384f98bb786cc93769aaf572a 100644 (file)
 // buglink test - see issue #1337.
 
 fn test_alias<I: Iterator>(i: Option<<I as Iterator>::Item>) {
-    let s = sub_struct{ field2: 45u32, };
+    let s = sub_struct{ field2: 45, };
 
     // import tests
     fn foo(x: &Float) {}
     let _: Option<u8> = from_i32(45);
 
-    let x = 42_usize;
+    let x = 42;
 
     myflate::deflate_bytes(&[]);
 
-    let x = (3, 4_usize);
+    let x = (3, 4);
     let y = x.1;
 }
 
@@ -245,9 +245,10 @@ fn hello<X: SomeTrait>((z, a) : (u32, String), ex: X) {
     let x = 32.0f32;
     let _ = (x + ((x * x) + 1.0).sqrt()).ln();
 
-    let s: Box<SomeTrait> = box some_fields {field1: 43};
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let s: Box<SomeTrait> = Box::new(some_fields {field1: 43});
     let s2: Box<some_fields> =  box some_fields {field1: 43};
-    let s3 = box nofields;
+    let s3: Box<_> = box nofields;
 
     s.Method(43);
     s3.Method(43);
@@ -282,7 +283,7 @@ pub struct blah {
 }
 
 fn main() { // foo
-    let s = box some_fields {field1: 43};
+    let s: Box<_> = box some_fields {field1: 43};
     hello((43, "a".to_string()), *s);
     sub::sub2::hello();
     sub2::sub3::hello();
old mode 100755 (executable)
new mode 100644 (file)
index e1f36ecda53e83c5daaf73456b44b6c886688baa..f81d4803f8fa491f686137f91f428b85dc5e507a 100644 (file)
@@ -16,5 +16,5 @@ impl Foo for uint {}
 
 pub fn dummy() {
     // force the vtable to be created
-    let _x = &1_usize as &Foo;
+    let _x = &1 as &Foo;
 }
index ef6c799336bd4e5171878fe7ccf1b9339c32fded..a6cb9fe0324d7d7c5cde512aa9ce39506a04a46e 100644 (file)
@@ -80,7 +80,7 @@ fn main() {
                          .arg(format!("{} {}",
                                       rustc,
                                       main_file.as_str()
-                                               .unwrap()).as_slice())
+                                               .unwrap()))
                          .output().unwrap();
 
     let err = String::from_utf8_lossy(result.error.as_slice());
index 9e164522d77a60db51fd8c6e693eecb7587b36a2..75a968c3f811330de7eda03ceacbbfbd5e54e7d8 100644 (file)
@@ -25,6 +25,7 @@
 use rustc_driver::{driver, CompilerCalls, Compilation};
 use syntax::diagnostics;
 
+use std::path::PathBuf;
 
 struct TestCalls {
     count: u32
@@ -43,14 +44,15 @@ fn late_callback(&mut self,
                      _: &getopts::Matches,
                      _: &Session,
                      _: &Input,
-                     _: &Option<Path>,
-                     _: &Option<Path>)
+                     _: &Option<PathBuf>,
+                     _: &Option<PathBuf>)
                      -> Compilation {
         self.count *= 3;
         Compilation::Stop
     }
 
-    fn some_input(&mut self, input: Input, input_path: Option<Path>) -> (Input, Option<Path>) {
+    fn some_input(&mut self, input: Input, input_path: Option<PathBuf>)
+                  -> (Input, Option<PathBuf>) {
         self.count *= 5;
         (input, input_path)
     }
@@ -58,10 +60,10 @@ fn some_input(&mut self, input: Input, input_path: Option<Path>) -> (Input, Opti
     fn no_input(&mut self,
                 _: &getopts::Matches,
                 _: &config::Options,
-                _: &Option<Path>,
-                _: &Option<Path>,
+                _: &Option<PathBuf>,
+                _: &Option<PathBuf>,
                 _: &diagnostics::registry::Registry)
-                -> Option<(Input, Option<Path>)> {
+                -> Option<(Input, Option<PathBuf>)> {
         panic!("This shouldn't happen");
     }
 
diff --git a/src/test/run-pass-fulldeps/derive-totalsum.rs b/src/test/run-pass-fulldeps/derive-totalsum.rs
new file mode 100644 (file)
index 0000000..848b242
--- /dev/null
@@ -0,0 +1,59 @@
+// Copyright 2015 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.
+
+// aux-build:custom_derive_plugin.rs
+// ignore-stage1
+
+#![feature(plugin, custom_derive)]
+#![plugin(custom_derive_plugin)]
+
+trait TotalSum {
+    fn total_sum(&self) -> isize;
+}
+
+impl TotalSum for isize {
+    fn total_sum(&self) -> isize {
+        *self
+    }
+}
+
+struct Seven;
+
+impl TotalSum for Seven {
+    fn total_sum(&self) -> isize {
+        7
+    }
+}
+
+#[derive(TotalSum)]
+struct Foo {
+    seven: Seven,
+    bar: Bar,
+    baz: isize,
+}
+
+#[derive(TotalSum)]
+struct Bar {
+    quux: isize,
+    bleh: isize,
+}
+
+
+pub fn main() {
+    let v = Foo {
+        seven: Seven,
+        bar: Bar {
+            quux: 9,
+            bleh: 3,
+        },
+        baz: 80,
+    };
+    assert_eq!(v.total_sum(), 99);
+}
diff --git a/src/test/run-pass-fulldeps/issue-15778-pass.rs b/src/test/run-pass-fulldeps/issue-15778-pass.rs
new file mode 100644 (file)
index 0000000..a767779
--- /dev/null
@@ -0,0 +1,19 @@
+// Copyright 2015 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.
+
+// aux-build:lint_for_crate.rs
+// ignore-stage1
+// compile-flags: -D crate-not-okay
+
+#![feature(plugin, custom_attribute)]
+#![plugin(lint_for_crate)]
+#![crate_okay]
+
+pub fn main() { }
index 58ccd79b7121dbe9afe8201db76283556de8a170..7a2846c31b66331815ce76613619a2a83386a51a 100644 (file)
@@ -11,7 +11,7 @@
 // aux-build:macro_crate_test.rs
 // ignore-stage1
 
-#![feature(plugin)]
+#![feature(plugin, custom_attribute)]
 #![plugin(macro_crate_test)]
 
 #[macro_use] #[no_link]
diff --git a/src/test/run-pass-fulldeps/mbe_matching_test_macro.rs b/src/test/run-pass-fulldeps/mbe_matching_test_macro.rs
new file mode 100644 (file)
index 0000000..5383b11
--- /dev/null
@@ -0,0 +1,25 @@
+// Copyright 2015 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.
+
+// aux-build:procedural_mbe_matching.rs
+// ignore-stage1
+
+#![feature(plugin)]
+#![plugin(procedural_mbe_matching)]
+
+#[no_link]
+extern crate procedural_mbe_matching;
+
+pub fn main() {
+    let abc = 123u32;
+    assert_eq!(matches!(Some(123), None | Some(0)), false);
+    assert_eq!(matches!(Some(123), None | Some(123)), true);
+    assert_eq!(matches!(true, true), true);
+}
index 252d297d12d3053d44f3be816057c9d146d0e928..92cb0d71e4570fe6f422f4549b6da83ff07d64b3 100644 (file)
@@ -1,4 +1,4 @@
-// Copyright 2012-2014 The Rust Project Developers. See the COPYRIGHT
+// Copyright 2015 The Rust Project Developers. See the COPYRIGHT
 // file at the top-level directory of this distribution and at
 // http://rust-lang.org/COPYRIGHT.
 //
@@ -74,6 +74,9 @@ fn main() {
 
     let arm = quote_arm!(cx, (ref x, ref y) => (x, y));
     check_pp(ext_cx, arm, pprust::print_stmt, "(ref x, ref y) = (x, y)".to_string());
+
+    let attr = quote_attr!(cx, #![cfg(foo = "bar")]);
+    check_pp(ext_cx, attr, pprust::print_attribute, "#![cfg(foo = "bar")]".to_string());
 }
 
 fn check_pp<T>(cx: fake_ext_ctxt,
index e76c379177b9962dec61dfa1028c2ebe95d4180f..a9b77419b9a37ad7a59ec5c54608b06ab4d5e87a 100644 (file)
@@ -40,6 +40,11 @@ fn syntax_extension(cx: &ExtCtxt) {
     let _k: P<syntax::ast::Method> = quote_method!(cx, #[doc = "hello"] fn foo(&self) {});
 
     let _l: P<syntax::ast::Ty> = quote_ty!(cx, &int);
+
+    let _m: Vec<syntax::ast::TokenTree> = quote_matcher!(cx, $($foo:tt,)* bar);
+    let _n: syntax::ast::Attribute = quote_attr!(cx, #![cfg(foo, bar = "baz")]);
+
+    let _o: Option<P<syntax::ast::Item>> = quote_item!(cx, fn foo<T: ?Sized>() {});
 }
 
 fn main() {
index c49a684de945df046b3015e2cd5b0a35488b865e..d051b7b491b946d775b677ca982c4e7fba40dc1a 100644 (file)
@@ -8,8 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 static mut DROP_RAN: bool = false;
 
 struct Foo;
@@ -28,7 +26,8 @@ struct Fat<T: ?Sized> {
 
 pub fn main() {
     {
-        let _x: Box<Fat<Trait>> = box Fat { f: Foo };
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        let _x: Box<Fat<Trait>> = Box::<Fat<Foo>>::new(Fat { f: Foo });
     }
     unsafe {
         assert!(DROP_RAN);
index 2c7b89d680a3d92275c096f97dd55f35eb6de962..2cb5f77fdc3f3b0e7385a08478c60d6d2def0862 100644 (file)
@@ -8,8 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![feature(box_syntax)]
-
 static mut DROP_RAN: int = 0;
 
 struct Foo;
@@ -25,7 +23,8 @@ struct Fat<T: ?Sized> {
 
 pub fn main() {
     {
-        let _x: Box<Fat<[Foo]>> = box Fat { f: [Foo, Foo, Foo] };
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        let _x: Box<Fat<[Foo]>> = Box::<Fat<[Foo; 3]>>::new(Fat { f: [Foo, Foo, Foo] });
     }
     unsafe {
         assert!(DROP_RAN == 3);
index b1bebf0b3e60648b3a051be51a4c535589a53dcb..45dd213d71fefffee006e2e04bdf9b06176c2297 100644 (file)
@@ -17,7 +17,7 @@ enum sty { ty_nil, }
 struct RawT {struct_: sty, cname: Option<String>, hash: uint}
 
 fn mk_raw_ty(st: sty, cname: Option<String>) -> RawT {
-    return RawT {struct_: st, cname: cname, hash: 0_usize};
+    return RawT {struct_: st, cname: cname, hash: 0};
 }
 
 pub fn main() { mk_raw_ty(sty::ty_nil, None::<String>); }
index e55a2d39cbf889af375405d39a020049a64eddfa..c52e04322e911b24ce1e881e0a119c3f3d968243 100644 (file)
@@ -8,15 +8,12 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 #[derive(PartialEq, Debug)]
 struct Point { x : int }
 
 pub fn main() {
     assert_eq!(14,14);
     assert_eq!("abc".to_string(),"abc".to_string());
-    assert_eq!(box Point{x:34},box Point{x:34});
+    assert_eq!(Box::new(Point{x:34}),Box::new(Point{x:34}));
     assert_eq!(&Point{x:34},&Point{x:34});
 }
index 2f9a0b328b5d492146d76adb077dd3e8585d97db..c6c66f1c75c5432d477fdf980389b348a4bf38e4 100644 (file)
@@ -16,7 +16,7 @@ pub trait Foo {
 }
 
 #[derive(PartialEq)]
-struct Bar;
+pub struct Bar;
 
 impl Foo for int {
     type A = uint;
index 57e9230336c1e082a0b203cca2ec36801f9f1bff..299225e3a47b97ea527dc0a1e2c0d1c8d01c0311 100644 (file)
@@ -35,5 +35,5 @@ fn get(x: int) -> <int as SignedUnsigned>::Opposite {
 
 fn main() {
     let x = get(22);
-    assert_eq!(22_usize, x);
+    assert_eq!(22, x);
 }
index 7365e052171eff975809517f89c5a5a7b8d056ce..941e9a84538025b34d0b0b3e030cee1d90449a7a 100644 (file)
@@ -25,6 +25,7 @@ fn pairwise_sub(mut t: Box<DoubleEndedIterator<Item=int>>) -> int {
 
 fn main() {
     let v = vec!(1, 2, 3, 4, 5, 6);
-    let r = pairwise_sub(box v.into_iter());
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let r = pairwise_sub(Box::new(v.into_iter()));
     assert_eq!(r, 9);
 }
index 0ec8a3661906f7aaee7806a151ba4718339eb7da..901b3c0d96b010c78b50cd1c8f6ddfc797968722 100644 (file)
@@ -15,7 +15,7 @@ pub trait Foo {
     fn boo(&self) -> <Self as Foo>::A;
 }
 
-struct Bar;
+pub struct Bar;
 
 impl Foo for char {
     type A = Bar;
index fe24ab6bbeb1b453a21c8ac791820c2f10aeac7f..e7ab910bc95088e8427ba9d56adb204bac81c020 100644 (file)
@@ -16,7 +16,7 @@ pub trait Foo {
 }
 
 #[derive(PartialEq)]
-struct Bar;
+pub struct Bar;
 
 impl Foo for int {
     type A = uint;
@@ -43,7 +43,7 @@ fn foo2<I: Foo>(x: I) -> <I as Foo>::A {
 
 pub fn main() {
     let a = 42;
-    assert!(foo2(a) == 42_usize);
+    assert!(foo2(a) == 42);
 
     let a = Bar;
     assert!(foo2(a) == 43);
index 8667f6c8430aba03c706a9ae8d61bf273e920a5e..a63274beb0ebb32a6b2edd7887a535dca66d766d 100644 (file)
@@ -36,8 +36,8 @@ impl UnifyKey for u32 {
 
 pub fn main() {
     let node: Node<i32> = Node { key: 1, value: Some(22) };
-    assert_eq!(foo(&node), Some(22_u32));
+    assert_eq!(foo(&node), Some(22));
 
     let node: Node<u32> = Node { key: 1, value: Some(22) };
-    assert_eq!(foo(&node), Some(22_i32));
+    assert_eq!(foo(&node), Some(22));
 }
index 9503f78a71b908ed469cfc109a4a11f89f9151b6..3be2623185bcdadd43c2579933a51d9c17571065 100644 (file)
@@ -33,8 +33,8 @@ impl UnifyKey for u32 {
 
 pub fn main() {
     let node: Node<i32> = Node(1, Some(22));
-    assert_eq!(foo(&node), Some(22_u32));
+    assert_eq!(foo(&node), Some(22));
 
     let node: Node<u32> = Node(1, Some(22));
-    assert_eq!(foo(&node), Some(22_i32));
+    assert_eq!(foo(&node), Some(22));
 }
index c068065ac6ae7e2167636a4ae336398c1bec9b8a..7e7299961d8a889659676ad6be2df1f30fd6c04a 100644 (file)
@@ -41,5 +41,5 @@ fn f() {
 }
 
 pub fn main() {
-    let z: uint = bar(2, 4_usize);
+    let z: uint = bar(2, 4);
 }
index 7c126fc420aac7f6b5e5522a5dd33b00977c9f1c..2b84adcb15ccbdaa111627fd12ff6bc304393776 100644 (file)
@@ -131,19 +131,19 @@ enum Quark<T> {
 enum CLike { A, B, C }
 
 pub fn main() {
-    let a = &Plus(@Minus(@Val(3_usize), @Val(10_usize)), @Plus(@Val(22_usize), @Val(5_usize)));
+    let a = &Plus(@Minus(@Val(3), @Val(10)), @Plus(@Val(22), @Val(5)));
     test_rbml(a);
 
-    let a = &Spanned {lo: 0_usize, hi: 5_usize, node: 22_usize};
+    let a = &Spanned {lo: 0, hi: 5, node: 22};
     test_rbml(a);
 
-    let a = &Point {x: 3_usize, y: 5_usize};
+    let a = &Point {x: 3, y: 5};
     test_rbml(a);
 
-    let a = &Top(22_usize);
+    let a = &Top(22);
     test_rbml(a);
 
-    let a = &Bottom(222_usize);
+    let a = &Bottom(222);
     test_rbml(a);
 
     let a = &A;
index 9e88eb6da6aea813b1f6472ce2206ead59bec651..6a90fa47e58ff84733d521ef50e7319535b37d78 100644 (file)
@@ -16,10 +16,10 @@ trait double {
 }
 
 impl double for uint {
-    fn double(self: Box<uint>) -> uint { *self * 2_usize }
+    fn double(self: Box<uint>) -> uint { *self * 2 }
 }
 
 pub fn main() {
-    let x = box() (box 3_usize as Box<double>);
-    assert_eq!(x.double(), 6_usize);
+    let x: Box<_> = box() (box 3 as Box<double>);
+    assert_eq!(x.double(), 6);
 }
index 67dd25ddc5389154872251209486312aee9291ef..cadce45b18d026041d76e45462e12f4ae6afb6bb 100644 (file)
@@ -20,10 +20,10 @@ fn double(self) -> uint { self }
 }
 
 impl double for Box<uint> {
-    fn double(self) -> uint { *self * 2_usize }
+    fn double(self) -> uint { *self * 2 }
 }
 
 pub fn main() {
-    let x = box 3_usize;
-    assert_eq!(x.double(), 6_usize);
+    let x: Box<_> = box 3;
+    assert_eq!(x.double(), 6);
 }
index 6437c78161c00f72d4fa104533ebc79216330130..746107803c90d0dc1dddede22ee9151509205a97 100644 (file)
@@ -16,10 +16,10 @@ trait double {
 }
 
 impl double for Box<uint> {
-    fn double(self: Box<Box<uint>>) -> uint { **self * 2_usize }
+    fn double(self: Box<Box<uint>>) -> uint { **self * 2 }
 }
 
 pub fn main() {
-    let x = box box box box box 3_usize;
-    assert_eq!(x.double(), 6_usize);
+    let x: Box<Box<Box<Box<Box<_>>>>> = box box box box box 3;
+    assert_eq!(x.double(), 6);
 }
index 8cbc151f0cd24af4930e5eaeb24296789b1983b1..51b5c98816a2c447c7157ea3ba89936cd35e6421 100644 (file)
@@ -16,10 +16,10 @@ trait double {
 }
 
 impl double for uint {
-    fn double(self: Box<uint>) -> uint { *self * 2_usize }
+    fn double(self: Box<uint>) -> uint { *self * 2 }
 }
 
 pub fn main() {
-    let x = box box 3_usize;
-    assert_eq!(x.double(), 6_usize);
+    let x: Box<Box<_>> = box box 3;
+    assert_eq!(x.double(), 6);
 }
index c8fa3c9fd5fb505518d1e71e396f891d0321beb1..61e704276af31c984084716b9ce0b4e9ee6184c3 100644 (file)
@@ -16,10 +16,10 @@ trait double {
 }
 
 impl double for uint {
-    fn double(self: Box<uint>) -> uint { *self * 2_usize }
+    fn double(self: Box<uint>) -> uint { *self * 2 }
 }
 
 pub fn main() {
-    let x = box 3_usize;
-    assert_eq!(x.double(), 6_usize);
+    let x: Box<_> = box 3;
+    assert_eq!(x.double(), 6);
 }
index 87157b9334f167f0bf3a540a5dbcd132e9e37613..86d6a91e75b7613273ac58b6e982153efad7bb04 100644 (file)
@@ -29,6 +29,6 @@ fn foo(&self) -> String {
 }
 
 pub fn main() {
-    let x = box 3_usize;
+    let x: Box<_> = box 3;
     assert_eq!(x.foo(), "box 3".to_string());
 }
index a2a63d44a784575041c658712d6faf6fbe6149b9..23aadbc70537ebf508f2aea0a853f386bc8dd220 100644 (file)
@@ -68,7 +68,7 @@ fn dump_filelines(filelines: &[Pos]) {
 }
 
 #[inline(never)]
-fn inner(counter: &mut u32, main_pos: Pos, outer_pos: Pos) {
+fn inner(counter: &mut i32, main_pos: Pos, outer_pos: Pos) {
     check!(counter; main_pos, outer_pos);
     check!(counter; main_pos, outer_pos);
     let inner_pos = pos!(); aux::callback(|aux_pos| {
@@ -80,12 +80,12 @@ fn inner(counter: &mut u32, main_pos: Pos, outer_pos: Pos) {
 }
 
 #[inline(always)]
-fn inner_inlined(counter: &mut u32, main_pos: Pos, outer_pos: Pos) {
+fn inner_inlined(counter: &mut i32, main_pos: Pos, outer_pos: Pos) {
     check!(counter; main_pos, outer_pos);
     check!(counter; main_pos, outer_pos);
 
     #[inline(always)]
-    fn inner_further_inlined(counter: &mut u32, main_pos: Pos, outer_pos: Pos, inner_pos: Pos) {
+    fn inner_further_inlined(counter: &mut i32, main_pos: Pos, outer_pos: Pos, inner_pos: Pos) {
         check!(counter; main_pos, outer_pos, inner_pos);
     }
     inner_further_inlined(counter, main_pos, outer_pos, pos!());
@@ -103,7 +103,7 @@ fn inner_further_inlined(counter: &mut u32, main_pos: Pos, outer_pos: Pos, inner
 }
 
 #[inline(never)]
-fn outer(mut counter: u32, main_pos: Pos) {
+fn outer(mut counter: i32, main_pos: Pos) {
     inner(&mut counter, main_pos, pos!());
     inner_inlined(&mut counter, main_pos, pos!());
 }
index 6f76322cb778d57a0401c4a333619c5dace9418f..879b3e920ab96ba067ed9f3c8e9ee6e83b8cc974 100644 (file)
@@ -53,7 +53,9 @@ fn runtest(me: &str) {
             "bad output: {}", s);
 
     // Make sure the stack trace is *not* printed
-    let p = template.clone().arg("fail").spawn().unwrap();
+    // (Remove RUST_BACKTRACE from our own environment, in case developer
+    // is running `make check` with it on.)
+    let p = template.clone().arg("fail").env_remove("RUST_BACKTRACE").spawn().unwrap();
     let out = p.wait_with_output().unwrap();
     assert!(!out.status.success());
     let s = str::from_utf8(&out.error).unwrap();
index 8afb33c7669f542158e198b0a0759ae41987cc83..01ac2fc20bffe1ebb3f918dad124e60f5cf98c4d 100644 (file)
@@ -9,10 +9,10 @@
 // except according to those terms.
 
 pub fn main() {
-    assert_eq!(0xffffffffu32, (-1 as u32));
-    assert_eq!(4294967295u32, (-1 as u32));
-    assert_eq!(0xffffffffffffffffu64, (-1 as u64));
-    assert_eq!(18446744073709551615u64, (-1 as u64));
+    assert_eq!(0xffffffff, (-1 as u32));
+    assert_eq!(4294967295, (-1 as u32));
+    assert_eq!(0xffffffffffffffff, (-1 as u64));
+    assert_eq!(18446744073709551615, (-1 as u64));
 
-    assert_eq!(-2147483648i32 - 1i32, 2147483647i32);
+    assert_eq!(-2147483648 - 1, 2147483647);
 }
index 7bb9f042fe891ee418b2112c7f522f82fa54bbd7..24bfbd9eb44088b54b901caaa95587d5653255e7 100644 (file)
@@ -16,8 +16,8 @@
 use std::collections::BitVec;
 
 fn bitv_test() {
-    let mut v1 = box BitVec::from_elem(31, false);
-    let v2 = box BitVec::from_elem(31, true);
+    let mut v1: Box<_> = box BitVec::from_elem(31, false);
+    let v2: Box<_> = box BitVec::from_elem(31, true);
     v1.union(&*v2);
 }
 
index d319aaa2f8e18b58e80317f319c50413f484d2b6..8be6d1bd35ae81f48ac80690dac90d02472ccaa6 100644 (file)
@@ -13,6 +13,6 @@ fn asBlock<F>(f: F) -> uint where F: FnOnce() -> uint {
 }
 
 pub fn main() {
-   let x = asBlock(|| 22_usize);
-   assert_eq!(x, 22_usize);
+   let x = asBlock(|| 22);
+   assert_eq!(x, 22);
 }
index d5d26f42ef0953cce28df180d701eaa9b81e3c04..7cbe8104deb5d939176929e563cd773983149072 100644 (file)
@@ -11,8 +11,8 @@
 fn iter_vec<T, F>(v: Vec<T> , mut f: F) where F: FnMut(&T) { for x in &v { f(x); } }
 
 pub fn main() {
-    let v = vec![1i32, 2, 3, 4, 5, 6, 7];
-    let mut odds = 0i32;
+    let v = vec![1, 2, 3, 4, 5, 6, 7];
+    let mut odds = 0;
     iter_vec(v, |i| {
         if *i % 2 == 1 {
             odds += 1;
index 8c079ca4b079afe2e3e600424abe294ba624f327..7701f6114ca6233a29b077919fd3c7b3247ae3ef 100644 (file)
@@ -11,7 +11,7 @@
 fn iter_vec<T, F>(v: Vec<T>, mut f: F) where F: FnMut(&T) { for x in &v { f(x); } }
 
 pub fn main() {
-    let v = vec![1i32, 2, 3, 4, 5];
+    let v = vec![1, 2, 3, 4, 5];
     let mut sum = 0;
     iter_vec(v.clone(), |i| {
         iter_vec(v.clone(), |j| {
index c907778339ec50b64e72f42343c9b25321975bd1..75161d16bc064c5d3954f2a36d1519bdbba64755 100644 (file)
@@ -15,7 +15,7 @@
 // the closures are in scope. Issue #6801.
 
 fn a() -> i32 {
-    let mut x = 3i32;
+    let mut x = 3;
     x += 1;
     let c1 = || x * 4;
     let c2 = || x * 5;
@@ -27,7 +27,7 @@ fn get(x: &i32) -> i32 {
 }
 
 fn b() -> i32 {
-    let mut x = 3i32;
+    let mut x = 3;
     x += 1;
     let c1 = || get(&x);
     let c2 = || get(&x);
@@ -35,7 +35,7 @@ fn b() -> i32 {
 }
 
 fn c() -> i32 {
-    let mut x = 3i32;
+    let mut x = 3;
     x += 1;
     let c1 = || x * 5;
     let c2 = || get(&x);
index 1be57674fa1ff4ad9c981e3bd59c924029011e39..27fbfc9641088137c6abe59aa178e9c854d45d96 100644 (file)
@@ -13,7 +13,7 @@
 #![feature(unboxed_closures)]
 
 pub fn main() {
-    let bar = box 3;
+    let bar: Box<_> = box 3;
     let h = || -> int *bar;
     assert_eq!(h(), 3);
 }
index 2dbaec8fbb16796e8d072f80aa8e73e005876c6e..d35600ef22efd5d327bda94cf5dbc1407cd05baa 100644 (file)
@@ -26,11 +26,11 @@ fn add_int(x: &mut Ints, v: int) {
 
 fn iter_ints<F>(x: &Ints, mut f: F) -> bool where F: FnMut(&int) -> bool {
     let l = x.values.len();
-    (0_usize..l).all(|i| f(&x.values[i]))
+    (0..l).all(|i| f(&x.values[i]))
 }
 
 pub fn main() {
-    let mut ints = box Ints {sum: box 0, values: Vec::new()};
+    let mut ints: Box<_> = box Ints {sum: box 0, values: Vec::new()};
     add_int(&mut *ints, 22);
     add_int(&mut *ints, 44);
 
index 6246ee9c6c41a9ad4bdcd7c94cc8c8a1dfa9c82f..1de7520d2b1d04218cf0f5b2c943991ee2a77364 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-fast doesn't like extern crate
 
 extern crate libc;
 
index dd417f1a9eb73ad53fe6d1d0135a6cded719368a..19316590c262d6967bbd20f75b183fbdc56e8756 100644 (file)
@@ -17,8 +17,8 @@ fn each<'a,T,F:FnMut(&'a T)>(x: &'a [T], mut f: F) {
 }
 
 fn main() {
-    let mut sum = 0_usize;
-    let elems = [ 1_usize, 2, 3, 4, 5 ];
+    let mut sum = 0;
+    let elems = [ 1, 2, 3, 4, 5 ];
     each(&elems, |val: &uint| sum += *val);
     assert_eq!(sum, 15);
 }
index f8a680b2a97ac74b53e5439f3f2151df38681604..fc71e6c59fcafe6f197492cf9b478d5b6742fb6c 100644 (file)
@@ -16,6 +16,6 @@ pub fn main() {
     assert_eq!(u, 'Q' as u32);
     assert_eq!(i as u8, 'Q' as u8);
     assert_eq!(i as u8 as i8, 'Q' as u8 as i8);
-    assert_eq!(0x51u8 as char, 'Q');
+    assert_eq!(0x51 as char, 'Q');
     assert_eq!(0 as u32, false as u32);
 }
index 00c600ed006f87d8125fa0ba0da420e3cb526cf2..cd8f783a2e523ab2756e1414791ed09c11fa0c4b 100644 (file)
@@ -17,8 +17,8 @@
 use cci_borrow_lib::foo;
 
 pub fn main() {
-    let p = box 22_usize;
+    let p: Box<_> = box 22;
     let r = foo(&*p);
     println!("r={}", r);
-    assert_eq!(r, 22_usize);
+    assert_eq!(r, 22);
 }
index c4b55b9962fb65027cb8482197db1853c66329d7..bda3b73e29c4927a3e7908253771e45732c40eb7 100644 (file)
@@ -17,7 +17,7 @@ pub fn main() {
     //let bt0 = sys::frame_address();
     //println!("%?", bt0);
 
-    3_usize.to(10_usize, |i| {
+    3.to(10, |i| {
         println!("{}", i);
 
         //let bt1 = sys::frame_address();
index e4b26ba74be0215fc9e5d86a21f9e34daf3807ac..5b91af7a19431b2e364c48bf0e6bbc739aefdb18 100644 (file)
 extern crate cci_iter_lib;
 
 pub fn main() {
-    //let bt0 = sys::rusti::frame_address(1u32);
+    //let bt0 = sys::rusti::frame_address(1);
     //println!("%?", bt0);
     cci_iter_lib::iter(&[1, 2, 3], |i| {
         println!("{}", *i);
-        //assert!(bt0 == sys::rusti::frame_address(2u32));
+        //assert!(bt0 == sys::rusti::frame_address(2));
     })
 }
index 2040bd7ad713236ded387435a86988648ff9d6e3..cc76ed530c4b5e7fa491f5fba62cbcfed3a13ed3 100644 (file)
@@ -21,7 +21,7 @@ pub fn main() {
     // actually working.
     //let bt0 = sys::frame_address();
     //println!("%?", bt0);
-    iter(vec!(1_usize, 2_usize, 3_usize), |i| {
+    iter(vec!(1, 2, 3), |i| {
         println!("{}", i);
 
         //let bt1 = sys::frame_address();
index 9a388c9bc241d99d0dfc0c2db473bb8af978feb3..da51ad761c70a15db384c8ae3e606d94dffdd420 100644 (file)
@@ -25,6 +25,6 @@ fn print_out(thing: Box<ToString>, expected: String) {
 }
 
 pub fn main() {
-  let nyan: Box<ToString> = box cat(0_usize, 2, "nyan".to_string()) as Box<ToString>;
+  let nyan: Box<ToString> = box cat(0, 2, "nyan".to_string()) as Box<ToString>;
   print_out(nyan, "nyan".to_string());
 }
index 476594c270ec3a2ed781ac81d71abc06fd62754c..01513ab6f47e6deba3d6c837ded4361310cdf740 100644 (file)
@@ -42,8 +42,8 @@ pub fn eat(&mut self) -> bool {
 impl cat {
     fn meow(&mut self) {
       println!("Meow");
-      self.meows += 1_usize;
-      if self.meows % 5_usize == 0_usize {
+      self.meows += 1;
+      if self.meows % 5 == 0 {
           self.how_hungry += 1;
       }
     }
@@ -59,7 +59,7 @@ fn cat(in_x : uint, in_y : int, in_name: String) -> cat {
 
 
 pub fn main() {
-    let mut nyan = cat(0_usize, 2, "nyan".to_string());
+    let mut nyan = cat(0, 2, "nyan".to_string());
     let mut nyan: &mut noisy = &mut nyan;
     nyan.speak();
 }
index 14247ad775487cc7f7dc9d0c6f41d8376608bd63..c98e53c8a95a9c198bc6a008222d98979e7f3c58 100644 (file)
@@ -21,7 +21,7 @@ fn drop(&mut self) {
 
 fn cat(done: extern fn(uint)) -> cat {
     cat {
-        meows: 0_usize,
+        meows: 0,
         done: done
     }
 }
index 4c7d0e6951ab64c33749a94710b612bba065f7ea..1cf4c35ee96e0fe860544e9c73985b0e02117bc2 100644 (file)
@@ -27,7 +27,7 @@ pub fn get_name(&self) -> String { self.name.clone() }
     pub fn cat(in_name: String) -> cat {
         cat {
             name: in_name,
-            meows: 0_usize
+            meows: 0
         }
     }
 }
index 47cc500e44ecb1ff05c63652ec8c87727c85625d..55acd2e040d9e51e8b1e60fd7b2010e40fa346d1 100644 (file)
@@ -13,8 +13,8 @@
 use cci_class_2::kitties::cat;
 
 pub fn main() {
-  let nyan : cat = cat(52_usize, 99);
-  let kitty = cat(1000_usize, 2);
+  let nyan : cat = cat(52, 99);
+  let kitty = cat(1000, 2);
   assert_eq!(nyan.how_hungry, 99);
   assert_eq!(kitty.how_hungry, 2);
   nyan.speak();
index d62a726dcdd55bb6d077508c7560bf7f05f30807..34c309780b1bc12b4b903d0ba2f0c88ca6938c15 100644 (file)
 use cci_class_3::kitties::cat;
 
 pub fn main() {
-    let mut nyan : cat = cat(52_usize, 99);
-    let kitty = cat(1000_usize, 2);
+    let mut nyan : cat = cat(52, 99);
+    let kitty = cat(1000, 2);
     assert_eq!(nyan.how_hungry, 99);
     assert_eq!(kitty.how_hungry, 2);
     nyan.speak();
-    assert_eq!(nyan.meow_count(), 53_usize);
+    assert_eq!(nyan.meow_count(), 53);
 }
index 18fb03ec935ed59fc2ee67246da1ffed3bb0802a..8fa76342286153a1cf78df51b9c26e1520a6f4d0 100644 (file)
@@ -15,7 +15,7 @@ struct cat {
 }
 
 impl cat {
-    pub fn speak(&mut self) { self.meows += 1_usize; }
+    pub fn speak(&mut self) { self.meows += 1; }
     pub fn meow_count(&mut self) -> uint { self.meows }
 }
 
@@ -27,10 +27,10 @@ fn cat(in_x: uint, in_y: int) -> cat {
 }
 
 pub fn main() {
-  let mut nyan: cat = cat(52_usize, 99);
-  let kitty = cat(1000_usize, 2);
+  let mut nyan: cat = cat(52, 99);
+  let kitty = cat(1000, 2);
   assert_eq!(nyan.how_hungry, 99);
   assert_eq!(kitty.how_hungry, 2);
   nyan.speak();
-  assert_eq!(nyan.meow_count(), 53_usize);
+  assert_eq!(nyan.meow_count(), 53);
 }
index b529b0a077210b62012c2e9c5697b06d6941b518..557f9986238c7432a5798487df7ad05dca7fb930 100644 (file)
@@ -32,12 +32,12 @@ fn cat<U>(in_x : uint, in_y : int, in_info: Vec<U> ) -> cat<U> {
 }
 
 pub fn main() {
-  let mut nyan : cat<int> = cat::<int>(52_usize, 99, vec!(9));
-  let mut kitty = cat(1000_usize, 2, vec!("tabby".to_string()));
+  let mut nyan : cat<int> = cat::<int>(52, 99, vec!(9));
+  let mut kitty = cat(1000, 2, vec!("tabby".to_string()));
   assert_eq!(nyan.how_hungry, 99);
   assert_eq!(kitty.how_hungry, 2);
   nyan.speak(vec!(1,2,3));
-  assert_eq!(nyan.meow_count(), 55_usize);
+  assert_eq!(nyan.meow_count(), 55);
   kitty.speak(vec!("meow".to_string(), "mew".to_string(), "purr".to_string(), "chirp".to_string()));
-  assert_eq!(kitty.meow_count(), 1004_usize);
+  assert_eq!(kitty.meow_count(), 1004);
 }
index daff321efcfd9d39299fb7c03e35b30934635d8c..2bdc053675fbef16b43064d36ffedaa9e1385b7f 100644 (file)
@@ -39,8 +39,8 @@ pub fn eat(&mut self) -> bool {
 impl cat {
     fn meow(&mut self) {
         println!("Meow");
-        self.meows += 1_usize;
-        if self.meows % 5_usize == 0_usize {
+        self.meows += 1;
+        if self.meows % 5 == 0 {
             self.how_hungry += 1;
         }
     }
@@ -67,6 +67,6 @@ fn print_out(thing: Box<ToString>, expected: String) {
 }
 
 pub fn main() {
-  let nyan: Box<ToString> = box cat(0_usize, 2, "nyan".to_string()) as Box<ToString>;
+  let nyan: Box<ToString> = box cat(0, 2, "nyan".to_string()) as Box<ToString>;
   print_out(nyan, "nyan".to_string());
 }
index b56a749d33bb85d9fef9501a9f777ce55b7e81da..c50a8cc83a503ee8b8358180f17add7f82cdedb6 100644 (file)
@@ -17,7 +17,7 @@ struct cat<U> {
 }
 
 impl<U> cat<U> {
-    pub fn speak(&mut self) { self.meows += 1_usize; }
+    pub fn speak(&mut self) { self.meows += 1; }
     pub fn meow_count(&mut self) -> uint { self.meows }
 }
 
@@ -31,6 +31,6 @@ fn cat<U>(in_x : uint, in_y : int) -> cat<U> {
 
 
 pub fn main() {
-  let _nyan : cat<int> = cat::<int>(52_usize, 99);
-  //  let mut kitty = cat(1000_usize, 2);
+  let _nyan : cat<int> = cat::<int>(52, 99);
+  //  let mut kitty = cat(1000, 2);
 }
index 8037d77807d1d76e0397328d0911452cdd55e4f2..0966045464878f364ed99be06d85e94dc5268d5c 100644 (file)
@@ -13,8 +13,8 @@
 use cci_class::kitties::cat;
 
 pub fn main() {
-  let nyan : cat = cat(52_usize, 99);
-  let kitty = cat(1000_usize, 2);
+  let nyan : cat = cat(52, 99);
+  let kitty = cat(1000, 2);
   assert_eq!(nyan.how_hungry, 99);
   assert_eq!(kitty.how_hungry, 2);
 }
index b15d6544fed29ddea62df03404cf82d2ae6056bb..502fa73ed93e53a58cacd7e8317271505d2375f1 100644 (file)
@@ -26,8 +26,8 @@ fn cat(in_x : uint, in_y : int) -> cat {
 }
 
 pub fn main() {
-  let mut nyan : cat = cat(52_usize, 99);
-  let kitty = cat(1000_usize, 2);
+  let mut nyan : cat = cat(52, 99);
+  let kitty = cat(1000, 2);
   assert_eq!(nyan.how_hungry, 99);
   assert_eq!(kitty.how_hungry, 2);
   nyan.speak();
index 9bf8df3ce4bc99182b2778961fcff012ddffa7a0..3cf529f2958bdfcaf4c52dc202db0d8490ff3b73 100644 (file)
@@ -22,8 +22,8 @@ fn cat(in_x : uint, in_y : int) -> cat {
 }
 
 pub fn main() {
-  let nyan : cat = cat(52_usize, 99);
-  let kitty = cat(1000_usize, 2);
+  let nyan : cat = cat(52, 99);
+  let kitty = cat(1000, 2);
   assert_eq!(nyan.how_hungry, 99);
   assert_eq!(kitty.how_hungry, 2);
 }
index 96ae7e3d3368f2fdc5abed5d7c8fbbbdd5f16e85..ff883294fd3940b4c115ef22e195b433b37e788b 100644 (file)
@@ -43,7 +43,7 @@ fn get_bar(x: uint) -> Vec<uint> { vec!(x * 2) }
 
 pub fn fails() {
     let x = 2;
-    let mut y = Vec::new();
+    let mut y: Vec<Box<_>> = Vec::new();
     y.push(box Conzabble::Bickwick(do_it(&get_bar(x))));
 }
 
index 8eeae7a28ac8543978d2078df31d197c7a466f24..5cc567cb14c6efda9c6561f00cdcced39a449d0d 100644 (file)
@@ -19,7 +19,7 @@ struct Pair {
 }
 
 pub fn main() {
-    let z = box Pair { a : 10, b : 12};
+    let z: Box<_> = box Pair { a : 10, b : 12};
 
     let _t = Thread::spawn(move|| {
         assert_eq!(z.a, 10);
index ee19d9e69b3018788b4abd0e534f0fa065375dc9..8a9325aecb1438832904b9deb3b6990dafdb91dd 100644 (file)
 // rvalue expressions to be unsized. See #20169 for more information.
 
 pub fn main() {
-    let _: Box<[int]> = box { [1, 2, 3] };
-    let _: Box<[int]> = box if true { [1, 2, 3] } else { [1, 3, 4] };
-    let _: Box<[int]> = box match true { true => [1, 2, 3], false => [1, 3, 4] };
-    let _: Box<Fn(int) -> _> = box { |x| (x as u8) };
-    let _: Box<Debug> = box if true { false } else { true };
-    let _: Box<Debug> = box match true { true => 'a', false => 'b' };
+    // FIXME #22405: We cannot infer the type `Box<[int; k]>` for
+    // the r-value expression from the context `Box<[int]>`, and
+    // therefore the `box EXPR` desugaring breaks down.
+    //
+    // One could reasonably claim that the `box EXPR` desugaring is
+    // effectively regressing half of Issue #20169. Hopefully we will
+    // eventually fix that, at which point the `Box::new` calls below
+    // should be replaced wth uses of `box`.
+
+    let _: Box<[int]> = Box::new({ [1, 2, 3] });
+    let _: Box<[int]> = Box::new(if true { [1, 2, 3] } else { [1, 3, 4] });
+    let _: Box<[int]> = Box::new(match true { true => [1, 2, 3], false => [1, 3, 4] });
+    let _: Box<Fn(int) -> _> = Box::new({ |x| (x as u8) });
+    let _: Box<Debug> = Box::new(if true { false } else { true });
+    let _: Box<Debug> = Box::new(match true { true => 'a', false => 'b' });
 
     let _: &[int] = &{ [1, 2, 3] };
     let _: &[int] = &if true { [1, 2, 3] } else { [1, 3, 4] };
@@ -36,6 +45,6 @@ pub fn main() {
 
     let _: Vec<Box<Fn(int) -> _>> = vec![
         Box::new(|x| (x as u8)),
-        box |x| (x as i16 as u8),
+        Box::new(|x| (x as i16 as u8)),
     ];
 }
index 098a08b07871d29a274736e4b0fb50ebba987e85..2592957b738596541d5bdd1afc5058d2787e9e5f 100644 (file)
 #![feature(box_syntax)]
 
 pub fn main() {
-    let _: Box<[int]> = if true { box [1, 2, 3] } else { box [1] };
+    let _: Box<[int]> =
+        if true { let b: Box<_> = box [1, 2, 3]; b } else { let b: Box<_> = box [1]; b };
 
-    let _: Box<[int]> = match true { true => box [1, 2, 3], false => box [1] };
+    let _: Box<[int]> = match true {
+        true => { let b: Box<_> = box [1, 2, 3]; b }
+        false => { let b: Box<_> = box [1]; b }
+    };
 
     // Check we don't get over-keen at propagating coercions in the case of casts.
     let x = if true { 42 } else { 42u8 } as u16;
index ade18a71259678de4440b813b2837659cfc358af..32230c82a7253a9b604f8cfb3780620933ba1f02 100644 (file)
@@ -18,7 +18,7 @@ fn bip(v: &[uint]) -> Vec<uint> {
 }
 
 pub fn main() {
-    let mut the_vec = vec!(1_usize, 2, 3, 100);
+    let mut the_vec = vec!(1, 2, 3, 100);
     assert_eq!(the_vec.clone(), bar(&mut the_vec));
     assert_eq!(the_vec.clone(), bip(&the_vec));
 }
index b0c3a5922b6344f86e7f7dbaf88ce44617569c73..2de881993f156f07f62b833319b25f5bb90eb79a 100644 (file)
@@ -15,12 +15,12 @@ pub fn main() {
     assert_eq!(concat!("qux", "quux",).to_string(), "quxquux".to_string());
 
     assert_eq!(
-        concat!(1, 2, 3_usize, 4f32, 4.0, 'a', true),
+        concat!(1, 2, 3, 4f32, 4.0, 'a', true),
         "12344.0atrue"
     );
 
     assert!(match "12344.0atrue" {
-        concat!(1, 2, 3_usize, 4f32, 4.0, 'a', true) => true,
+        concat!(1, 2, 3, 4f32, 4.0, 'a', true) => true,
         _ => false
     })
 }
index b5a5f57d07abda322171f642cf19c29b7a9eec5f..90142350772b82693c6b3b1da58c63513aa62358 100644 (file)
@@ -8,7 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// compile-flags: --cfg ndebug
+// compile-flags: -C debug-assertions=no
 // exec-env:RUST_LOG=conditional-debug-macro-off=4
 
 #[macro_use]
index cdb96e5dcbfcd166be6d8cf44d12b20b8e808cbb..bdde0cf02c95895b244084d70c0ca3112906ecd9 100644 (file)
@@ -58,6 +58,6 @@ pub fn main() {
     assert_eq!(BLOCK_FN(300), 300);
     assert_eq!(BLOCK_ENUM_CONSTRUCTOR(200), Some(200));
     // FIXME #13972
-    // assert_eq!(BLOCK_UNSAFE_SAFE_PTR as *const isize as usize, 0xdeadbeef_us);
-    // assert_eq!(BLOCK_UNSAFE_SAFE_PTR_2 as *const isize as usize, 0xdeadbeef_us);
+    // assert_eq!(BLOCK_UNSAFE_SAFE_PTR as *const isize as usize, 0xdeadbeef);
+    // assert_eq!(BLOCK_UNSAFE_SAFE_PTR_2 as *const isize as usize, 0xdeadbeef);
 }
index 93a7d3e1c36aa1bf095a89ac9f313e0f1468e861..9b0e7e4e75ebfa0700b202cec905dfb360297141 100644 (file)
@@ -11,9 +11,6 @@
 // Make sure const bounds work on things, and test that a few types
 // are const.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn foo<T: Sync>(x: T) -> T { x }
 
 struct F { field: int }
@@ -23,7 +20,7 @@ pub fn main() {
     foo("hi".to_string());
     foo(~[1, 2, 3]);
     foo(F{field: 42});
-    foo((1, 2_usize));
+    foo((1, 2));
     foo(@1);*/
-    foo(box 1);
+    foo(Box::new(1));
 }
index 1a3e87b55b64b5f5a438c8bceda395f08ed8dde5..043bfe429add3286620f4eefd503d6d66767e09d 100644 (file)
@@ -22,7 +22,7 @@
 pub fn main() {
     use crate_method_reexport_grrrrrrr2::rust::add;
     use crate_method_reexport_grrrrrrr2::rust::cx;
-    let x = box() ();
+    let x: Box<_> = box () ();
     x.cx();
     let y = ();
     y.add("hi".to_string());
diff --git a/src/test/run-pass/deprecated-derive.rs b/src/test/run-pass/deprecated-derive.rs
new file mode 100644 (file)
index 0000000..494d62c
--- /dev/null
@@ -0,0 +1,15 @@
+// Copyright 2015 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.
+
+#[derive(Show)]
+//~^ WARNING derive(Show) is deprecated
+struct Test1;
+
+fn main() { }
index 41c74250b3b0ef0a7ebfecb6cd900f3ded848553..fc97b22a4a99e3cedd167e1789ca91091854e4b6 100644 (file)
@@ -14,7 +14,7 @@
 use std::cell::Cell;
 
 pub fn main() {
-    let x = box Cell::new(5);
+    let x: Box<_> = box Cell::new(5);
     x.set(1000);
     println!("{}", x.get());
 }
index b00ceb6ed22c75b622f25e57b26278dfccd5d1bd..4d157f64fb9eda85553d93f8141692b990783a73 100644 (file)
@@ -20,6 +20,7 @@ struct A {
 
 pub fn main() {
     let a: A = Default::default();
-    let b: Box<[_]> = box [];
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let b: Box<[_]> = Box::<[bool; 0]>::new([]);
     assert_eq!(a.foo, b);
 }
index 838d05cf0d53084873383d4c3cabd51529818619..454156b4c9e3fa25b9c0ddcbfff14a15f9738afd 100644 (file)
@@ -23,7 +23,8 @@ struct A {
 }
 
 fn main() {
-    let obj = A { foo: box [true, false] };
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let obj = A { foo: Box::new([true, false]) };
     let s = json::encode(&obj).unwrap();
     let obj2: A = json::decode(&s).unwrap();
     assert!(obj.foo == obj2.foo);
index 3b89c943edb1c20f4f2cae307338e4699f4b7ee5..03c93d3ab949b1efa06265c00e3989819f0b0bb1 100644 (file)
@@ -8,15 +8,13 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 #[derive(PartialEq, PartialOrd, Eq, Ord)]
 struct Foo(Box<[u8]>);
 
 pub fn main() {
-    let a = Foo(box [0, 1, 2]);
-    let b = Foo(box [0, 1, 2]);
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let a = Foo(Box::new([0, 1, 2]));
+    let b = Foo(Box::new([0, 1, 2]));
     assert!(a == b);
     println!("{}", a != b);
     println!("{}", a < b);
index 8018f681f3833fcd89e270184f86ca0600c2f054..0cb48670f23da3043e6659fcaaf09e0028fa5003 100644 (file)
@@ -9,23 +9,23 @@
 // except according to those terms.
 
 fn check_expr() {
-    let _:         & uint =     &1_usize;
-    let _:       & & uint =    &&1_usize;
-    let _:     & & & uint =   &&&1_usize;
-    let _:     & & & uint =  & &&1_usize;
-    let _:   & & & & uint =  &&&&1_usize;
-    let _:   & & & & uint = & &&&1_usize;
-    let _: & & & & & uint = &&&&&1_usize;
+    let _:         & uint =     &1;
+    let _:       & & uint =    &&1;
+    let _:     & & & uint =   &&&1;
+    let _:     & & & uint =  & &&1;
+    let _:   & & & & uint =  &&&&1;
+    let _:   & & & & uint = & &&&1;
+    let _: & & & & & uint = &&&&&1;
 }
 
 fn check_ty() {
-    let _:     &uint =         & 1_usize;
-    let _:    &&uint =       & & 1_usize;
-    let _:   &&&uint =     & & & 1_usize;
-    let _:  & &&uint =     & & & 1_usize;
-    let _:  &&&&uint =   & & & & 1_usize;
-    let _: & &&&uint =   & & & & 1_usize;
-    let _: &&&&&uint = & & & & & 1_usize;
+    let _:     &uint =         & 1;
+    let _:    &&uint =       & & 1;
+    let _:   &&&uint =     & & & 1;
+    let _:  & &&uint =     & & & 1;
+    let _:  &&&&uint =   & & & & 1;
+    let _: & &&&uint =   & & & & 1;
+    let _: &&&&&uint = & & & & & 1;
 }
 
 fn check_pat() {
index f94da9fc747e695fb850e7d2f8f5645df66617d5..353bd7a9ce06222c06df4c7c83881f965eed7266 100644 (file)
@@ -62,7 +62,7 @@ pub fn main() {
 
     let (sender, receiver) = channel();
     {
-        let v = Foo::NestedVariant(box 42_usize, SendOnDrop { sender: sender.clone() }, sender);
+        let v = Foo::NestedVariant(box 42, SendOnDrop { sender: sender.clone() }, sender);
     }
     assert_eq!(receiver.recv().unwrap(), Message::DestructorRan);
     assert_eq!(receiver.recv().unwrap(), Message::Dropped);
@@ -79,10 +79,10 @@ pub fn main() {
     let (sender, receiver) = channel();
     let t = {
         thread::spawn(move|| {
-            let mut v = Foo::NestedVariant(box 42usize, SendOnDrop {
+            let mut v = Foo::NestedVariant(box 42, SendOnDrop {
                 sender: sender.clone()
             }, sender.clone());
-            v = Foo::NestedVariant(box 42_usize,
+            v = Foo::NestedVariant(box 42,
                                    SendOnDrop { sender: sender.clone() },
                                    sender.clone());
             v = Foo::SimpleVariant(sender.clone());
index 909f7f4897a6ae8372e20dc2355f65de47976c48..33548d5e298cd16600594173574b8549a810dc42 100644 (file)
@@ -10,9 +10,6 @@
 
 // Test that a custom deref with a fat pointer return type does not ICE
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 use std::ops::{Deref, DerefMut};
 
 pub struct Arr {
@@ -41,6 +38,7 @@ pub fn foo(arr: &mut Arr) {
 }
 
 fn main() {
-    let mut a = Arr { ptr: box [1, 2, 3] };
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let mut a = Arr { ptr: Box::new([1, 2, 3]) };
     foo(&mut a);
 }
index ad4456b5b592d1a05fc65715cbc7e35aff8e4a4e..147a27afa80ed69b683fcc0a59d994675d6c307c 100644 (file)
@@ -10,9 +10,6 @@
 
 // Test that a custom deref with a fat pointer return type does not ICE
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 use std::ops::Deref;
 
 pub struct Arr {
@@ -36,6 +33,7 @@ pub fn foo(arr: &Arr) {
 }
 
 fn main() {
-    let a = Arr { ptr: box [1, 2, 3] };
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let a = Arr { ptr: Box::new([1, 2, 3]) };
     foo(&a);
 }
index ee5193adbc6a4b1d93218a7d3ca0e6e4d3626e44..15558414bf58ebeeffc68cb9b478e2dcf218b0c2 100644 (file)
@@ -115,7 +115,7 @@ pub fn main() {
     foo3(f5);
 
     // Box.
-    let f1 = box [1, 2, 3];
+    let f1 = Box::new([1, 2, 3]);
     assert!((*f1)[1] == 2);
     let f2: Box<[int]> = f1;
     assert!((*f2)[1] == 2);
@@ -125,6 +125,9 @@ pub fn main() {
     foo(&*f1);
     let f2 : Box<Fat<[int]>> = f1;
     foo(&*f2);
-    let f3 : Box<Fat<[int]>> = box Fat { f1: 5, f2: "some str", ptr: [1, 2, 3] };
+
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let f3 : Box<Fat<[int]>> =
+        Box::<Fat<[_; 3]>>::new(Fat { f1: 5, f2: "some str", ptr: [1, 2, 3] });
     foo(&*f3);
 }
index fd1c7247e375d501a9c637b0606c593fcbc9bb79..6590a8e1847dca828bc8446200ddeff140a5bae2 100644 (file)
@@ -95,7 +95,9 @@ pub fn main() {
     assert!(f6.ptr.to_bar() == Bar);
 
     // &*
-    let f7: Box<ToBar> = box Bar1 {f :42};
+    //
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let f7: Box<ToBar> = Box::new(Bar1 {f :42});
     bar(&*f7);
 
     // Deep nesting
index 269e0ee6ce425662b5acd6ba452d547b205bf0bb..0459206c5b910854504bfeaa5227e69079d0a479 100644 (file)
@@ -8,18 +8,17 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 
 pub fn main() {
-    assert!(Some(box() ()).is_some());
+    assert!(Some(Box::new(())).is_some());
 
-    let xs: Box<[()]> = box [];
+    let xs: Box<[()]> = Box::<[(); 0]>::new([]);
     assert!(Some(xs).is_some());
 
     struct Foo;
-    assert!(Some(box Foo).is_some());
+    assert!(Some(Box::new(Foo)).is_some());
 
-    let ys: Box<[Foo]> = box [];
+    let ys: Box<[Foo]> = Box::<[Foo; 0]>::new([]);
     assert!(Some(ys).is_some());
 }
index e95d58c706b27689f96c016ac3d7581eac87d25a..f56d8843acd3fae7fc37fc4ecdca227b8a064f68 100644 (file)
@@ -8,9 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 pub fn main() {
-    let x = *box() ();
+    let x = *Box::new(());
 }
index 382c5c58e92ee70adfde48df8f9c2c248706f94b..865fccbc3fa3a865e65dbdfebcee08ea08a1c390 100644 (file)
@@ -33,6 +33,6 @@ pub fn len(&mut self) -> uint {
 }
 
 pub fn main() {
-    let mut m = box linear_map::<(),()>();
+    let mut m: Box<_> = box linear_map::<(),()>();
     assert_eq!(m.len(), 0);
 }
index e5d8ec3f8ad0d497ca6ae282fd3360343ae1f233..3d06a5562034cc0c383bcfba68ad93a498f66bc8 100644 (file)
@@ -70,7 +70,7 @@ pub fn spam(self) -> int { self.x.a }
 impl Nus for thing { fn f(&self) {} }
 
 pub fn main() {
-    let y = box thing(A {a: 10});
+    let y: Box<_> = box thing(A {a: 10});
     assert_eq!(y.clone().bar(), 10);
     assert_eq!(y.quux(), 10);
 
index d10b209965f1374dfed9eedb68f3d1bb71f50152..d7d5a39f452f3dee030474b068d7e7ba05c4fd0d 100644 (file)
@@ -12,4 +12,4 @@
 #![allow(unknown_features)]
 #![feature(box_syntax)]
 
-pub fn main() { let x = { box 100 }; assert!((*x == 100)); }
+pub fn main() { let x: Box<_> = { box 100 }; assert!((*x == 100)); }
index 317e54349301144d7f54355f48f810980e3c1572..a58161277989870bf9da7f8a5230ecf9ec836897 100644 (file)
@@ -15,7 +15,7 @@
 
 // Tests for if as expressions returning boxed types
 fn test_box() {
-    let rs = if true { box 100 } else { box 101 };
+    let rs: Box<_> = if true { box 100 } else { box 101 };
     assert_eq!(*rs, 100);
 }
 
index 57ccfe1d5e09253a72c2904093282b842ea1a1dd..9641cacddc0a682e22cc498188ed097e172df876 100644 (file)
@@ -13,7 +13,7 @@
 
 // Tests for match as expressions resulting in boxed types
 fn test_box() {
-    let res = match true { true => { box 100 }, _ => panic!() };
+    let res: Box<_> = match true { true => { box 100 }, _ => panic!() };
     assert_eq!(*res, 100);
 }
 
index 49c3bf62dbc859a57236716eb8cf44ca49c7abb2..2e86b3774c8dd64722fc5e493606aa5002056a9a 100644 (file)
@@ -17,6 +17,6 @@
 
 pub fn main() {
     unsafe {
-        assert_eq!(22_u8, rust_dbg_extern_identity_u8(22_u8));
+        assert_eq!(22, rust_dbg_extern_identity_u8(22));
     }
 }
index 07c04af8e1bfd9ce95901d2ae0456e684c81446a..2c01808440762e30b7038e4f10f3a2d60a2be4f5 100644 (file)
@@ -17,6 +17,6 @@
 
 pub fn main() {
     unsafe {
-        assert_eq!(22_u32, rust_dbg_extern_identity_u32(22_u32));
+        assert_eq!(22, rust_dbg_extern_identity_u32(22));
     }
 }
index e19c73ebe2054fa552c7b9dfcd9d7b63ee230abe..e72e87d3d93635ebc142082fbfd0fd16cbb60593 100644 (file)
@@ -17,6 +17,6 @@
 
 pub fn main() {
     unsafe {
-        assert_eq!(22_u64, rust_dbg_extern_identity_u64(22_u64));
+        assert_eq!(22, rust_dbg_extern_identity_u64(22));
     }
 }
diff --git a/src/test/run-pass/extern-stress.rs b/src/test/run-pass/extern-stress.rs
deleted file mode 100644 (file)
index b9e08e4..0000000
+++ /dev/null
@@ -1,49 +0,0 @@
-// 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.
-
-// This creates a bunch of descheduling tasks that run concurrently
-// while holding onto C stacks
-
-extern crate libc;
-use std::thread::Thread;
-
-mod rustrt {
-    extern crate libc;
-
-    #[link(name = "rust_test_helpers")]
-    extern {
-        pub fn rust_dbg_call(cb: extern "C" fn(libc::uintptr_t) -> libc::uintptr_t,
-                             data: libc::uintptr_t)
-                             -> libc::uintptr_t;
-    }
-}
-
-extern fn cb(data: libc::uintptr_t) -> libc::uintptr_t {
-    if data == 1 {
-        data
-    } else {
-        Thread::yield_now();
-        count(data - 1) + count(data - 1)
-    }
-}
-
-fn count(n: libc::uintptr_t) -> libc::uintptr_t {
-    unsafe {
-        rustrt::rust_dbg_call(cb, n)
-    }
-}
-
-pub fn main() {
-    (0_usize..100).map(|_| {
-        Thread::scoped(move|| {
-            assert_eq!(count(5), 16);
-        })
-    }).collect::<Vec<_>>();
-}
diff --git a/src/test/run-pass/extern-yield.rs b/src/test/run-pass/extern-yield.rs
deleted file mode 100644 (file)
index 80428d7..0000000
+++ /dev/null
@@ -1,48 +0,0 @@
-// 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.
-
-extern crate libc;
-use std::thread::Thread;
-
-mod rustrt {
-    extern crate libc;
-
-    #[link(name = "rust_test_helpers")]
-    extern {
-        pub fn rust_dbg_call(cb: extern "C" fn (libc::uintptr_t) -> libc::uintptr_t,
-                             data: libc::uintptr_t)
-                             -> libc::uintptr_t;
-    }
-}
-
-extern fn cb(data: libc::uintptr_t) -> libc::uintptr_t {
-    if data == 1 {
-        data
-    } else {
-        count(data - 1) + count(data - 1)
-    }
-}
-
-fn count(n: libc::uintptr_t) -> libc::uintptr_t {
-    unsafe {
-        Thread::yield_now();
-        rustrt::rust_dbg_call(cb, n)
-    }
-}
-
-pub fn main() {
-    (0..10_usize).map(|i| {
-        Thread::scoped(move|| {
-            let result = count(5);
-            println!("result = {}", result);
-            assert_eq!(result, 16);
-        })
-    }).collect::<Vec<_>>();
-}
index 24b711328a18ab0fb5681e0de0d07b15d844f3d1..172ece0c4bfd94ccc8bbfe861bf774eb49887187 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-fast doesn't like extern crate
 
 extern crate libc;
 use std::ffi::CString;
@@ -32,5 +31,5 @@ fn strlen(str: String) -> uint {
 
 pub fn main() {
     let len = strlen("Rust".to_string());
-    assert_eq!(len, 4_usize);
+    assert_eq!(len, 4);
 }
index e1ed0b8ea3b0c0743ba2a5663c553f581f2b6b9e..03023f032335fafa8f7c57336ba5573c16bedb2c 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-fast doesn't like extern crate
 
 extern crate libc;
 
index ce2f895566439433143810603ae1b87984796622..5ebc4effb3718775e0be521deda499c5568e69c0 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-fast doesn't like extern crate
 
 extern crate libc;
 
index b23d8db3cfdd58890ab12cf9c765e74ad1194b9b..581f71a737651a59f5fe1abfcac2eda76e3fd6a8 100644 (file)
@@ -25,7 +25,7 @@ fn foo(Foo {x, ..}: Foo) -> *const uint {
 }
 
 pub fn main() {
-    let obj = box 1;
+    let obj: Box<_> = box 1;
     let objptr: *const uint = &*obj;
     let f = Foo {x: obj, y: box 2};
     let xptr = foo(f);
index 5d44a9461bebcbaf7d30511917e84ea04f3ed0c8..799b865bd2d7aa5c91d50d27cadd4b42f05716c0 100644 (file)
@@ -28,7 +28,7 @@ fn checkval(box ref x: Box<uint>) -> uint {
 }
 
 pub fn main() {
-    let obj = box 1;
+    let obj: Box<_> = box 1;
     let objptr: *const uint = &*obj;
     let xptr = getaddr(obj);
     assert_eq!(objptr, xptr);
index db468ba1802a662f374f32325f86be7e193cbb51..42062b89cfd2fe459eb7d2c86612ec88cab8a7dc 100644 (file)
@@ -14,7 +14,7 @@
 fn id<T:Send>(t: T) -> T { return t; }
 
 pub fn main() {
-    let expected = box 100;
+    let expected: Box<_> = box 100;
     let actual = id::<Box<int>>(expected.clone());
     println!("{}", *actual);
     assert_eq!(*expected, *actual);
index 6e3d19b05d4b1d9272fb0c03ad338132849d8f91..062ee507864bbdf18eb46050b98369943ebfa295 100644 (file)
@@ -10,7 +10,7 @@
 
 use std::num::Int;
 
-extern "C" fn foo<T: Int>(a: T, b: T) -> T { a + b }
+extern "C" fn foo<T: WrappingOps>(a: T, b: T) -> T { a.wrapping_add(b) }
 
 fn main() {
     assert_eq!(99u8, foo(255u8, 100u8));
index 677038af9a9c4e0de4609f0622e812f17f377486..81c4054d0091013a9d9ff2fccddb52e32f327965 100644 (file)
@@ -9,7 +9,6 @@
 // except according to those terms.
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 /**
@@ -61,7 +60,8 @@ fn emit(im: &mut HashMap<String, int>,
         }
 
         let ctrl_clone = ctrl.clone();
-        ::map(input, box |a,b| emit(&mut intermediates, ctrl.clone(), a, b) );
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        ::map(input, Box::new(|a,b| emit(&mut intermediates, ctrl.clone(), a, b)));
         ctrl_clone.send(ctrl_proto::mapper_done).unwrap();
     }
 
index b59e7b67d4eddb4ad11b80ede4fe0193feb0ad4e..f4daf9a4f629789696ce65177ad9f18ea75235b3 100644 (file)
@@ -9,7 +9,6 @@
 // except according to those terms.
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 // Test that `Fn(int) -> int + 'static` parses as `(Fn(int) -> int) +
@@ -17,7 +16,8 @@
 // cause a compilation error. Issue #18772.
 
 fn adder(y: int) -> Box<Fn(int) -> int + 'static> {
-    box move |x| y + x
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    Box::new(move |x| y + x)
 }
 
 fn main() {}
index e5451431adedfd2bc2aba36990872be000f874d5..cebfd89d8aae696295669b13aaaeb0380fd01a82 100644 (file)
@@ -11,4 +11,4 @@
 
 
 
-pub fn main() { let mut x: i32 = -400_i32; x = 0_i32 - x; assert!((x == 400_i32)); }
+pub fn main() { let mut x: i32 = -400; x = 0 - x; assert!((x == 400)); }
index fbb4e446dd55e9d230031769305e46504a4b4be4..c91e738b822dcd58f32155e180a055991fe3e1ed 100644 (file)
@@ -12,9 +12,9 @@
 
 
 pub fn main() {
-    let mut x: i8 = -12i8;
-    let y: i8 = -12i8;
-    x = x + 1i8;
-    x = x - 1i8;
+    let mut x: i8 = -12;
+    let y: i8 = -12;
+    x = x + 1;
+    x = x - 1;
     assert_eq!(x, y);
 }
index d2a1a3c71a5fc1d365c9094e3d426b1262acab0f..766cced4c2673ba11dffcff136480054cb129a8a 100644 (file)
@@ -9,9 +9,9 @@
 // except according to those terms.
 
 fn even(x: uint) -> bool {
-    if x < 2_usize {
+    if x < 2 {
         return false;
-    } else if x == 2_usize { return true; } else { return even(x - 2_usize); }
+    } else if x == 2 { return true; } else { return even(x - 2); }
 }
 
 fn foo(x: uint) {
@@ -22,4 +22,4 @@ fn foo(x: uint) {
     }
 }
 
-pub fn main() { foo(2_usize); }
+pub fn main() { foo(2); }
index 62b8ff528a5e2e1395881d72a19a6dba16a8765e..41c859214e96b188cdc19f970946831ad3bf30f2 100644 (file)
@@ -154,7 +154,7 @@ pub fn main() {
     test_order();
 
     // make sure that format! doesn't move out of local variables
-    let a = box 3;
+    let a: Box<_> = box 3;
     format!("{}", a);
     format!("{}", a);
 
index ee793359fbc89b522786b7c281d93987f0b35b24..4ee06d44e65656a1f8957c09f0722f8619a5a9ad 100644 (file)
@@ -67,7 +67,7 @@ fn test_tup() {
 fn test_unique() {
     let i = &Cell::new(0);
     {
-        let _a = box r(i);
+        let _a: Box<_> = box r(i);
     }
     assert_eq!(i.get(), 1);
 }
@@ -75,7 +75,7 @@ fn test_unique() {
 fn test_unique_rec() {
     let i = &Cell::new(0);
     {
-        let _a = box BoxR {
+        let _a: Box<_> = box BoxR {
             x: r(i)
         };
     }
index 4b0e9168e19bd35fac2a431dfc0dab09508aaf19..d111462ed5a318510692c55a2f179e507fad0d16 100644 (file)
@@ -27,8 +27,8 @@ mod m {
     #[cfg(target_arch = "x86")]
     pub fn main() {
         unsafe {
-            assert_eq!(::rusti::pref_align_of::<u64>(), 8_usize);
-            assert_eq!(::rusti::min_align_of::<u64>(), 4_usize);
+            assert_eq!(::rusti::pref_align_of::<u64>(), 8);
+            assert_eq!(::rusti::min_align_of::<u64>(), 4);
         }
     }
 
@@ -36,8 +36,8 @@ pub fn main() {
     #[cfg(any(target_arch = "x86_64", target_arch = "arm", target_arch = "aarch64"))]
     pub fn main() {
         unsafe {
-            assert_eq!(::rusti::pref_align_of::<u64>(), 8_usize);
-            assert_eq!(::rusti::min_align_of::<u64>(), 8_usize);
+            assert_eq!(::rusti::pref_align_of::<u64>(), 8);
+            assert_eq!(::rusti::min_align_of::<u64>(), 8);
         }
     }
 }
@@ -48,8 +48,8 @@ mod m {
     #[cfg(target_arch = "x86_64")]
     pub fn main() {
         unsafe {
-            assert_eq!(::rusti::pref_align_of::<u64>(), 8u);
-            assert_eq!(::rusti::min_align_of::<u64>(), 8u);
+            assert_eq!(::rusti::pref_align_of::<u64>(), 8);
+            assert_eq!(::rusti::min_align_of::<u64>(), 8);
         }
     }
 }
@@ -60,8 +60,8 @@ mod m {
     #[cfg(target_arch = "x86")]
     pub fn main() {
         unsafe {
-            assert_eq!(::rusti::pref_align_of::<u64>(), 8_usize);
-            assert_eq!(::rusti::min_align_of::<u64>(), 8_usize);
+            assert_eq!(::rusti::pref_align_of::<u64>(), 8);
+            assert_eq!(::rusti::min_align_of::<u64>(), 8);
         }
     }
 
@@ -69,8 +69,8 @@ pub fn main() {
     #[cfg(target_arch = "x86_64")]
     pub fn main() {
         unsafe {
-            assert_eq!(::rusti::pref_align_of::<u64>(), 8_usize);
-            assert_eq!(::rusti::min_align_of::<u64>(), 8_usize);
+            assert_eq!(::rusti::pref_align_of::<u64>(), 8);
+            assert_eq!(::rusti::min_align_of::<u64>(), 8);
         }
     }
 }
@@ -81,8 +81,8 @@ mod m {
     #[cfg(any(target_arch = "arm", target_arch = "aarch64"))]
     pub fn main() {
         unsafe {
-            assert_eq!(::rusti::pref_align_of::<u64>(), 8_usize);
-            assert_eq!(::rusti::min_align_of::<u64>(), 8_usize);
+            assert_eq!(::rusti::pref_align_of::<u64>(), 8);
+            assert_eq!(::rusti::min_align_of::<u64>(), 8);
         }
     }
 }
index d3f62f9d04ad030555d7e393432d5c152cd3976c..1d7a74b042fac815fb7dbc48a9f70873122d607c 100644 (file)
@@ -40,7 +40,7 @@ mod rusti {
 
 pub fn main() {
     unsafe {
-        let mut x = box 1;
+        let mut x: Box<_> = box 1;
 
         assert_eq!(rusti::atomic_load(&*x), 1);
         *x = 5;
index 0daf661c2f6c5bd04f882d018065e1774893f666..09dd5304ec5c21a2a75bdb0bf22c4c270507ff47 100644 (file)
@@ -23,7 +23,7 @@ mod rusti {
 
 pub fn main() {
     unsafe {
-        let x = box 1;
+        let x: Box<_> = box 1;
         let mut y = rusti::init();
         let mut z: *const uint = transmute(&x);
         rusti::move_val_init(&mut y, x);
index 2b0f7cc7d7d3214dad905b149475b645f79303ac..e5724c1e0dc16ce81e211089b6097bf5ae0a94e7 100644 (file)
@@ -37,83 +37,83 @@ pub fn main() {
     unsafe {
         use rusti::*;
 
-        assert_eq!(ctpop8(0u8), 0u8);
-        assert_eq!(ctpop16(0u16), 0u16);
-        assert_eq!(ctpop32(0u32), 0u32);
-        assert_eq!(ctpop64(0u64), 0u64);
-
-        assert_eq!(ctpop8(1u8), 1u8);
-        assert_eq!(ctpop16(1u16), 1u16);
-        assert_eq!(ctpop32(1u32), 1u32);
-        assert_eq!(ctpop64(1u64), 1u64);
-
-        assert_eq!(ctpop8(10u8), 2u8);
-        assert_eq!(ctpop16(10u16), 2u16);
-        assert_eq!(ctpop32(10u32), 2u32);
-        assert_eq!(ctpop64(10u64), 2u64);
-
-        assert_eq!(ctpop8(100u8), 3u8);
-        assert_eq!(ctpop16(100u16), 3u16);
-        assert_eq!(ctpop32(100u32), 3u32);
-        assert_eq!(ctpop64(100u64), 3u64);
-
-        assert_eq!(ctpop8(-1u8), 8u8);
-        assert_eq!(ctpop16(-1u16), 16u16);
-        assert_eq!(ctpop32(-1u32), 32u32);
-        assert_eq!(ctpop64(-1u64), 64u64);
-
-        assert_eq!(ctlz8(0u8), 8u8);
-        assert_eq!(ctlz16(0u16), 16u16);
-        assert_eq!(ctlz32(0u32), 32u32);
-        assert_eq!(ctlz64(0u64), 64u64);
-
-        assert_eq!(ctlz8(1u8), 7u8);
-        assert_eq!(ctlz16(1u16), 15u16);
-        assert_eq!(ctlz32(1u32), 31u32);
-        assert_eq!(ctlz64(1u64), 63u64);
-
-        assert_eq!(ctlz8(10u8), 4u8);
-        assert_eq!(ctlz16(10u16), 12u16);
-        assert_eq!(ctlz32(10u32), 28u32);
-        assert_eq!(ctlz64(10u64), 60u64);
-
-        assert_eq!(ctlz8(100u8), 1u8);
-        assert_eq!(ctlz16(100u16), 9u16);
-        assert_eq!(ctlz32(100u32), 25u32);
-        assert_eq!(ctlz64(100u64), 57u64);
-
-        assert_eq!(cttz8(-1u8), 0u8);
-        assert_eq!(cttz16(-1u16), 0u16);
-        assert_eq!(cttz32(-1u32), 0u32);
-        assert_eq!(cttz64(-1u64), 0u64);
-
-        assert_eq!(cttz8(0u8), 8u8);
-        assert_eq!(cttz16(0u16), 16u16);
-        assert_eq!(cttz32(0u32), 32u32);
-        assert_eq!(cttz64(0u64), 64u64);
-
-        assert_eq!(cttz8(1u8), 0u8);
-        assert_eq!(cttz16(1u16), 0u16);
-        assert_eq!(cttz32(1u32), 0u32);
-        assert_eq!(cttz64(1u64), 0u64);
-
-        assert_eq!(cttz8(10u8), 1u8);
-        assert_eq!(cttz16(10u16), 1u16);
-        assert_eq!(cttz32(10u32), 1u32);
-        assert_eq!(cttz64(10u64), 1u64);
-
-        assert_eq!(cttz8(100u8), 2u8);
-        assert_eq!(cttz16(100u16), 2u16);
-        assert_eq!(cttz32(100u32), 2u32);
-        assert_eq!(cttz64(100u64), 2u64);
-
-        assert_eq!(cttz8(-1u8), 0u8);
-        assert_eq!(cttz16(-1u16), 0u16);
-        assert_eq!(cttz32(-1u32), 0u32);
-        assert_eq!(cttz64(-1u64), 0u64);
-
-        assert_eq!(bswap16(0x0A0Bu16), 0x0B0Au16);
-        assert_eq!(bswap32(0x0ABBCC0Du32), 0x0DCCBB0Au32);
-        assert_eq!(bswap64(0x0122334455667708u64), 0x0877665544332201u64);
+        assert_eq!(ctpop8(0), 0);
+        assert_eq!(ctpop16(0), 0);
+        assert_eq!(ctpop32(0), 0);
+        assert_eq!(ctpop64(0), 0);
+
+        assert_eq!(ctpop8(1), 1);
+        assert_eq!(ctpop16(1), 1);
+        assert_eq!(ctpop32(1), 1);
+        assert_eq!(ctpop64(1), 1);
+
+        assert_eq!(ctpop8(10), 2);
+        assert_eq!(ctpop16(10), 2);
+        assert_eq!(ctpop32(10), 2);
+        assert_eq!(ctpop64(10), 2);
+
+        assert_eq!(ctpop8(100), 3);
+        assert_eq!(ctpop16(100), 3);
+        assert_eq!(ctpop32(100), 3);
+        assert_eq!(ctpop64(100), 3);
+
+        assert_eq!(ctpop8(-1), 8);
+        assert_eq!(ctpop16(-1), 16);
+        assert_eq!(ctpop32(-1), 32);
+        assert_eq!(ctpop64(-1), 64);
+
+        assert_eq!(ctlz8(0), 8);
+        assert_eq!(ctlz16(0), 16);
+        assert_eq!(ctlz32(0), 32);
+        assert_eq!(ctlz64(0), 64);
+
+        assert_eq!(ctlz8(1), 7);
+        assert_eq!(ctlz16(1), 15);
+        assert_eq!(ctlz32(1), 31);
+        assert_eq!(ctlz64(1), 63);
+
+        assert_eq!(ctlz8(10), 4);
+        assert_eq!(ctlz16(10), 12);
+        assert_eq!(ctlz32(10), 28);
+        assert_eq!(ctlz64(10), 60);
+
+        assert_eq!(ctlz8(100), 1);
+        assert_eq!(ctlz16(100), 9);
+        assert_eq!(ctlz32(100), 25);
+        assert_eq!(ctlz64(100), 57);
+
+        assert_eq!(cttz8(-1), 0);
+        assert_eq!(cttz16(-1), 0);
+        assert_eq!(cttz32(-1), 0);
+        assert_eq!(cttz64(-1), 0);
+
+        assert_eq!(cttz8(0), 8);
+        assert_eq!(cttz16(0), 16);
+        assert_eq!(cttz32(0), 32);
+        assert_eq!(cttz64(0), 64);
+
+        assert_eq!(cttz8(1), 0);
+        assert_eq!(cttz16(1), 0);
+        assert_eq!(cttz32(1), 0);
+        assert_eq!(cttz64(1), 0);
+
+        assert_eq!(cttz8(10), 1);
+        assert_eq!(cttz16(10), 1);
+        assert_eq!(cttz32(10), 1);
+        assert_eq!(cttz64(10), 1);
+
+        assert_eq!(cttz8(100), 2);
+        assert_eq!(cttz16(100), 2);
+        assert_eq!(cttz32(100), 2);
+        assert_eq!(cttz64(100), 2);
+
+        assert_eq!(cttz8(-1), 0);
+        assert_eq!(cttz16(-1), 0);
+        assert_eq!(cttz32(-1), 0);
+        assert_eq!(cttz64(-1), 0);
+
+        assert_eq!(bswap16(0x0A0B), 0x0B0A);
+        assert_eq!(bswap32(0x0ABBCC0D), 0x0DCCBB0A);
+        assert_eq!(bswap64(0x0122334455667708), 0x0877665544332201);
     }
 }
index ed88b3c65e09c8f428c3740c77e693a0a9b82c2e..ab65f35dd34d86d6e9ddae3a545d618946d4ccb7 100644 (file)
@@ -65,8 +65,8 @@ pub fn main() {
         assert_approx_eq!(sqrtf32(64f32), 8f32);
         assert_approx_eq!(sqrtf64(64f64), 8f64);
 
-        assert_approx_eq!(powif32(25f32, -2i32), 0.0016f32);
-        assert_approx_eq!(powif64(23.2f64, 2i32), 538.24f64);
+        assert_approx_eq!(powif32(25f32, -2), 0.0016f32);
+        assert_approx_eq!(powif64(23.2f64, 2), 538.24f64);
 
         assert_approx_eq!(sinf32(0f32), 0f32);
         assert_approx_eq!(sinf64(f64::consts::PI / 2f64), 1f64);
index 174a69e1135cdf7a766ada2f71a70984dd537e7d..48ea00e47d696a70c2ef4bd6c72eb7b1e6d12a2d 100644 (file)
@@ -42,13 +42,13 @@ fn new(w: Box<MyTrait+'static>) -> Whatever {
 
 fn main() {
     {
-        let f = box DroppableStruct;
+        let f: Box<_> = box DroppableStruct;
         let _a = Whatever::new(box f as Box<MyTrait>);
     }
     assert!(unsafe { DROPPED });
     unsafe { DROPPED = false; }
     {
-        let f = box DroppableEnum::DroppableVariant1;
+        let f: Box<_> = box DroppableEnum::DroppableVariant1;
         let _a = Whatever::new(box f as Box<MyTrait>);
     }
     assert!(unsafe { DROPPED });
index 22c88c874f096a70a92c8112ff941e438f73ec2d..2ade0df7f6b68811ad371c9359237826bd0cdb1a 100644 (file)
@@ -24,21 +24,21 @@ struct X<T> {
 pub fn main() {
     let x: X<int> = X {
         a: 12345678,
-        b: 9u8,
+        b: 9,
         c: true,
-        d: 10u8,
-        e: 11u16,
-        f: 12u8,
-        g: 13u8
+        d: 10,
+        e: 11,
+        f: 12,
+        g: 13
     };
     bar(x);
 }
 
 fn bar<T>(x: X<T>) {
-    assert_eq!(x.b, 9u8);
+    assert_eq!(x.b, 9);
     assert_eq!(x.c, true);
-    assert_eq!(x.d, 10u8);
-    assert_eq!(x.e, 11u16);
-    assert_eq!(x.f, 12u8);
-    assert_eq!(x.g, 13u8);
+    assert_eq!(x.d, 10);
+    assert_eq!(x.e, 11);
+    assert_eq!(x.f, 12);
+    assert_eq!(x.g, 13);
 }
index 1325b51a54ff2b6a4380f38bb7d64f8d9420846f..c67ce92ee0a9acebcc4bb53e0b876e0fd3728656 100644 (file)
@@ -9,8 +9,8 @@
 // except according to those terms.
 
 #![allow(dead_code)]
-#![allow(unknown_features)]
-#![feature(box_syntax)]
+
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 
 trait Foo { fn dummy(&self) { } }
 impl Foo for int {}
@@ -39,16 +39,16 @@ fn main() {
     let r = &1;
     foog(x, &[r]);
 
-    let x: [Box<Foo>; 2] = [box 1, box 2];
+    let x: [Box<Foo>; 2] = [Box::new(1), Box::new(2)];
     bar(x);
-    bar([box 1, box 2]);
+    bar([Box::new(1), Box::new(2)]);
 
-    let x: &[Box<Foo>] = &[box 1, box 2];
+    let x: &[Box<Foo>] = &[Box::new(1), Box::new(2)];
     bars(x);
-    bars(&[box 1, box 2]);
+    bars(&[Box::new(1), Box::new(2)]);
 
-    let x: &[Box<Foo>] = &[box 1, box 2];
-    foog(x, &[box 1]);
+    let x: &[Box<Foo>] = &[Box::new(1), Box::new(2)];
+    foog(x, &[Box::new(1)]);
 
     struct T<'a> {
         t: [&'a (Foo+'a); 2]
@@ -85,9 +85,9 @@ struct M<'a> {
         t: &'a [Box<Foo+'static>]
     }
     let _n = M {
-        t: &[box 1, box 2]
+        t: &[Box::new(1), Box::new(2)]
     };
-    let x: [Box<Foo>; 2] = [box 1, box 2];
+    let x: [Box<Foo>; 2] = [Box::new(1), Box::new(2)];
     let _n = M {
         t: &x
     };
index 7cccac4483d49da1edfed2dd0c397493dc45c16d..4b2b3e8702427fc8725405d37e887b1831faff2f 100644 (file)
@@ -9,8 +9,6 @@
 // except according to those terms.
 
 #![allow(dead_code)]
-#![allow(unknown_features)]
-#![feature(box_syntax)]
 
 // this code used to cause an ICE
 
@@ -28,5 +26,6 @@ impl X<int> for F {
 }
 
 fn main() {
-  S {f: box F, g: box F};
+  // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+  S {f: Box::new(F), g: Box::new(F) };
 }
index b901e95ff55edb453c6a7b8642af99e394850d67..b09d516dd35922957b512502966d922e82935d2c 100644 (file)
@@ -15,7 +15,7 @@
 
 fn main() {
     // Generate sieve of Eratosthenes for n up to 1e6
-    let n = 1000000_usize;
+    let n = 1000000;
     let mut sieve = BitVec::from_elem(n+1, true);
     let limit: uint = (n as f32).sqrt() as uint;
     for i in 2..limit+1 {
index 00613f35f17bb71a1257021477671d01f7ba02cc..bb34dae77b344874fcf5123da8660bef9b22b61e 100644 (file)
@@ -19,6 +19,6 @@
 use std::thunk::Thunk;
 
 pub fn main() {
-    let mut x = 1i32;
+    let mut x = 1;
     let _thunk = Thunk::new(move|| { x = 2; });
 }
index 2f7ba315aa1f6ae073f1e5d8f0c3f684070131e4..56d1d3599c7fde3dcb7e3cfd8a49c5a88cc46d2f 100644 (file)
@@ -8,10 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn main() {
-    fn test() -> Box<std::any::Any + 'static> { box 1 }
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    fn test() -> Box<std::any::Any + 'static> { Box::new(1) }
     println!("{:?}", test())
 }
index b7dc98b92e0db21feed21496f54a6ef675e43711..11a2e52cf9767a7da97f3cbaaa194721389c25fe 100644 (file)
@@ -15,7 +15,7 @@ fn copy<T: Copy>(&x: &T) -> T {
 }
 
 fn main() {
-    let arr = [(1, 1_usize), (2, 2), (3, 3)];
+    let arr = [(1, 1), (2, 2), (3, 3)];
 
     let v1: Vec<&_> = arr.iter().collect();
     let v2: Vec<_> = arr.iter().map(copy).collect();
index 3c5ece87b737dabae0d7d16709bd68175e3a9cbb..96e2a0dc48539c71f620dfdf434145e038d9d119 100644 (file)
@@ -8,16 +8,14 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 struct Foo<'a> {
     listener: Box<FnMut() + 'a>,
 }
 
 impl<'a> Foo<'a> {
     fn new<F>(listener: F) -> Foo<'a> where F: FnMut() + 'a {
-        Foo { listener: box listener }
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        Foo { listener: Box::new(listener) }
     }
 }
 
index db7eacce9d10b007292ae09dce9b550eef54543f..d413e323a09997738ede945cb2b603abb11e2b08 100644 (file)
@@ -23,6 +23,6 @@ trait A { fn foo(&self) {} }
 impl A for B1 {}
 
 fn main() {
-    let v = box B1;
+    let v: Box<_> = box B1;
     let _c: Box<A> = v.clone();
 }
index 71d88ee6215103a991f81a0a2ea904f45ad3cf16..5924aa44d4d63c672dc701041d446289fdd8cfc6 100644 (file)
 // All 3 expressions should work in that the argument gets
 // coerced to a trait object
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 
 fn main() {
-    send::<Box<Foo>>(box Output(0));
-    Test::<Box<Foo>>::foo(box Output(0));
-    Test::<Box<Foo>>::new().send(box Output(0));
+    send::<Box<Foo>>(Box::new(Output(0)));
+    Test::<Box<Foo>>::foo(Box::new(Output(0)));
+    Test::<Box<Foo>>::new().send(Box::new(Output(0)));
 }
 
 fn send<T>(_: T) {}
index 933e7e40f06d34ce23ae96de299da6a594acb62b..fbf08ab564d3510d9ba11ed64340cee2d1f47a3d 100644 (file)
@@ -8,9 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 trait Matcher {
     fn next_match(&mut self) -> Option<(uint, uint)>;
 }
@@ -32,9 +29,10 @@ trait IntoMatcher<'a, T> {
 
 impl<'a, 'b, F> IntoMatcher<'a, CharPredMatcher<'a, 'b>> for F where F: FnMut(char) -> bool + 'b {
     fn into_matcher(self, s: &'a str) -> CharPredMatcher<'a, 'b> {
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
         CharPredMatcher {
             str: s,
-            pred: box self,
+            pred: Box::new(self),
         }
     }
 }
index ab9554f65d4c89d93aa6c813b883551d737809ea..3dc76f4a089d9a50114b79b3be8ebcc38ce3f58d 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 fn match_on_local() {
-    let mut foo = Some(box 5);
+    let mut foo: Option<Box<_>> = Some(box 5);
     match foo {
         None => {},
         Some(x) => {
@@ -33,7 +33,7 @@ fn match_on_arg(mut foo: Option<Box<i32>>) {
 }
 
 fn match_on_binding() {
-    match Some(box 7) {
+    match Some(Box::new(7)) {
         mut foo => {
             match foo {
                 None => {},
@@ -47,7 +47,7 @@ fn match_on_binding() {
 }
 
 fn match_on_upvar() {
-    let mut foo = Some(box 8i32);
+    let mut foo: Option<Box<_>> = Some(box 8);
     let f = move|| {
         match foo {
             None => {},
index a6b8a04eeb60ed63a88133466eb4933fa09885d8..227d8f7b8c82ab970409f07a228386646f1f0590 100644 (file)
@@ -11,5 +11,5 @@
 use std::iter::AdditiveIterator;
 fn main() {
     let x: [u64; 3] = [1, 2, 3];
-    assert_eq!(6, (0_usize..3).map(|i| x[i]).sum());
+    assert_eq!(6, (0..3).map(|i| x[i]).sum());
 }
index e66ac8ff53c1f76e6511cd13b9e8987cd31baa44..18e4190ee459f6b24acccb8d36a18733a6ca28d8 100644 (file)
@@ -53,12 +53,12 @@ fn index<'a>(&'a self, col: &uint) -> &'a T {
 }
 
 fn main() {
-    let m = Mat::new(vec!(1_usize, 2, 3, 4, 5, 6), 3);
+    let m = Mat::new(vec!(1, 2, 3, 4, 5, 6), 3);
     let r = m.row(1);
 
     assert!(r.index(&2) == &6);
     assert!(r[2] == 6);
-    assert!(r[2_usize] == 6_usize);
+    assert!(r[2] == 6);
     assert!(6 == r[2]);
 
     let e = r[2];
index daf09047bef723649a519d9d5a952376ce28b4ec..786c701a0427bf0808c321b14002c872c25f1c4e 100644 (file)
@@ -11,7 +11,6 @@
 // ignore-pretty
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 struct Parser<'a, I, O> {
@@ -20,13 +19,14 @@ struct Parser<'a, I, O> {
 
 impl<'a, I: 'a, O: 'a> Parser<'a, I, O> {
     fn compose<K: 'a>(mut self, mut rhs: Parser<'a, O, K>) -> Parser<'a, I, K> {
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
         Parser {
-            parse: box move |x: I| {
+            parse: Box::new(move |x: I| {
                 match (self.parse)(x) {
                     Ok(r) => (rhs.parse)(r),
                     Err(e) => Err(e)
                 }
-            }
+            })
         }
     }
 }
index 7bd41cc5b52a2fa06453d197100c5574c0b5daa4..dbfa91553e60cdc88446cd2ee399571e47e93b90 100644 (file)
@@ -17,7 +17,7 @@
 struct Bar<'a> { m: marker::PhantomData<&'a ()> }
 
 impl<'a> i::Foo<'a, uint> for Bar<'a> {
-    fn foo(&self) -> uint { 5_usize }
+    fn foo(&self) -> uint { 5 }
 }
 
 pub fn main() {
index 3cff16409cb9b811c2b6fdf782bb18fdb7824578..497361969bfc3cffa1eddd796358c4c8a496eb05 100644 (file)
 
 // Test that generating drop glue for Box<str> doesn't ICE
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn f(s: Box<str>) -> Box<str> {
     s
 }
 
 fn main() {
     // There is currently no safe way to construct a `Box<str>`, so improvise
-    let box_arr: Box<[u8]> = box ['h' as u8, 'e' as u8, 'l' as u8, 'l' as u8, 'o' as u8];
+    //
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let box_arr: Box<[u8]> = Box::new(['h' as u8, 'e' as u8, 'l' as u8, 'l' as u8, 'o' as u8]);
     let box_str: Box<str> = unsafe { std::mem::transmute(box_arr) };
     assert_eq!(&*box_str, "hello");
     f(box_str);
index ec7481ead0482dd29af975617cf66ad6bd2ae045..2011b87e731021a96761aaea10b2d56ff5d963fd 100644 (file)
@@ -11,9 +11,6 @@
 // Check that trans doesn't ICE when translating an array repeat
 // expression with a count of 1 and a non-Copy element type.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn main() {
-    let _ = [box 1_usize; 1];
+    let _ = [Box::new(1_usize); 1];
 }
index ce56f3e8d72875b996ec4c0ad66dc258997af30b..b92cfa1f29b52a026034c2b1391637a252b8ea6b 100644 (file)
@@ -19,5 +19,5 @@ fn uint_to_foo(_: uint) -> Foo {
 
 #[allow(unused_must_use)]
 fn main() {
-    (0_usize..10).map(uint_to_foo);
+    (0..10).map(uint_to_foo);
 }
index 572a0d825282e7c5425690b47ef056f02954ae8b..7e89cfe24e16aeaef2ed23204a2852845b9664ad 100644 (file)
@@ -41,10 +41,10 @@ fn dummy(&self) { }
 }
 
 pub fn main() {
-    fn box_1() -> Box<[i8; 1]> { Box::new( [1i8; 1] ) }
-    fn box_2() -> Box<[i8; 2]> { Box::new( [1i8; 2] ) }
-    fn box_3() -> Box<[i8; 3]> { Box::new( [1i8; 3] ) }
-    fn box_4() -> Box<[i8; 4]> { Box::new( [1i8; 4] ) }
+    fn box_1() -> Box<[i8; 1]> { Box::new( [1; 1] ) }
+    fn box_2() -> Box<[i8; 2]> { Box::new( [1; 2] ) }
+    fn box_3() -> Box<[i8; 3]> { Box::new( [1; 3] ) }
+    fn box_4() -> Box<[i8; 4]> { Box::new( [1; 4] ) }
 
     foo(box_1, box_2, box_3, box_4);
 }
index f751be6f13bc10ac9ee5ce2fbf1b78c0670c4376..5af5186e94f3748137dd8ebf8fe4bd90ba7afb74 100644 (file)
 }
 
 pub fn main() {
-    fn box_1() -> Box<[i8; 1]> { Box::new( [1i8] ) }
-    fn box_2() -> Box<[i8; 20]> { Box::new( [1i8; 20] ) }
-    fn box_3() -> Box<[i8; 300]> { Box::new( [1i8; 300] ) }
-    fn box_4() -> Box<[i8; 4000]> { Box::new( [1i8; 4000] ) }
+    fn box_1() -> Box<[i8; 1]> { Box::new( [1] ) }
+    fn box_2() -> Box<[i8; 20]> { Box::new( [1; 20] ) }
+    fn box_3() -> Box<[i8; 300]> { Box::new( [1; 300] ) }
+    fn box_4() -> Box<[i8; 4000]> { Box::new( [1; 4000] ) }
 
     foo(box_1, box_2, box_3, box_4);
 }
index f83150b95184b15167322500172257ba08346325..9ebd96a685eafefbccb7c421098bee23a51cc7ba 100644 (file)
 
 // Test that overloaded calls work with zero arity closures
 
-#![feature(box_syntax)]
-
 fn main() {
-    let functions: [Box<Fn() -> Option<()>>; 1] = [box || None];
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let functions: [Box<Fn() -> Option<()>>; 1] = [Box::new(|| None)];
 
     let _: Option<Vec<()>> = functions.iter().map(|f| (*f)()).collect();
 }
index 01a2322ae939919c397dbe71d8902180cccbdabf..640774f9d24ce70de9111b2b0c1a483ce15ca4ac 100644 (file)
@@ -15,6 +15,6 @@
 use std::fmt;
 
 fn main() {
-    let a: &fmt::Debug = &1_i32;
+    let a: &fmt::Debug = &1;
     format!("{:?}", a);
 }
index 145145af5194dba01d208490816aa63814f71730..29701bd668aafc977b772460662a741bbfb65778 100644 (file)
 use m::{START, END};
 
 fn main() {
-    match 42u32 {
+    match 42 {
         m::START...m::END => {},
-        0u32...m::END => {},
-        m::START...59u32 => {},
+        0...m::END => {},
+        m::START...59 => {},
         _  => {},
     }
 }
index 20ff8d29b7076bc4dc7d7028ad33ac8bc75dabd2..3da0a67ea8ef0a7ec5e589a297c5842a235cdf5e 100644 (file)
@@ -72,17 +72,17 @@ fn range(lo: uint, hi: uint, it: |uint|) {
     let mut i = lo;
     while i < hi {
         it(i);
-        i += 1_usize;
+        i += 1;
     }
 }
 
 pub fn main() {
-    let range: 'static ||uint|| = |a| range(0_usize, 1000_usize, a);
+    let range: 'static ||uint|| = |a| range(0, 1000, a);
     let filt: 'static ||v: uint|| = |a| filter(
         range,
-        |&&n: uint| n % 3_usize != 0_usize && n % 5_usize != 0_usize,
+        |&&n: uint| n % 3 != 0 && n % 5 != 0,
         a);
-    let sum = foldl(filt, 0_usize, |accum, &&n: uint| accum + n );
+    let sum = foldl(filt, 0, |accum, &&n: uint| accum + n );
 
     println!("{}", sum);
 }
index c06a29c09f78eeda9eb6e5354c243976f48a03f3..7bc6393ef8915b679dc0793af22d460463cfb40b 100644 (file)
@@ -28,6 +28,6 @@ fn digit_iter(self) -> I {
 }
 
 fn main() {
-    let xs = vec![1u8, 2, 3, 4, 5];
+    let xs = vec![1, 2, 3, 4, 5];
     assert_eq!(xs.into_iter().digit_sum(), 15);
 }
index 395b2c4b459eba638256e89466b0290f8e2661b2..c55de959a9464aee56073d392bf016de074f4a5d 100644 (file)
@@ -22,5 +22,5 @@ fn f<T>(_x: T) {
 }
 
 pub fn main() {
-    f(C(1_usize));
+    f(C(1));
 }
index 80e9ca470251775107a4ab4c03961df14ae64c86..0bef42b6202edfaec0291b7706f2b8a63ed10452 100644 (file)
@@ -17,6 +17,6 @@ fn a_val(x: Box<int>, y: Box<int>) -> int {
 }
 
 pub fn main() {
-    let z = box 22;
+    let z: Box<_> = box 22;
     a_val(z.clone(), z.clone());
 }
index 1f072af0f5a64c44c7739f47e7c414bc40490b4c..6aeec228c0d3e2f9a1bf4f3564b21daece451fa0 100644 (file)
@@ -31,5 +31,5 @@ fn Font() -> Font {
 }
 
 pub fn main() {
-    let _f = box Font();
+    let _f: Box<_> = box Font();
 }
index b8a541a0fc4de70876fe5240ec7efebbbc8e6192..ae146d8d35356960d45f15ec5ec1642f2e870bb4 100644 (file)
@@ -11,8 +11,6 @@
 //
 // ignore-lexer-test FIXME #15883
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unsafe_destructor)]
 
 pub type Task = int;
@@ -52,11 +50,11 @@ unsafe impl<T:Send> Send for packet<T> {}
 
     pub fn packet<T:Send>() -> *const packet<T> {
         unsafe {
-            let p: *const packet<T> = mem::transmute(box Stuff{
+            let p: *const packet<T> = mem::transmute(Box::new(Stuff{
                 state: empty,
                 blocked_task: None::<Task>,
                 payload: None::<T>
-            });
+            }));
             p
         }
     }
index 31599d0caadeeee981557c3a874df23db7a1db0f..e653dda8de5f00591470368694d1b2ad82b4aac8 100644 (file)
@@ -28,7 +28,7 @@ pub fn main() {
   //   let y = box ({a: 4});
   //    let z = box ({a: 4} as it);
   //    let z = box ({a: true} as it);
-    let z = box() (box true as Box<it>);
+    let z: Box<_> = box () (box true as Box<it>);
     //  x.f();
     // y.f();
     // (*z).f();
index 8767d397b647a19149e766c8d54fca765bf5bac2..8b6eb12f102ee24c5b7c7cc220e55ffcf926cdef 100644 (file)
@@ -21,11 +21,11 @@ fn to_bytes(&self) -> Vec<u8> {
 // the position of this function is significant! - if it comes before methods
 // then it works, if it comes after it then it doesn't!
 fn to_bools(bitv: Storage) -> Vec<bool> {
-    (0_usize..8).map(|i| {
+    (0..8).map(|i| {
         let w = i / 64;
         let b = i % 64;
-        let x = 1u64 & (bitv.storage[w] >> b);
-        x == 1u64
+        let x = 1 & (bitv.storage[w] >> b);
+        x == 1
     }).collect()
 }
 
@@ -35,7 +35,7 @@ pub fn main() {
     let bools = vec!(false, false, true, false, false, true, true, false);
     let bools2 = to_bools(Storage{storage: vec!(0b01100100)});
 
-    for i in 0_usize..8 {
+    for i in 0..8 {
         println!("{} => {} vs {}", i, bools[i], bools2[i]);
     }
 
index de2d4374d787fdf15915dbcf5b082fdb862fd69e..6f107a37e9b25b9bec97cb09f671e76b61017910 100644 (file)
@@ -20,5 +20,5 @@
 
 pub fn main() {
     let fd: libc::c_int = 1 as libc::c_int;
-    let _sock = box socket::socket_handle(fd);
+    let _sock: Box<_> = box socket::socket_handle(fd);
 }
index 25663f2605fcb4233cc47bc27743d738068f188b..98c9f3d5ec5ade97e045bbbe8973429857c07078 100644 (file)
@@ -17,7 +17,7 @@
 use std::collections::HashMap;
 
 pub fn main() {
-    let x;
+    let x: Box<_>;
     let mut buggy_map: HashMap<uint, &uint> = HashMap::new();
     x = box 1;
     buggy_map.insert(42, &*x);
index 3e7deee6ec10720b4690df4336df72e1beae4bca..0784c8be883c84dd39abde8723b1fd19404c1282 100644 (file)
@@ -8,13 +8,11 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 type Connection = Box<FnMut(Vec<u8>) + 'static>;
 
 fn f() -> Option<Connection> {
-    let mock_connection: Connection = box |_| {};
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let mock_connection: Connection = Box::new(|_| {});
     Some(mock_connection)
 }
 
index c8d6e69801fa13094a05b57347bcf9ab35c8bd9a..1c1b329e314c1d7ad96109c6467d138005685926 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-   let mut x = box 3;
+   let mut x: Box<_> = box 3;
    x = x;
    assert_eq!(*x, 3);
 }
index 0d85f61e51350d7dbc3715882505ab855f3f3d6e..e039be058defec1a6f6d1502da16eeda8172bcc5 100644 (file)
@@ -11,7 +11,6 @@
 // rustc --test ignores2.rs && ./ignores2
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 use std::old_path::{Path};
 
 fn tester()
 {
-    let mut loader: rsrc_loader = box move|_path| {
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let mut loader: rsrc_loader = Box::new(move|_path| {
         result::Result::Ok("more blah".to_string())
-    };
+    });
 
     let path = old_path::Path::new("blah");
     assert!(loader(&path).is_ok());
index 4a28c34e5d9f4299683811b7159e100fe59a5823..b51edcf8bec4d60adad737e151b5e1d6efcc1c73 100644 (file)
@@ -9,7 +9,6 @@
 // except according to those terms.
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 
 use std::thread::Thread;
 use std::sync::mpsc::Sender;
@@ -27,9 +26,9 @@ fn foo(name: String, samples_chan: Sender<Msg>) {
     let _t = Thread::spawn(move|| {
         let mut samples_chan = samples_chan;
 
-        // `box() (...)` syntax is needed to make pretty printer converge in one try:
-        let callback: SamplesFn = box() (move |buffer| {
-            for i in 0_usize..buffer.len() {
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        let callback: SamplesFn = Box::new(move |buffer| {
+            for i in 0..buffer.len() {
                 println!("{}: {}", i, buffer[i])
             }
         });
index c1d19f228db617511960278bbb2f5dbfb016fe32..1f53d9ce5422fc4831c540c3725beb2c424debf6 100644 (file)
@@ -13,6 +13,6 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let y = box 1;
+    let y: Box<_> = box 1;
     y;
 }
index bf422bd0405a1c9343f82af2cd38fb63abcbc3e1..196e9748b107317df9cc0e140d0ccedf3979c042 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-fast doesn't like extern crate
 
 #![allow(unknown_features)]
 #![feature(box_syntax)]
index ce2f488b90c7b6adf7bde9917ce62b05cdc1b26a..a565460c42e28333fad057b931ed6d27ecc14fc0 100644 (file)
@@ -7,9 +7,7 @@
 // <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-lexer-test FIXME #15877
 
 trait U { fn f(self); }
-impl U for int { fn f(self) {} }
+impl U for isize { fn f(self) {} }
 pub fn main() { 4.f(); }
index 36aa8a9cbca5d2c66e4f225328e6943117d380da..7e773cd799476c12f9b46b0a53c991ba0d8c57f4 100644 (file)
@@ -16,7 +16,7 @@
 macro_rules! foo {
     ($tag: expr, $string: expr) => {
         if $tag == $string {
-            let element = box Element;
+            let element: Box<_> = box Element;
             unsafe {
                 return std::mem::transmute::<_, uint>(element);
             }
index 93edffdcb477fc9c62a7801c3bf302a4f062875e..562e2b68af174391bd71ddbf093f919bb22445db 100644 (file)
@@ -8,13 +8,10 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 enum Either<T, U> { Left(T), Right(U) }
 
 pub fn main() {
-    match Either::Left(box 17) {
+    match Either::Left(Box::new(17)) {
         Either::Right(()) => {}
         _ => {}
     }
index 93429ff10dcd1f9fe356e7f4ece7856e42e35f3f..1a1f538a548b722ab86c40f1d2b596b5cc888b40 100644 (file)
@@ -12,9 +12,9 @@
 
 pub fn main() {
     let i: uint = 0;
-    assert!(i <= 0xFFFF_FFFF_usize);
+    assert!(i <= 0xFFFF_FFFF);
 
     let i: int = 0;
-    assert!(i >= -0x8000_0000__isize);
-    assert!(i <= 0x7FFF_FFFF__isize);
+    assert!(i >= -0x8000_0000);
+    assert!(i <= 0x7FFF_FFFF);
 }
index 557ec82233ddebca8a17538b5132abe162ffd6ef..6faca339651c07b77d091200363385f9a40e6be8 100644 (file)
@@ -49,7 +49,7 @@ fn main() {
     assert_eq!(unsafe { NUM_DROPS }, 3);
     { let _x = FooBar::_Foo(Foo); }
     assert_eq!(unsafe { NUM_DROPS }, 5);
-    { let _x = FooBar::_Bar(42_usize); }
+    { let _x = FooBar::_Bar(42); }
     assert_eq!(unsafe { NUM_DROPS }, 6);
 
     { let _ = Foo; }
@@ -60,6 +60,6 @@ fn main() {
     assert_eq!(unsafe { NUM_DROPS }, 9);
     { let _ = FooBar::_Foo(Foo); }
     assert_eq!(unsafe { NUM_DROPS }, 11);
-    { let _ = FooBar::_Bar(42_usize); }
+    { let _ = FooBar::_Bar(42); }
     assert_eq!(unsafe { NUM_DROPS }, 12);
 }
index 96db28f4a101fbaab6d30fe890a47e48d310e992..3a9864f3a766718cd277481995ceff45e5c76b9e 100644 (file)
 struct signature<'a> { pattern : &'a [u32] }
 
 static test1: signature<'static> =  signature {
-  pattern: &[0x243f6a88u32,0x85a308d3u32,0x13198a2eu32,0x03707344u32,0xa4093822u32,0x299f31d0u32]
+  pattern: &[0x243f6a88,0x85a308d3,0x13198a2e,0x03707344,0xa4093822,0x299f31d0]
 };
 
 pub fn main() {
-  let test: &[u32] = &[0x243f6a88u32,0x85a308d3u32,0x13198a2eu32,
-                       0x03707344u32,0xa4093822u32,0x299f31d0u32];
+  let test: &[u32] = &[0x243f6a88,0x85a308d3,0x13198a2e,
+                       0x03707344,0xa4093822,0x299f31d0];
   println!("{}",test==test1.pattern);
 }
index 494b62178550349f2f545b5fee1c3c3d74690f90..d4d2603bfe2449b2626257b4e9504bcbdbe550b2 100644 (file)
@@ -8,18 +8,15 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 pub fn main() {
-    match &[(box 5,box 7)] {
+    match &[(Box::new(5),Box::new(7))] {
         ps => {
            let (ref y, _) = ps[0];
            assert!(**y == 5);
         }
     }
 
-    match Some(&[(box 5,)]) {
+    match Some(&[(Box::new(5),)]) {
         Some(ps) => {
            let (ref y,) = ps[0];
            assert!(**y == 5);
@@ -27,7 +24,7 @@ pub fn main() {
         None => ()
     }
 
-    match Some(&[(box 5,box 7)]) {
+    match Some(&[(Box::new(5),Box::new(7))]) {
         Some(ps) => {
            let (ref y, ref z) = ps[0];
            assert!(**y == 5);
index 815e00e129143f0ee2d8c60e2cb14e4013ac450c..303dd191006ad88465c39633f32a67049e70241b 100644 (file)
@@ -13,7 +13,7 @@
 struct X { pub x: uint }
 impl Default for X {
     fn default() -> X {
-        X { x: 42_usize }
+        X { x: 42 }
     }
 }
 
index b4a41ef44f82d502298c382a7cadbf478efd2192..58424089c5e02a83457c5f3b7ee309730b8ab649 100644 (file)
@@ -12,5 +12,5 @@
 extern crate issue2170lib;
 
 pub fn main() {
-   // let _ = issue2170lib::rsrc(2i32);
+   // let _ = issue2170lib::rsrc(2);
 }
diff --git a/src/test/run-pass/iter-cloned-type-inference.rs b/src/test/run-pass/iter-cloned-type-inference.rs
new file mode 100644 (file)
index 0000000..6ce226b
--- /dev/null
@@ -0,0 +1,25 @@
+// Copyright 2015 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.
+
+// Test to see that the element type of .cloned() can be inferred
+// properly. Previously this would fail to deduce the type of `sum`.
+
+#![feature(core)]
+
+use std::iter::AdditiveIterator;
+
+fn square_sum(v: &[i64]) -> i64 {
+    let sum = v.iter().cloned().sum();
+    sum * sum
+}
+
+fn main() {
+    assert_eq!(36, square_sum(&[1,2,3]));
+}
index dd38a5f8b3ba7b23906bc3b11dede3688d8cfb41..121338823d29133497b1bfa86bf048e1c13df82a 100644 (file)
@@ -13,8 +13,8 @@
 
 fn producer(tx: &Sender<Vec<u8>>) {
     tx.send(
-         vec!(1u8, 2u8, 3u8, 4u8, 5u8, 6u8, 7u8, 8u8, 9u8, 10u8, 11u8, 12u8,
-          13u8)).unwrap();
+         vec!(1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12,
+          13)).unwrap();
 }
 
 pub fn main() {
index 566d34e6d86df763a4c9f13ee51bed0ea8555dae..45964efad97c86e27ce97a0cbad38b9797aea193 100644 (file)
 struct A { a: Box<isize> }
 
 fn foo() -> Box<FnMut() -> isize + 'static> {
-    let k = box 22;
+    let k: Box<_> = box 22;
     let _u = A {a: k.clone()};
-    // FIXME(#16640) suffix in `22_isize` suffix shouldn't be necessary
-    let result  = || 22_isize;
-    box result
+    // FIXME(#16640) suffix in `22` suffix shouldn't be necessary
+    let result  = || 22;
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    Box::new(result)
 }
 
 pub fn main() {
index 19a780d180f2804d404971bf0f3de5827ccbc364..7b11aae168ca965744ccbb01a9423e799947db1f 100644 (file)
@@ -17,7 +17,7 @@ struct A { a: Box<int> }
 
 pub fn main() {
     fn invoke<F>(f: F) where F: FnOnce() { f(); }
-    let k = box 22;
+    let k: Box<_> = box 22;
     let _u = A {a: k.clone()};
     invoke(|| println!("{}", k.clone()) )
 }
index 9ac016d534f09c40c40ca235a1abdf74890b3fe0..1500edce779c371d5baa8ee5d069b95a2695c4f8 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 fn f() {
-    let a = box 1;
+    let a: Box<_> = box 1;
     let b: &int = &*a;
     println!("{}", b);
 }
diff --git a/src/test/run-pass/lint-cstack.rs b/src/test/run-pass/lint-cstack.rs
deleted file mode 100644 (file)
index f180ffc..0000000
+++ /dev/null
@@ -1,26 +0,0 @@
-// Copyright 2013 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 crate libc;
-
-extern {
-    fn rust_get_test_int() -> libc::intptr_t;
-}
-
-trait A {
-    fn foo(&self) {
-        unsafe {
-            rust_get_test_int();
-        }
-    }
-}
-
-pub fn main() {
-}
index 262d9b21eb48bddd57815f6d246e26151037ef4a..dfc9272827066c517138209ab1851338af90e681 100644 (file)
@@ -8,7 +8,7 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// compile-flags:--cfg ndebug
+// compile-flags:-C debug-assertions=no
 // exec-env:RUST_LOG=logging-enabled-debug=debug
 
 #[macro_use]
index 8526dfe72da134a5c96e16fd7c1459d4db099c56..82a155b117301980bb74b123fa524a4cc74c37e7 100644 (file)
@@ -10,6 +10,7 @@
 
 // ignore-windows
 // exec-env:RUST_LOG=debug
+// compile-flags:-C debug-assertions=y
 
 #[macro_use]
 extern crate log;
index 069aeb9220e604a70ecd87ebdf9988ca8072bbfe..1cbd4f6bc704c3895eff103446568a83f79ebbe5 100644 (file)
@@ -24,6 +24,6 @@ fn $fnname($arg: $ty) -> Option<$ty> $body
 
 pub fn main() {
     assert!(overly_complicated!(f, x, Option<uint>, { return Some(x); },
-                               Some(8_usize), Some(y), y) == 8_usize)
+                               Some(8), Some(y), y) == 8)
 
 }
index 6f2626a5af51ef7b45d8571893ff5d99bf42e014..7a3e55322c8e1cb5cb1c87d6bd96e147df3c4a4b 100644 (file)
@@ -47,9 +47,9 @@ fn f(c: Option<char>) -> uint {
 }
 
 pub fn main() {
-    assert_eq!(1_usize, f(Some('x')));
-    assert_eq!(2_usize, f(Some('y')));
-    assert_eq!(3_usize, f(None));
+    assert_eq!(1, f(Some('x')));
+    assert_eq!(2, f(Some('y')));
+    assert_eq!(3, f(None));
 
     assert_eq!(1, match Some('x') {
         Some(char_x!()) => 1,
index 6883187c402f3a3af8aa398e141cfd8fe03e1711..cd4802f4b397a6407f5e4525f459b842d415b99b 100644 (file)
@@ -14,7 +14,7 @@
 struct Pair { a: Box<int>, b: Box<int> }
 
 pub fn main() {
-    let mut x = box Pair {a: box 10, b: box 20};
+    let mut x: Box<_> = box Pair {a: box 10, b: box 20};
     let x_internal = &mut *x;
     match *x_internal {
       Pair {a: ref mut a, b: ref mut _b} => {
index d2e27fc822eebe8323a641772db87038842e2e8c..79b197f08e2718616db5e1bff9e6ce00a557baf9 100644 (file)
@@ -16,6 +16,6 @@ pub fn main() {
         None => return (),
         Some(num) => num as u32
     };
-    assert_eq!(f, 1234u32);
+    assert_eq!(f, 1234);
     println!("{}", f)
 }
index 0ad600dd85d9338a1ed33c230053c369fa0098c7..3ffac98418a7472a7d2a119cd1a356c9f90e3412 100644 (file)
@@ -38,7 +38,7 @@ fn my_write(&mut self, buf: &[u8]) -> IoResult<()> {
 }
 
 fn main() {
-    let mut buf = [0_u8; 6];
+    let mut buf = [0; 6];
 
     {
         let mut writer: &mut [_] = &mut buf;
index e9a1e19d4bf8416494606a25cdb4285f61cd1910..81212ee348f1f68936266cbcceb9127332e42725 100644 (file)
@@ -26,5 +26,5 @@ fn main() {
 
     x.foo(&x);
 
-    assert!(method_self_arg1::get_count() == 2u64*3*3*3*5*5*5*7*7*7);
+    assert!(method_self_arg1::get_count() == 2*3*3*3*5*5*5*7*7*7);
 }
index 7fa810ce1549ad9f671caf94a6907225a87c887b..ca81860dd080c9ed3f8fffe146ee534951ec0b80 100644 (file)
@@ -30,5 +30,5 @@ fn main() {
 
     x.run_trait();
 
-    assert!(method_self_arg2::get_count() == 2u64*2*3*3*5*5*7*7*11*11*13*13*17);
+    assert!(method_self_arg2::get_count() == 2*2*3*3*5*5*7*7*11*11*13*13*17);
 }
index c79141d97950045a9b1f2e68e9bbe7ad44f6f67d..17fdd7b45c20c033a2d328420464a7f27ca6058b 100644 (file)
@@ -75,5 +75,5 @@ fn main() {
 
     x.baz();
 
-    unsafe { assert!(COUNT == 2u64*2*3*3*5*5*7*7*11*11*13*13*17); }
+    unsafe { assert!(COUNT == 2*2*3*3*5*5*7*7*11*11*13*13*17); }
 }
index de24297c7b51af6f3fcd5d4147d04cd868d73697..62b3d52860ba8d2625f3928828324069834bb22f 100644 (file)
@@ -54,5 +54,5 @@ fn main() {
 
     x.foo(&x);
 
-    unsafe { assert!(COUNT == 2_usize*3*3*3*5*5*5*7*7*7); }
+    unsafe { assert!(COUNT == 2*3*3*3*5*5*5*7*7*7); }
 }
index 7463783be59892fe95a343a2eb4a220c5f773e45..a49ce82617007e2921b3fb5f207af537c0b1eccb 100644 (file)
@@ -39,7 +39,7 @@ fn call_foo_copy() -> int {
 }
 
 fn call_foo_other() -> int {
-    let mut x = Vec::new();
+    let mut x: Vec<Box<_>> = Vec::new();
     let y = x.foo();
     x.push(box 0);
     y
index 018cd440cad343523c65327f3661fb0273f58bdb..ff06df079b05e029717153c437d1d7a6ff28432f 100644 (file)
@@ -26,7 +26,7 @@ fn test(x: bool, foo: Box<Triple>) -> int {
 }
 
 pub fn main() {
-    let x = box Triple{x: 1, y: 2, z: 3};
+    let x: Box<_> = box Triple{x: 1, y: 2, z: 3};
     assert_eq!(test(true, x.clone()), 2);
     assert_eq!(test(true, x.clone()), 2);
     assert_eq!(test(true, x.clone()), 2);
index 50187ef8baad23fb8768c8e242b79c0a4e0ed139..590caff3c2dc850c168fb376c7c72b8137efba7a 100644 (file)
@@ -14,7 +14,7 @@
 struct X { x: int, y: int, z: int }
 
 pub fn main() {
-    let x = box X{x: 1, y: 2, z: 3};
+    let x: Box<_> = box X{x: 1, y: 2, z: 3};
     let y = x;
     assert!((y.y == 2));
 }
index 6561a9b2d5b565c24a3f6c525400170ee4d7b4af..0bff2c2292e74be2caf7c884473571bc40f038f0 100644 (file)
@@ -13,4 +13,4 @@
 
 struct X { x: int, y: int, z: int }
 
-pub fn main() { let x = box X {x: 1, y: 2, z: 3}; let y = x; assert!((y.y == 2)); }
+pub fn main() { let x: Box<_> = box X {x: 1, y: 2, z: 3}; let y = x; assert!((y.y == 2)); }
index 07d0594b494d966d1f5df70c0e05ffcf9423ac2d..8241424124e0e0e3373913c695927e0cd14a61f4 100644 (file)
@@ -26,7 +26,7 @@ fn test(x: bool, foo: Box<Triple>) -> int {
 }
 
 pub fn main() {
-    let x = box Triple{x: 1, y: 2, z: 3};
+    let x: Box<_> = box Triple{x: 1, y: 2, z: 3};
     for _ in 0_usize..10000_usize {
         assert_eq!(test(true, x.clone()), 2);
     }
index 64c4f1fdbaeabf6e2d9e06bdb80646e4063c4ede..d68a7c831f212ca4ae683e5e4469e4cc9c818d83 100644 (file)
@@ -11,7 +11,7 @@
 #![feature(box_syntax)]
 
 fn main() {
-    let x = box 1;
+    let x: Box<_> = box 1;
 
     let v = (1, 2);
 
index 130cdc85b013d6af888468b6e809197e4c5d264b..039e53cab8044805db0dd51f51c63c482867bcd0 100644 (file)
 // Test that the lambda kind is inferred correctly as a return
 // expression
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
-fn unique() -> Box<FnMut()+'static> { return box || (); }
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+fn unique() -> Box<FnMut()+'static> { return Box::new(|| ()); }
 
 pub fn main() {
 }
index 0952bedd6e309a2fbfdcc798db2e30f2657064c7..b7216c87c30bbc22a7f174ca07c3f25ea4447d61 100644 (file)
 // Test that the lambda kind is inferred correctly as a return
 // expression
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
-fn unique() -> Box<FnMut()+'static> { box || () }
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+fn unique() -> Box<FnMut()+'static> { Box::new(|| ()) }
 
 pub fn main() {
 }
index 8631755f37fd9a7895ab5678957c2cda5f509eec..15c4e8b04533939a2804f572562ff240ab08e008 100644 (file)
@@ -8,7 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-fast doesn't like extern crate
 
 extern crate libc;
 use libc::c_int;
index 22786c0abc89b9bd6487882d021967e18abb377f..4a14969209f027dbeb5d8128d7b549851ee57c9e 100644 (file)
 
 pub fn main()
 {
-    let all_nuls1 = "\0\x00\u0000\U00000000";
-    let all_nuls2 = "\U00000000\u0000\x00\0";
-    let all_nuls3 = "\u0000\U00000000\x00\0";
-    let all_nuls4 = "\x00\u0000\0\U00000000";
+    let all_nuls1 = "\0\x00\u{0}\u{0}";
+    let all_nuls2 = "\u{0}\u{0}\x00\0";
+    let all_nuls3 = "\u{0}\u{0}\x00\0";
+    let all_nuls4 = "\x00\u{0}\0\u{0}";
 
     // sizes for two should suffice
     assert_eq!(all_nuls1.len(), 4);
@@ -35,8 +35,8 @@ pub fn main()
 
     // testing equality between explicit character literals
     assert_eq!('\0', '\x00');
-    assert_eq!('\u0000', '\x00');
-    assert_eq!('\u0000', '\U00000000');
+    assert_eq!('\u{0}', '\x00');
+    assert_eq!('\u{0}', '\u{0}');
 
     // NUL characters should make a difference
     assert!("Hello World" != "Hello \0World");
index bb62b1599a4fe5aa5f99563b90877e8036b4a863..03027e40d6c1e50c345e4615cc08fa07f1625440 100644 (file)
@@ -55,7 +55,7 @@ macro_rules! check_fancy {
         check_fancy!($e, $T, |ptr| assert!(*ptr == $e));
     }};
     ($e:expr, $T:ty, |$v:ident| $chk:expr) => {{
-        assert!(E::Nothing::<$T>((), ((), ()), [23i8; 0]).is_none());
+        assert!(E::Nothing::<$T>((), ((), ()), [23; 0]).is_none());
         let e = $e;
         let t_ = E::Thing::<$T>(23, e);
         match t_.get_ref() {
index 8da753acb966ef292e0d982d86273cb5eaf93701..9c7a925b5bbc2a932190c9567bc695fbb6ab19e0 100644 (file)
@@ -29,7 +29,7 @@ fn get(&self) -> i32 {
 }
 
 fn main() {
-    let x = 22_i32;
+    let x = 22;
     let x1: &SomeTrait<SomeType=i32> = &x;
     let y = get_int(x1);
     assert_eq!(x, y);
index 998af27c338dc88210fb1f56e02b20a73a178419..d2523bc4f246f34ec0fb1c4e4383aeed577fe930 100644 (file)
@@ -40,9 +40,9 @@ fn do_it_imm(obj: &Foo, v: uint) {
 }
 
 pub fn main() {
-    let mut x = 22_usize;
+    let mut x = 22;
     let obj = &mut x as &mut Foo;
     do_it_mut(obj);
-    do_it_imm(obj, 23_usize);
+    do_it_imm(obj, 23);
     do_it_mut(obj);
 }
index 30a8c270bd7944c36fa43f0833b3621663906de4..9cee266c4a7b9f1aa8eabb2052e82268697dca5b 100644 (file)
@@ -37,7 +37,7 @@ pub fn main() {
         box BarStruct{ x: 2 } as Box<FooTrait>
     );
 
-    for i in 0_usize..foos.len() {
+    for i in 0..foos.len() {
         assert_eq!(i, foos[i].foo());
     }
 }
index 654d2429a0ba06fb83428c44aa97eb8fa8751c41..ef399044abc99347c11d258a0f59ea5ec740b7da 100644 (file)
@@ -16,6 +16,6 @@ fn or_alt(q: blah) -> int {
 
 pub fn main() {
     assert_eq!(or_alt(blah::c), 0);
-    assert_eq!(or_alt(blah::a(10, 100, 0_usize)), 110);
+    assert_eq!(or_alt(blah::a(10, 100, 0)), 110);
     assert_eq!(or_alt(blah::b(20, 200)), 220);
 }
index f40c9dc45cab1c592adc549c22d50c1e557934e3..6436165968d678801130a581164d5a9e85b9f6fa 100644 (file)
@@ -22,9 +22,10 @@ struct Point {
 }
 
 pub fn main() {
-    let box_5 = box 5_usize;
+    let box_5: Box<_> = box 5_usize;
     assert_eq!(Rc::new(5_usize).to_uint(), Some(5));
-    assert_eq!((box &box &Rc::new(box box &box_5)).to_uint(), Some(5));
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    assert_eq!((Box::new(&Box::new(&Rc::new(Box::new(Box::new(&box_5)))))).to_uint(), Some(5));
     let point = Rc::new(Point {x: 2, y: 4});
     assert_eq!(point.x, 2);
     assert_eq!(point.y, 4);
index 2ef9e08134cf7259fcf5dde6a4f99a59ac889bdb..0ac9c97532bffd29b33b8cc483724b0f1dad9e48 100644 (file)
@@ -28,5 +28,5 @@ extern "rust-call" fn call(&self, (arg,): (A,)) -> i32 {
 
 fn main() {
     // ICE trigger
-    (G(PhantomData))(1_i32);
+    (G(PhantomData))(1);
 }
index f56e7d56fe16aec00df2034f97375ea37f461eb2..bb1694be5e29b7765b8d2ae00449fbb84fa948a0 100644 (file)
@@ -8,9 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 use std::cell::RefCell;
 use std::rc::Rc;
 use std::string::String;
@@ -23,7 +20,7 @@ struct Point {
 
 pub fn main() {
     assert_eq!(*Rc::new(5), 5);
-    assert_eq!(***Rc::new(box box 5), 5);
+    assert_eq!(***Rc::new(Box::new(Box::new(5))), 5);
     assert_eq!(*Rc::new(Point {x: 2, y: 4}), Point {x: 2, y: 4});
 
     let i = Rc::new(RefCell::new(2));
index d5ccf8cd2befb0f4f18e29fc0021ba49f4d814bf..8f655f0517ddf47fe56224d420ba0e0a34992a59 100644 (file)
@@ -55,7 +55,7 @@ fn get_from_ref(&self) -> int { *self }
 }
 
 fn main() {
-    let mut f = box Foo {
+    let mut f: Box<_> = box Foo {
         x: 1,
         y: 2,
     };
index 2db6f7ffaaa61ccab311c3ecb93a978c91ddc04a..9be6b212a3caabd0b7259800b96999d68cf5ceee 100644 (file)
@@ -8,11 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn f<T: 'static>(_x: T) {}
 
 pub fn main() {
-    f(box 5);
+    f(Box::new(5));
 }
index cfe49c38c5267835a1e1b4c57c06895634d5b857..92f57f04b10ae5279fb9c3acce7a253ce86eb209 100644 (file)
@@ -24,7 +24,7 @@ pub fn main() {
 
     assert_eq!(mem::size_of::<[Foo; 10]>(), 90);
 
-    for i in 0_usize..10 {
+    for i in 0..10 {
         assert_eq!(foos[i], Foo { bar: 1, baz: 2});
     }
 
index 02d8602d59e311618fd820922d239d3aa851e4eb..08d00d4dc035b37a648e6fd6de66487cb2681f1c 100644 (file)
@@ -14,4 +14,4 @@ mod foo {
     pub fn bar(_offset: uint) { }
 }
 
-pub fn main() { foo::bar(0_usize); }
+pub fn main() { foo::bar(0); }
index c7380b362fbbad794447b2b2e7de26072d37f8b8..b4d04ba18f98ef032c4c4d62c341b56cc7380303 100644 (file)
@@ -26,6 +26,6 @@ fn cat(in_x : uint, in_y : int) -> cat {
 }
 
 pub fn main() {
-    let mut nyan : cat = cat(52_usize, 99);
-    assert_eq!(nyan.meow_count(), 52_usize);
+    let mut nyan : cat = cat(52, 99);
+    assert_eq!(nyan.meow_count(), 52);
 }
index f7adb0f6e444b91a18adedd6e70817a352dfe351..f12cf82f939c7d2356a0cea330deb6171d5cdfdf 100644 (file)
 #![feature(box_syntax)]
 
 fn sums_to(v: Vec<int> , sum: int) -> bool {
-    let mut i = 0_usize;
+    let mut i = 0;
     let mut sum0 = 0;
     while i < v.len() {
         sum0 += v[i];
-        i += 1_usize;
+        i += 1;
     }
     return sum0 == sum;
 }
 
 fn sums_to_using_uniq(v: Vec<int> , sum: int) -> bool {
-    let mut i = 0_usize;
-    let mut sum0 = box 0;
+    let mut i = 0;
+    let mut sum0: Box<_> = box 0;
     while i < v.len() {
         *sum0 += v[i];
-        i += 1_usize;
+        i += 1;
     }
     return *sum0 == sum;
 }
 
 fn sums_to_using_rec(v: Vec<int> , sum: int) -> bool {
-    let mut i = 0_usize;
+    let mut i = 0;
     let mut sum0 = F {f: 0};
     while i < v.len() {
         sum0.f += v[i];
-        i += 1_usize;
+        i += 1;
     }
     return sum0.f == sum;
 }
@@ -46,11 +46,11 @@ fn sums_to_using_rec(v: Vec<int> , sum: int) -> bool {
 struct F<T> { f: T }
 
 fn sums_to_using_uniq_rec(v: Vec<int> , sum: int) -> bool {
-    let mut i = 0_usize;
-    let mut sum0 = F {f: box 0};
+    let mut i = 0;
+    let mut sum0 = F::<Box<_>> {f: box 0};
     while i < v.len() {
         *sum0.f += v[i];
-        i += 1_usize;
+        i += 1;
     }
     return *sum0.f == sum;
 }
index db414abb7ffc87478820738a37b5fdaa43b6148c..41ed9a74d13107153826251939f62afe2c32a92f 100644 (file)
@@ -38,7 +38,7 @@ fn main() {
     let x = ..1+3;
     assert!(x == (..4));
 
-    let a = &[0i32, 1, 2, 3, 4, 5, 6];
+    let a = &[0, 1, 2, 3, 4, 5, 6];
     let x = &a[1+1..2+2];
     assert!(x == &a[2..4]);
     let x = &a[..1+2];
index 35e863d05a177dd06262b4d4302b5f40886ed0aa..298ac8f77eb11dd6f5a4a63ea68920e34a5e7d61 100644 (file)
Binary files a/src/test/run-pass/raw-str.rs and b/src/test/run-pass/raw-str.rs differ
index 84a230fd5767c201b25a00b417a735ebd4b39ff6..7bc761d2f606d06119d9b83a25196ade1b54c10b 100644 (file)
@@ -25,7 +25,7 @@ fn get(self) -> int {
 }
 
 pub fn main() {
-    let x = box 6;
+    let x: Box<_> = box 6;
     let y = x.get();
     println!("y={}", y);
     assert_eq!(y, 6);
index de5b14104c5300da7dd50c8b9f66def1104699d2..e8bcff38131a66ea43546f211c4c5f859f5319a4 100644 (file)
@@ -35,9 +35,9 @@ unsafe fn test_triangle() -> bool {
     // from pairs of rows (where each pair of rows is equally sized),
     // and the elements of the triangle match their row-pair index.
     unsafe fn sanity_check(ascend: &[*mut u8]) {
-        for i in 0_usize..COUNT / 2 {
+        for i in 0..COUNT / 2 {
             let (p0, p1, size) = (ascend[2*i], ascend[2*i+1], idx_to_size(i));
-            for j in 0_usize..size {
+            for j in 0..size {
                 assert_eq!(*p0.offset(j as int), i as u8);
                 assert_eq!(*p1.offset(j as int), i as u8);
             }
@@ -88,14 +88,14 @@ fn idx_to_size(i: uint) -> uint { (i+1) * 10 }
     // that at least two rows will be allocated near each other, so
     // that we trigger the bug (a buffer overrun) in an observable
     // way.)
-    for i in 0_usize..COUNT / 2 {
+    for i in 0..COUNT / 2 {
         let size = idx_to_size(i);
         ascend[2*i]   = allocate(size, ALIGN);
         ascend[2*i+1] = allocate(size, ALIGN);
     }
 
     // Initialize each pair of rows to distinct value.
-    for i in 0_usize..COUNT / 2 {
+    for i in 0..COUNT / 2 {
         let (p0, p1, size) = (ascend[2*i], ascend[2*i+1], idx_to_size(i));
         for j in 0..size {
             *p0.offset(j as int) = i as u8;
@@ -109,7 +109,7 @@ fn idx_to_size(i: uint) -> uint { (i+1) * 10 }
     test_3(ascend); // triangle -> square
     test_4(ascend); // square -> triangle
 
-    for i in 0_usize..COUNT / 2 {
+    for i in 0..COUNT / 2 {
         let size = idx_to_size(i);
         deallocate(ascend[2*i], size, ALIGN);
         deallocate(ascend[2*i+1], size, ALIGN);
@@ -123,7 +123,7 @@ fn idx_to_size(i: uint) -> uint { (i+1) * 10 }
     // rows as we go.
     unsafe fn test_1(ascend: &mut [*mut u8]) {
         let new_size = idx_to_size(COUNT-1);
-        for i in 0_usize..COUNT / 2 {
+        for i in 0..COUNT / 2 {
             let (p0, p1, old_size) = (ascend[2*i], ascend[2*i+1], idx_to_size(i));
             assert!(old_size < new_size);
 
@@ -138,7 +138,7 @@ unsafe fn test_1(ascend: &mut [*mut u8]) {
     // Test 2: turn the square back into a triangle, top to bottom.
     unsafe fn test_2(ascend: &mut [*mut u8]) {
         let old_size = idx_to_size(COUNT-1);
-        for i in 0_usize..COUNT / 2 {
+        for i in 0..COUNT / 2 {
             let (p0, p1, new_size) = (ascend[2*i], ascend[2*i+1], idx_to_size(i));
             assert!(new_size < old_size);
 
@@ -153,7 +153,7 @@ unsafe fn test_2(ascend: &mut [*mut u8]) {
     // Test 3: turn triangle into a square, bottom to top.
     unsafe fn test_3(ascend: &mut [*mut u8]) {
         let new_size = idx_to_size(COUNT-1);
-        for i in (0_usize..COUNT / 2).rev() {
+        for i in (0..COUNT / 2).rev() {
             let (p0, p1, old_size) = (ascend[2*i], ascend[2*i+1], idx_to_size(i));
             assert!(old_size < new_size);
 
@@ -168,7 +168,7 @@ unsafe fn test_3(ascend: &mut [*mut u8]) {
     // Test 4: turn the square back into a triangle, bottom to top.
     unsafe fn test_4(ascend: &mut [*mut u8]) {
         let old_size = idx_to_size(COUNT-1);
-        for i in (0_usize..COUNT / 2).rev() {
+        for i in (0..COUNT / 2).rev() {
             let (p0, p1, new_size) = (ascend[2*i], ascend[2*i+1], idx_to_size(i));
             assert!(new_size < old_size);
 
index 51b800bc9f01f2e101e541ad090d2a9478409d83..94fe3f1d9eaee5cf14c122c7e02ee9249c7befd0 100644 (file)
@@ -38,19 +38,19 @@ struct Outer {
 
 #[cfg(any(target_arch = "x86", target_arch = "arm", target_arch = "aarch64"))]
 mod m {
-    pub fn align() -> uint { 4_usize }
-    pub fn size() -> uint { 8_usize }
+    pub fn align() -> uint { 4 }
+    pub fn size() -> uint { 8 }
 }
 
 #[cfg(target_arch = "x86_64")]
 mod m {
-    pub fn align() -> uint { 4_usize }
-    pub fn size() -> uint { 8_usize }
+    pub fn align() -> uint { 4 }
+    pub fn size() -> uint { 8 }
 }
 
 pub fn main() {
     unsafe {
-        let x = Outer {c8: 22u8, t: Inner {c64: 44u32}};
+        let x = Outer {c8: 22, t: Inner {c64: 44}};
 
         // Send it through the shape code
         let y = format!("{:?}", x);
index 835b4c40f5ca76c5b48cb55a598453a9e9ac5dfe..8b7434ed063453a28e5a9de7f37e9756d1ed36a8 100644 (file)
@@ -44,14 +44,14 @@ struct Outer {
 mod m {
     #[cfg(target_arch = "x86")]
     pub mod m {
-        pub fn align() -> uint { 4_usize }
-        pub fn size() -> uint { 12_usize }
+        pub fn align() -> uint { 4 }
+        pub fn size() -> uint { 12 }
     }
 
     #[cfg(any(target_arch = "x86_64", target_arch = "arm", target_arch = "aarch64"))]
     pub mod m {
-        pub fn align() -> uint { 8_usize }
-        pub fn size() -> uint { 16_usize }
+        pub fn align() -> uint { 8 }
+        pub fn size() -> uint { 16 }
     }
 }
 
@@ -59,8 +59,8 @@ pub fn size() -> uint { 16_usize }
 mod m {
     #[cfg(target_arch = "x86_64")]
     pub mod m {
-        pub fn align() -> uint { 8u }
-        pub fn size() -> uint { 16u }
+        pub fn align() -> uint { 8 }
+        pub fn size() -> uint { 16 }
     }
 }
 
@@ -68,14 +68,14 @@ pub fn size() -> uint { 16u }
 mod m {
     #[cfg(target_arch = "x86")]
     pub mod m {
-        pub fn align() -> uint { 8_usize }
-        pub fn size() -> uint { 16_usize }
+        pub fn align() -> uint { 8 }
+        pub fn size() -> uint { 16 }
     }
 
     #[cfg(target_arch = "x86_64")]
     pub mod m {
-        pub fn align() -> uint { 8_usize }
-        pub fn size() -> uint { 16_usize }
+        pub fn align() -> uint { 8 }
+        pub fn size() -> uint { 16 }
     }
 }
 
@@ -83,14 +83,14 @@ pub fn size() -> uint { 16_usize }
 mod m {
     #[cfg(any(target_arch = "arm", target_arch = "aarch64"))]
     pub mod m {
-        pub fn align() -> uint { 8_usize }
-        pub fn size() -> uint { 16_usize }
+        pub fn align() -> uint { 8 }
+        pub fn size() -> uint { 16 }
     }
 }
 
 pub fn main() {
     unsafe {
-        let x = Outer {c8: 22u8, t: Inner {c64: 44u64}};
+        let x = Outer {c8: 22, t: Inner {c64: 44}};
 
         let y = format!("{:?}", x);
 
index 282a24a407c95d2252f5fdfae96115d9eb47d7de..b152470fbb640941a2668140138c33470f7370dd 100644 (file)
@@ -20,6 +20,6 @@ fn m(input: t3) -> int {
 }
 
 pub fn main() {
-    assert_eq!(m(t3::c(T2 {x: t1::a(10), y: 5}, 4_usize)), 10);
-    assert_eq!(m(t3::c(T2 {x: t1::b(10_usize), y: 5}, 4_usize)), 19);
+    assert_eq!(m(t3::c(T2 {x: t1::a(10), y: 5}, 4)), 10);
+    assert_eq!(m(t3::c(T2 {x: t1::b(10), y: 5}, 4)), 19);
 }
index 89779fa4d2d46283df19b5420768fa98ebaa617b..56dd386ead1c19fc31cf2443d83894fa47477cdc 100644 (file)
@@ -16,8 +16,8 @@ fn foo(x: &uint) -> uint {
 }
 
 pub fn main() {
-    let p = box 22_usize;
+    let p: Box<_> = box 22;
     let r = foo(&*p);
     println!("r={}", r);
-    assert_eq!(r, 22_usize);
+    assert_eq!(r, 22);
 }
index a1af7159a93d99235a5927b467d75e16e222b4ed..0673179eef0062ab4871d29f8d44188b9c42c2f3 100644 (file)
@@ -16,7 +16,7 @@ fn foo(x: &uint) -> uint {
 }
 
 pub fn main() {
-    let p = box 3_usize;
+    let p: Box<_> = box 3;
     let r = foo(&*p);
-    assert_eq!(r, 3_usize);
+    assert_eq!(r, 3);
 }
index 6ebef9f34ad6619d54bd1798288acd183bf532d1..b39343b1f5743ea3416c6255436b7fdd1df585b5 100644 (file)
@@ -9,7 +9,6 @@
 // except according to those terms.
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 struct closure_box<'a> {
@@ -21,11 +20,12 @@ fn box_it<'a>(x: Box<FnMut() + 'a>) -> closure_box<'a> {
 }
 
 pub fn main() {
-    let mut i = 3i32;
+    let mut i = 3;
     assert_eq!(i, 3);
     {
         let cl = || i += 1;
-        let mut cl_box = box_it(box cl);
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        let mut cl_box = box_it(Box::new(cl));
         cl_box.cl.call_mut(());
     }
     assert_eq!(i, 4);
index b15f9d34859932fb4af53a03fbe10081c3cdb274..3708d187d7161077e9cb411e564420d7ae8a3029 100644 (file)
@@ -15,6 +15,6 @@ fn foo(x: &uint) -> &uint { x }
 fn bar(x: &uint) -> uint { *x }
 
 pub fn main() {
-    let p = box 3_usize;
+    let p: Box<_> = box 3;
     assert_eq!(bar(foo(&*p)), 3);
 }
index faa9b37bdcc630807125881fe3046d737f42ae4b..0057a51012dd0bdaef6fdeda53b048a37e14aaf0 100644 (file)
@@ -13,7 +13,8 @@
 #![allow(dead_assignment)]
 #![allow(unused_variable)]
 #![allow(unknown_features)]
-#![feature(box_syntax)]
+
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
 
 // Should pass region checking.
 fn ok(f: Box<FnMut(&uint)>) {
@@ -23,14 +24,14 @@ fn ok(f: Box<FnMut(&uint)>) {
     // f's type should be a subtype of g's type), because f can be
     // used in any context that expects g's type.  But this currently
     // fails.
-    let mut g: Box<for<'r> FnMut(&'r uint)> = box |x| { };
+    let mut g: Box<for<'r> FnMut(&'r uint)> = Box::new(|x| { });
     g = f;
 }
 
 // This version is the same as above, except that here, g's type is
 // inferred.
 fn ok_inferred(f: Box<FnMut(&uint)>) {
-    let mut g: Box<for<'r> FnMut(&'r uint)> = box |_| {};
+    let mut g: Box<for<'r> FnMut(&'r uint)> = Box::new(|_| {});
     g = f;
 }
 
index d07110fd7217f74f5a7673d94581cb9eaea9d433..86f4f2dd18e643377501f2444adadfce20133a99 100644 (file)
@@ -14,7 +14,7 @@
 fn borrow<T>(x: &T) -> &T {x}
 
 pub fn main() {
-    let x = box 3;
+    let x: Box<_> = box 3;
     loop {
         let y = borrow(&*x);
         assert_eq!(*x, *y);
index 708d031a68a6351e9051b6e97885810a323d711a..ebbc5b70f604153934b97bcd208ee3b1413dd42f 100644 (file)
@@ -18,7 +18,7 @@ fn x_coord(p: &Point) -> &int {
 }
 
 pub fn main() {
-    let p = box Point {x: 3, y: 4};
+    let p: Box<_> = box Point {x: 3, y: 4};
     let xc = x_coord(&*p);
     assert_eq!(*xc, 3);
 }
index c71953e20f8af12bd0f3ba4337367c44958431b7..181d962cfae50da52d80bdcd061c36af7086356c 100644 (file)
@@ -21,6 +21,6 @@ fn parameterized(x: &uint) -> uint {
 }
 
 pub fn main() {
-    let x = 3_usize;
-    assert_eq!(parameterized(&x), 3_usize);
+    let x = 3;
+    assert_eq!(parameterized(&x), 3);
 }
index a224017780e2d936419b6ca4f6ec7e235b527b9c..30d8fc34d00744bbed427c1c5e5059204bda9ca7 100644 (file)
@@ -18,7 +18,7 @@
 // This version does not yet work (associated type issues)...
 #[cfg(cannot_use_this_yet)]
 fn foo<'a>(map: RefCell<HashMap<&'static str, &'a [u8]>>) {
-    let one = [1_usize];
+    let one = [1];
     assert_eq!(map.borrow().get("one"), Some(&one[..]));
 }
 
@@ -26,7 +26,7 @@ fn foo<'a>(map: RefCell<HashMap<&'static str, &'a [u8]>>) {
 // ... and this version does not work (the lifetime of `one` is
 // supposed to match the lifetime `'a`) ...
 fn foo<'a>(map: RefCell<HashMap<&'static str, &'a [u8]>>) {
-    let one = [1_usize];
+    let one = [1];
     assert_eq!(map.borrow().get("one"), Some(&one.as_slice()));
 }
 
@@ -41,9 +41,9 @@ fn foo<'a>(map: RefCell<HashMap<&'static str, &'a [u8]>>) {
 }
 
 fn main() {
-    let zer = [0u8];
-    let one = [1u8];
-    let two = [2u8];
+    let zer = [0];
+    let one = [1];
+    let two = [2];
     let mut map = HashMap::new();
     map.insert("zero", &zer[..]);
     map.insert("one",  &one[..]);
index e779e002b299005b33c9db21b1ea21bfb0f834ef..1ad96d4bc55933e7c1d783b5e777027dda87ca0a 100644 (file)
@@ -30,7 +30,8 @@ struct Foo<'a,'tcx:'a> {
 
 impl<'a,'tcx> Foo<'a,'tcx> {
     fn bother(&mut self) -> int {
-        self.elaborate_bounds(box |this| {
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        self.elaborate_bounds(Box::new(|this| {
             // (*) Here: type of `this` is `&'f0 Foo<&'f1, '_2>`,
             // where `'f0` and `'f1` are fresh, free regions that
             // result from the bound regions on the closure, and `'2`
@@ -44,7 +45,7 @@ fn bother(&mut self) -> int {
             // `region_inference.rs` file (and the `givens` field, in
             // particular) for more details.
             this.foo()
-        })
+        }))
     }
 
     fn foo(&mut self) -> int {
index 7198c35944f9a0f5b0e764cb55108a5346375ca0..1bcde77261b930d9ada9754a9a7e290f19bb7e61 100644 (file)
@@ -25,6 +25,7 @@ fn call_static_closure(mut cl: closure_box<'static>) {
 }
 
 pub fn main() {
-    let cl_box = box_it(box || println!("Hello, world!"));
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let cl_box = box_it(Box::new(|| println!("Hello, world!")));
     call_static_closure(cl_box);
 }
index eb3bec773266670d241bb68fbbbb6ec4bb43b803..807227d47db8f2d4eaa1154bcf3d378b1d75ca33 100644 (file)
@@ -37,7 +37,7 @@ fn extension<'e>(x: &'e E<'e>) -> Box<M+'e> {
 }
 
 fn main() {
-    let w = E { f: &10u8 };
+    let w = E { f: &10 };
     let o = extension(&w);
-    assert_eq!(o.n(), 10u8);
+    assert_eq!(o.n(), 10);
 }
index abe6ffe7d4ccaabdbac3ef7d7bf4a63cf364ba78..9209db22433137498df4d2a7fd1ac5b71a197e48 100644 (file)
@@ -34,7 +34,7 @@ fn rename_directory() {
         let fromp = CString::new(test_file.as_vec()).unwrap();
         let modebuf = CString::new(b"w+b").unwrap();
         let ostream = libc::fopen(fromp.as_ptr(), modebuf.as_ptr());
-        assert!((ostream as uint != 0_usize));
+        assert!((ostream as uint != 0));
         let s = "hello".to_string();
         let buf = CString::new(b"hello").unwrap();
         let write_len = libc::fwrite(buf.as_ptr() as *mut _,
index 74227192cabbefae06eb916fbcc1e002f37934ca..14b398b3d9a64dff9796ed2d9d9ea936f6317c2f 100644 (file)
 fn my_err(s: String) -> ! { println!("{}", s); panic!(); }
 
 fn okay(i: uint) -> int {
-    if i == 3_usize {
+    if i == 3 {
         my_err("I don't like three".to_string());
     } else {
         return 42;
     }
 }
 
-pub fn main() { okay(4_usize); }
+pub fn main() { okay(4); }
index ec033b74dd1cde1714b84dbf7b37636ed9aef1a7..abb16c39d113643a22aa1271773fc0a277055cdd 100644 (file)
@@ -43,15 +43,15 @@ fn start(argc: int, argv: *const *const u8) -> int {
     };
     let me = &*args[0];
 
-    let x: &[u8] = &[1u8];
+    let x: &[u8] = &[1];
     pass(Command::new(me).arg(x).output().unwrap());
-    let x: &[u8] = &[2u8];
+    let x: &[u8] = &[2];
     pass(Command::new(me).arg(x).output().unwrap());
-    let x: &[u8] = &[3u8];
+    let x: &[u8] = &[3];
     pass(Command::new(me).arg(x).output().unwrap());
-    let x: &[u8] = &[4u8];
+    let x: &[u8] = &[4];
     pass(Command::new(me).arg(x).output().unwrap());
-    let x: &[u8] = &[5u8];
+    let x: &[u8] = &[5];
     pass(Command::new(me).arg(x).output().unwrap());
 
     0
index e934498ea05066b34de6bea90afdf6f8dc92a682..92582177989b6d234d5dc26eb664898ce7dcc411 100644 (file)
@@ -40,7 +40,7 @@ pub fn main() {
     let new_x = x.change();
     assert_eq!(new_x.a, 55);
 
-    let x = box new_x;
+    let x: Box<_> = box new_x;
     let new_x = x.change_again();
     assert_eq!(new_x.a, 45);
 }
index cf09737e32efd5fc45d3302f40b693ef5310a310..b71b907fcf0432b23ae33ca4bee943041ccf282f 100644 (file)
@@ -17,7 +17,7 @@
 use std::rc::Rc;
 
 pub fn main() {
-   let mut x = box 3;
+   let mut x: Box<_> = box 3;
    x = x;
    assert!(*x == 3);
 
old mode 100755 (executable)
new mode 100644 (file)
index 18519573c26a6ea6ddb08c801559ec82f968293d..51c20bcd09852e7dd1ab39a0bf64842cced73ac7 100644 (file)
 
 
 fn test<F>(f: F) -> uint where F: FnOnce(uint) -> uint {
-    return f(22_usize);
+    return f(22);
 }
 
 pub fn main() {
-    let y = test(|x| 4_usize * x);
-    assert_eq!(y, 88_usize);
+    let y = test(|x| 4 * x);
+    assert_eq!(y, 88);
 }
index 523b7528103ad55026b10a4306707b69943e052d..264ee5f55b9771814b3907724d1d0209f3f85a1c 100644 (file)
@@ -20,7 +20,7 @@ fn test05_start<F:FnOnce(int)>(f: F) {
 }
 
 fn test05() {
-    let three = box 3;
+    let three: Box<_> = box 3;
     let fn_to_send = move|n:int| {
         println!("{}", *three + n); // will copy x into the closure
         assert_eq!(*three, 3);
index 2f56e09b2df83ea5f5d4974bb564d02842f7a245..26dc6c5316b160b9b68fa9fc4837086b97d25a9a 100644 (file)
@@ -25,17 +25,17 @@ struct Panolpy {
 }
 
 fn foo(p: &Panolpy) {
-    assert_eq!(22_i32 >> p.i8, 11_i32);
-    assert_eq!(22_i32 >> p.i16, 11_i32);
-    assert_eq!(22_i32 >> p.i32, 11_i32);
-    assert_eq!(22_i32 >> p.i64, 11_i32);
-    assert_eq!(22_i32 >> p.isize, 11_i32);
+    assert_eq!(22 >> p.i8, 11);
+    assert_eq!(22 >> p.i16, 11);
+    assert_eq!(22 >> p.i32, 11);
+    assert_eq!(22 >> p.i64, 11);
+    assert_eq!(22 >> p.isize, 11);
 
-    assert_eq!(22_i32 >> p.u8, 11_i32);
-    assert_eq!(22_i32 >> p.u16, 11_i32);
-    assert_eq!(22_i32 >> p.u32, 11_i32);
-    assert_eq!(22_i32 >> p.u64, 11_i32);
-    assert_eq!(22_i32 >> p.usize, 11_i32);
+    assert_eq!(22 >> p.u8, 11);
+    assert_eq!(22 >> p.u16, 11);
+    assert_eq!(22 >> p.u32, 11);
+    assert_eq!(22 >> p.u64, 11);
+    assert_eq!(22 >> p.usize, 11);
 }
 
 fn main() {
index f496765edca9882266cb850a8fc4399d93018680..03971668182acd98ff8d1607b2f6dad8033dfa98 100644 (file)
@@ -8,12 +8,10 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 #[derive(Debug)]
 struct Foo(Box<[u8]>);
 
 pub fn main() {
-    println!("{:?}", Foo(box [0, 1, 2]));
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    println!("{:?}", Foo(Box::new([0, 1, 2])));
 }
diff --git a/src/test/run-pass/single-derive-attr-with-gate.rs b/src/test/run-pass/single-derive-attr-with-gate.rs
new file mode 100644 (file)
index 0000000..cc5d8fc
--- /dev/null
@@ -0,0 +1,18 @@
+// Copyright 2015 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(custom_derive)]
+
+#[derive_Clone]
+struct Test;
+
+pub fn main() {
+    Test.clone();
+}
index 475af8f2b8ef05fa70cc1f46c6013705024ac8c6..86eed715f325a925b5e2954351363e21b9e3a71a 100644 (file)
@@ -29,14 +29,14 @@ macro_rules! check {
 pub fn main() {
     check!(Option<u8>, 2,
            None, "None",
-           Some(129u8), "Some(129)");
+           Some(129), "Some(129)");
     check!(Option<i16>, 4,
            None, "None",
-           Some(-20000i16), "Some(-20000)");
+           Some(-20000), "Some(-20000)");
     check!(Either<u8, i8>, 2,
-           Either::Left(132u8), "Left(132)",
-           Either::Right(-32i8), "Right(-32)");
+           Either::Left(132), "Left(132)",
+           Either::Right(-32), "Right(-32)");
     check!(Either<u8, i16>, 4,
-           Either::Left(132u8), "Left(132)",
-           Either::Right(-20000i16), "Right(-20000)");
+           Either::Left(132), "Left(132)",
+           Either::Right(-20000), "Right(-20000)");
 }
index f8fd81b9365159f6bcc21f72e46515172385720f..f650e56bb6b772ccf34ea72cff50b1ce21dbec86 100644 (file)
@@ -8,6 +8,8 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
+#![feature(static_assert)]
+
 #[static_assert]
 static b: bool = true;
 
index 5f6dc4f2a536285ba445671b3e5576d6214dbc87..47f46041c224a38063b397a96ec3004bc2f84ad8 100644 (file)
@@ -21,7 +21,7 @@ fn foo() -> int {
 
     impl Foo for uint {
         fn foo() -> uint {
-            5_usize
+            5
         }
     }
 }
index 359c14ea7b0c0d45ec129a7dff4c3e913a026998..cef7a93aeeddcf89aae499d2536cb4faa8642bd4 100644 (file)
@@ -12,12 +12,12 @@ pub fn main() {
     // Make sure we properly handle repeated self-appends.
     let mut a: String = "A".to_string();
     let mut i = 20;
-    let mut expected_len = 1_usize;
+    let mut expected_len = 1;
     while i > 0 {
         println!("{}", a.len());
         assert_eq!(a.len(), expected_len);
         a = format!("{}{}", a, a);
         i -= 1;
-        expected_len *= 2_usize;
+        expected_len *= 2;
     }
 }
index 6cebd17496a52b07d9aa4d0e389842f5af2caf64..a64477242c08fb43eb7b2fadbc81c5e866c95b50 100644 (file)
@@ -12,11 +12,12 @@ struct S { f0: String, f1: int }
 
 pub fn main() {
     let s = "Hello, world!".to_string();
-    let _s = S {
+    let s = S {
         f0: s.to_string(),
         ..S {
             f0: s,
             f1: 23
         }
     };
+    assert_eq!(s.f0, "Hello, world!");
 }
index 786f080bb9ee3c6350fe6244fdbcfdacdd9b1edf..359ecdab630eccc56fefe0bd811ac916dbc81bd4 100644 (file)
@@ -15,8 +15,9 @@ struct S {
 
 pub fn main() {
     let s = "Hello, world!".to_string();
-    let _s = S {
+    let s = S {
         f1: s.to_string(),
         f0: s
     };
+    assert_eq!(s.f0, "Hello, world!");
 }
diff --git a/src/test/run-pass/struct-order-of-eval-3.rs b/src/test/run-pass/struct-order-of-eval-3.rs
new file mode 100644 (file)
index 0000000..856ed7c
--- /dev/null
@@ -0,0 +1,46 @@
+// Copyright 2015 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.
+
+// Checks that functional-record-update order-of-eval is as expected
+// even when no Drop-implementations are involved.
+
+use std::sync::atomic::{Ordering, AtomicUsize, ATOMIC_USIZE_INIT};
+
+struct W { wrapped: u32 }
+struct S { f0: W, _f1: i32 }
+
+pub fn main() {
+    const VAL: u32 = 0x89AB_CDEF;
+    let w = W { wrapped: VAL };
+    let s = S {
+        f0: { event(0x01); W { wrapped: w.wrapped + 1 } },
+        ..S {
+            f0: { event(0x02); w},
+            _f1: 23
+        }
+    };
+    assert_eq!(s.f0.wrapped, VAL + 1);
+    let actual = event_log();
+    let expect = 0x01_02;
+    assert!(expect == actual,
+            "expect: 0x{:x} actual: 0x{:x}", expect, actual);
+}
+
+static LOG: AtomicUsize = ATOMIC_USIZE_INIT;
+
+fn event_log() -> usize {
+    LOG.load(Ordering::SeqCst)
+}
+
+fn event(tag: u8) {
+    let old_log = LOG.load(Ordering::SeqCst);
+    let new_log = (old_log << 8) + tag as usize;
+    LOG.store(new_log, Ordering::SeqCst);
+}
diff --git a/src/test/run-pass/struct-order-of-eval-4.rs b/src/test/run-pass/struct-order-of-eval-4.rs
new file mode 100644 (file)
index 0000000..25923be
--- /dev/null
@@ -0,0 +1,43 @@
+// Copyright 2015 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.
+
+// Checks that struct-literal expression order-of-eval is as expected
+// even when no Drop-implementations are involved.
+
+use std::sync::atomic::{Ordering, AtomicUsize, ATOMIC_USIZE_INIT};
+
+struct W { wrapped: u32 }
+struct S { f0: W, _f1: i32 }
+
+pub fn main() {
+    const VAL: u32 = 0x89AB_CDEF;
+    let w = W { wrapped: VAL };
+    let s = S {
+        _f1: { event(0x01); 23 },
+        f0: { event(0x02); w },
+    };
+    assert_eq!(s.f0.wrapped, VAL);
+    let actual = event_log();
+    let expect = 0x01_02;
+    assert!(expect == actual,
+            "expect: 0x{:x} actual: 0x{:x}", expect, actual);
+}
+
+static LOG: AtomicUsize = ATOMIC_USIZE_INIT;
+
+fn event_log() -> usize {
+    LOG.load(Ordering::SeqCst)
+}
+
+fn event(tag: u8) {
+    let old_log = LOG.load(Ordering::SeqCst);
+    let new_log = (old_log << 8) + tag as usize;
+    LOG.store(new_log, Ordering::SeqCst);
+}
index c8768731e2bdb5c19022a99f92bd134cb53d0ffe..d67c6322c61cad85d6adde002036c087f00ac495 100644 (file)
@@ -28,19 +28,19 @@ mod rustrt {
 
 fn test1() {
     unsafe {
-        let q = Quad { a: 0xaaaa_aaaa_aaaa_aaaa_u64,
-                 b: 0xbbbb_bbbb_bbbb_bbbb_u64,
-                 c: 0xcccc_cccc_cccc_cccc_u64,
-                 d: 0xdddd_dddd_dddd_dddd_u64 };
+        let q = Quad { a: 0xaaaa_aaaa_aaaa_aaaa,
+                 b: 0xbbbb_bbbb_bbbb_bbbb,
+                 c: 0xcccc_cccc_cccc_cccc,
+                 d: 0xdddd_dddd_dddd_dddd };
         let qq = rustrt::rust_dbg_abi_1(q);
         println!("a: {:x}", qq.a as uint);
         println!("b: {:x}", qq.b as uint);
         println!("c: {:x}", qq.c as uint);
         println!("d: {:x}", qq.d as uint);
-        assert_eq!(qq.a, q.c + 1u64);
-        assert_eq!(qq.b, q.d - 1u64);
-        assert_eq!(qq.c, q.a + 1u64);
-        assert_eq!(qq.d, q.b - 1u64);
+        assert_eq!(qq.a, q.c + 1);
+        assert_eq!(qq.b, q.d - 1);
+        assert_eq!(qq.c, q.a + 1);
+        assert_eq!(qq.d, q.b - 1);
     }
 }
 
@@ -48,14 +48,14 @@ fn test1() {
 fn test2() {
     unsafe {
         let f = Floats { a: 1.234567890e-15_f64,
-                 b: 0b_1010_1010_u8,
+                 b: 0b_1010_1010,
                  c: 1.0987654321e-15_f64 };
         let ff = rustrt::rust_dbg_abi_2(f);
         println!("a: {}", ff.a as f64);
         println!("b: {}", ff.b as uint);
         println!("c: {}", ff.c as f64);
         assert_eq!(ff.a, f.c + 1.0f64);
-        assert_eq!(ff.b, 0xff_u8);
+        assert_eq!(ff.b, 0xff);
         assert_eq!(ff.c, f.a - 1.0f64);
     }
 }
index ddd8cd8be3d5c00f84287e96521660282eeff7be..684ca7fa2b62d30e6daa53613d5b9de78824381d 100644 (file)
@@ -23,7 +23,7 @@ macro_rules! indirect_line { () => ( line!() ) }
 
 pub fn main() {
     assert_eq!(line!(), 25);
-    assert!((column!() == 4u32));
+    assert!((column!() == 4));
     assert_eq!(indirect_line!(), 27);
     assert!((file!().ends_with("syntax-extension-source-utils.rs")));
     assert_eq!(stringify!((2*3) + 5).to_string(), "( 2 * 3 ) + 5".to_string());
index b7fe4983b01b4289ac535efae9ada0e8f4499516..8d8d4caad2404ee69f149a52b4ca3afa3e54a098 100644 (file)
@@ -8,9 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-linux #7340 fails on 32-bit Linux
-// ignore-macos #7340 fails on 32-bit macos
-
 use std::mem;
 
 enum Tag<A> {
@@ -23,15 +20,16 @@ struct Rec {
 }
 
 fn mk_rec() -> Rec {
-    return Rec { c8:0u8, t:Tag::Tag2(0u64) };
+    return Rec { c8:0, t:Tag::Tag2(0) };
 }
 
-fn is_8_byte_aligned(u: &Tag<u64>) -> bool {
+fn is_u64_aligned(u: &Tag<u64>) -> bool {
     let p: uint = unsafe { mem::transmute(u) };
-    return (p & 7_usize) == 0_usize;
+    let u64_align = std::mem::min_align_of::<u64>();
+    return (p & (u64_align - 1)) == 0;
 }
 
 pub fn main() {
     let x = mk_rec();
-    assert!(is_8_byte_aligned(&x.t));
+    assert!(is_u64_aligned(&x.t));
 }
index cb298e720ed825211244db994021c6331b6ff72a..917f2c5b37468fe90bf1ddc4e28fafb19a6e632c 100644 (file)
@@ -8,9 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-linux #7340 fails on 32-bit Linux
-// ignore-macos #7340 fails on 32-bit macos
-
 use std::mem;
 
 enum Tag<A,B> {
@@ -26,12 +23,12 @@ struct Rec<A,B> {
 }
 
 fn mk_rec<A,B>(a: A, b: B) -> Rec<A,B> {
-    Rec { chA:0u8, tA:Tag::VarA(a), chB:1u8, tB:Tag::VarB(b) }
+    Rec { chA:0, tA:Tag::VarA(a), chB:1, tB:Tag::VarB(b) }
 }
 
 fn is_aligned<A>(amnt: uint, u: &A) -> bool {
     let p: uint = unsafe { mem::transmute(u) };
-    return (p & (amnt-1_usize)) == 0_usize;
+    return (p & (amnt-1)) == 0;
 }
 
 fn variant_data_is_aligned<A,B>(amnt: uint, u: &Tag<A,B>) -> bool {
@@ -42,33 +39,34 @@ fn variant_data_is_aligned<A,B>(amnt: uint, u: &Tag<A,B>) -> bool {
 }
 
 pub fn main() {
+    let u64_align = std::mem::min_align_of::<u64>();
     let x = mk_rec(22u64, 23u64);
-    assert!(is_aligned(8_usize, &x.tA));
-    assert!(variant_data_is_aligned(8_usize, &x.tA));
-    assert!(is_aligned(8_usize, &x.tB));
-    assert!(variant_data_is_aligned(8_usize, &x.tB));
+    assert!(is_aligned(u64_align, &x.tA));
+    assert!(variant_data_is_aligned(u64_align, &x.tA));
+    assert!(is_aligned(u64_align, &x.tB));
+    assert!(variant_data_is_aligned(u64_align, &x.tB));
 
     let x = mk_rec(22u64, 23u32);
-    assert!(is_aligned(8_usize, &x.tA));
-    assert!(variant_data_is_aligned(8_usize, &x.tA));
-    assert!(is_aligned(8_usize, &x.tB));
-    assert!(variant_data_is_aligned(4_usize, &x.tB));
+    assert!(is_aligned(u64_align, &x.tA));
+    assert!(variant_data_is_aligned(u64_align, &x.tA));
+    assert!(is_aligned(u64_align, &x.tB));
+    assert!(variant_data_is_aligned(4, &x.tB));
 
     let x = mk_rec(22u32, 23u64);
-    assert!(is_aligned(8_usize, &x.tA));
-    assert!(variant_data_is_aligned(4_usize, &x.tA));
-    assert!(is_aligned(8_usize, &x.tB));
-    assert!(variant_data_is_aligned(8_usize, &x.tB));
+    assert!(is_aligned(u64_align, &x.tA));
+    assert!(variant_data_is_aligned(4, &x.tA));
+    assert!(is_aligned(u64_align, &x.tB));
+    assert!(variant_data_is_aligned(u64_align, &x.tB));
 
     let x = mk_rec(22u32, 23u32);
-    assert!(is_aligned(4_usize, &x.tA));
-    assert!(variant_data_is_aligned(4_usize, &x.tA));
-    assert!(is_aligned(4_usize, &x.tB));
-    assert!(variant_data_is_aligned(4_usize, &x.tB));
+    assert!(is_aligned(4, &x.tA));
+    assert!(variant_data_is_aligned(4, &x.tA));
+    assert!(is_aligned(4, &x.tB));
+    assert!(variant_data_is_aligned(4, &x.tB));
 
     let x = mk_rec(22f64, 23f64);
-    assert!(is_aligned(8_usize, &x.tA));
-    assert!(variant_data_is_aligned(8_usize, &x.tA));
-    assert!(is_aligned(8_usize, &x.tB));
-    assert!(variant_data_is_aligned(8_usize, &x.tB));
+    assert!(is_aligned(u64_align, &x.tA));
+    assert!(variant_data_is_aligned(u64_align, &x.tA));
+    assert!(is_aligned(u64_align, &x.tB));
+    assert!(variant_data_is_aligned(u64_align, &x.tB));
 }
index cc0a75181db96aee22a6432e9ec4b0d632e2836b..5db886c815b2a875039142007894407caf97c881 100644 (file)
@@ -20,7 +20,7 @@ struct t_rec {
 }
 
 pub fn main() {
-    let x = t_rec {c8: 22u8, t: a_tag::a_tag_var(44u64)};
+    let x = t_rec {c8: 22, t: a_tag::a_tag_var(44)};
     let y = format!("{:?}", x);
     println!("y = {:?}", y);
     assert_eq!(y, "t_rec { c8: 22, t: a_tag_var(44) }".to_string());
index 713f55cc10c0ad08497120bab0341ee26503cf54..df99d77142c1b2880cac249744b04ff85f0e0f80 100644 (file)
@@ -8,9 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-// ignore-linux #7340 fails on 32-bit Linux
-// ignore-macos #7340 fails on 32-bit macos
-
 use std::mem;
 
 enum Tag {
@@ -23,15 +20,16 @@ struct Rec {
 }
 
 fn mk_rec() -> Rec {
-    return Rec { c8:0u8, t:Tag::TagInner(0u64) };
+    return Rec { c8:0, t:Tag::TagInner(0) };
 }
 
-fn is_8_byte_aligned(u: &Tag) -> bool {
+fn is_u64_aligned(u: &Tag) -> bool {
     let p: uint = unsafe { mem::transmute(u) };
-    return (p & 7_usize) == 0_usize;
+    let u64_align = std::mem::min_align_of::<u64>();
+    return (p & (u64_align - 1)) == 0;
 }
 
 pub fn main() {
     let x = mk_rec();
-    assert!(is_8_byte_aligned(&x.t));
+    assert!(is_u64_aligned(&x.t));
 }
index 1d297c04c825764f6925acfc7574f1093cfc0784..ca009677ee9746a00155e16a2d41a2092971e354 100644 (file)
@@ -16,12 +16,12 @@ fn test_rec() {
     struct R {val0: int, val1: u8, val2: char}
 
     let (tx, rx) = channel();
-    let r0: R = R {val0: 0, val1: 1u8, val2: '2'};
+    let r0: R = R {val0: 0, val1: 1, val2: '2'};
     tx.send(r0).unwrap();
     let mut r1: R;
     r1 = rx.recv().unwrap();
     assert_eq!(r1.val0, 0);
-    assert_eq!(r1.val1, 1u8);
+    assert_eq!(r1.val1, 1);
     assert_eq!(r1.val2, '2');
 }
 
@@ -84,14 +84,14 @@ fn test_tag() {
     let (tx, rx) = channel();
     tx.send(t::tag1).unwrap();
     tx.send(t::tag2(10)).unwrap();
-    tx.send(t::tag3(10, 11u8, 'A')).unwrap();
+    tx.send(t::tag3(10, 11, 'A')).unwrap();
     let mut t1: t;
     t1 = rx.recv().unwrap();
     assert_eq!(t1, t::tag1);
     t1 = rx.recv().unwrap();
     assert_eq!(t1, t::tag2(10));
     t1 = rx.recv().unwrap();
-    assert_eq!(t1, t::tag3(10, 11u8, 'A'));
+    assert_eq!(t1, t::tag3(10, 11, 'A'));
 }
 
 fn test_chan() {
index ca2a8cf5506eec1486b46550bfa9cacae87d1061..46f9e991347e42bc601c200cf0fd39d8b8fcb9c4 100644 (file)
@@ -17,7 +17,7 @@
 pub fn main() {
     let (tx, rx) = channel::<uint>();
 
-    let x = box 1;
+    let x: Box<_> = box 1;
     let x_in_parent = &(*x) as *const int as uint;
 
     let _t = Thread::spawn(move || {
index 82584c83de059da98438d880ca4f08924b182502..23ea998c026085331ab204c30a17cd5799937c08 100644 (file)
@@ -52,7 +52,7 @@ fn main() {
     let addr = rx.recv().unwrap();
 
     let (tx, rx) = channel();
-    for _ in 0_usize..1000 {
+    for _ in 0..1000 {
         let tx = tx.clone();
         Builder::new().stack_size(64 * 1024).spawn(move|| {
             match TcpStream::connect(addr) {
@@ -71,7 +71,7 @@ fn main() {
     // Wait for all clients to exit, but don't wait for the server to exit. The
     // server just runs infinitely.
     drop(tx);
-    for _ in 0_usize..1000 {
+    for _ in 0..1000 {
         rx.recv().unwrap();
     }
     unsafe { libc::exit(0) }
index dcb2fe6dfc07660a78be9646655e93b5df4bf3c8..b8e05b4d35ab78da407efe8174b2d383a2bac5ca 100644 (file)
 // ignore-pretty: does not work well with `--test`
 
 #[test]
-#[should_fail(expected = "foo")]
+#[should_panic(expected = "foo")]
 fn test_foo() {
     panic!("foo bar")
 }
 
 #[test]
-#[should_fail(expected = "foo")]
+#[should_panic(expected = "foo")]
 fn test_foo_dynamic() {
     panic!("{} bar", "foo")
 }
index 26772a5b22c076c140adb0244b7ff98a1e7e28d2..cf23785b844482d226a02b63ee008f5042505076 100644 (file)
@@ -104,9 +104,10 @@ fn check_legs(arc: Arc<Vec<Box<Pet+Sync+Send>>>) {
 }
 fn check_names(arc: Arc<Vec<Box<Pet+Sync+Send>>>) {
     for pet in &*arc {
-        pet.name(box |name| {
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        pet.name(Box::new(|name| {
             assert!(name.as_bytes()[0] == 'a' as u8 && name.as_bytes()[1] == 'l' as u8);
-        })
+        }))
     }
 }
 fn check_pedigree(arc: Arc<Vec<Box<Pet+Sync+Send>>>) {
index fa02dabb373b198690cd228533e818a2ead112d3..1565ccfe459d26a11b8fa25a5c6faaee5596d53b 100644 (file)
@@ -8,9 +8,6 @@
 // option. This file may not be copied, modified, or distributed
 // except according to those terms.
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 trait Trait<T> {
     fn f(&self, x: T);
 }
@@ -29,7 +26,8 @@ fn f(&self, x: &'static str) {
 
 pub fn main() {
     let a = Struct { x: 1, y: 2 };
-    let b: Box<Trait<&'static str>> = box a;
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let b: Box<Trait<&'static str>> = Box::new(a);
     b.f("Mary");
     let c: &Trait<&'static str> = &a;
     c.f("Joe");
index 1ae9b3f0e959bb25d1a446075a37175532af6abe..6db7113b0504cb169b1f350b984fc43fc81ba7c4 100644 (file)
@@ -33,14 +33,16 @@ fn foo(mut a: Box<Writer>) {
     a.write(b"Hello\n");
 }
 
+// FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+
 pub fn main() {
     let a = Struct { x: 1, y: 2 };
-    let b: Box<Trait> = box a;
+    let b: Box<Trait> = Box::new(a);
     b.f();
     let c: &Trait = &a;
     c.f();
 
     let out = old_io::stdout();
-    foo(box out);
+    foo(Box::new(out));
 }
 
index 383849ca51267532abe21f9b51b960caa721ff84..acaa74373f01f20f39c78a1f73791f11cc52a5fb 100644 (file)
@@ -21,6 +21,6 @@ fn f<T, V: A<T>>(i: V, j: uint) -> uint {
 }
 
 pub fn main () {
-    assert_eq!(f::<f64, int>(0, 2_usize), 2_usize);
-    assert_eq!(f::<uint, int>(0, 2_usize), 2_usize);
+    assert_eq!(f::<f64, int>(0, 2), 2);
+    assert_eq!(f::<uint, int>(0, 2), 2);
 }
index 6f89490716f081d123628285840d0404d4c17222..18097b59b08e26e8c5b7abe2d1855d3abaaaee50 100644 (file)
@@ -49,5 +49,5 @@ fn method(&self, _x: Type<(u8,V)>) -> int { 0 }
 
 pub fn main() {
     let a = box() () as Box<Trait<u8, u8>>;
-    assert_eq!(a.method(Type::Constant((1u8, 2u8))), 0);
+    assert_eq!(a.method(Type::Constant((1, 2))), 0);
 }
index 4e481910aa98fd215d9657ce77fb28cf6fa0832b..99910f1573887fef3f9c6031bfd424ba39554470 100644 (file)
@@ -36,7 +36,7 @@ fn extension<'e>(x: &'e E<'e>) -> Box<M+'e> {
 }
 
 fn main() {
-    let w = E { f: &10u8 };
+    let w = E { f: &10 };
     let o = extension(&w);
-    assert_eq!(o.n(), 10u8);
+    assert_eq!(o.n(), 10);
 }
diff --git a/src/test/run-pass/traits-assoc-type-in-supertrait.rs b/src/test/run-pass/traits-assoc-type-in-supertrait.rs
new file mode 100644 (file)
index 0000000..6a4a671
--- /dev/null
@@ -0,0 +1,31 @@
+// Copyright 2015 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.
+
+// Test case where an associated type is referenced from within the
+// supertrait definition. Issue #20220.
+
+use std::vec::IntoIter;
+
+pub trait Foo: Iterator<Item=<Self as Foo>::Key> {
+    type Key;
+}
+
+impl Foo for IntoIter<i32> {
+    type Key = i32;
+}
+
+fn sum_foo<F:Foo<Key=i32>>(f: F) -> i32 {
+    f.fold(0, |a,b| a + b)
+}
+
+fn main() {
+    let x = sum_foo(vec![11, 10, 1].into_iter());
+    assert_eq!(x, 22);
+}
index 5af2d4ee806d225422b1d5de0cf4b487870a6792..650688dd9088fc9d8da4f90ff55c98233e0111d8 100644 (file)
@@ -35,5 +35,5 @@ fn main() {
     assert_eq!(get_it(&1_u32), 1_u32);
     assert_eq!(get_it(&1_u16), 1_u16);
     assert_eq!(get_it(&Some(1_u16)), Some(1_u16));
-    assert_eq!(get_it(&box 1), box 1);
+    assert_eq!(get_it(&Box::new(1)), Box::new(1));
 }
diff --git a/src/test/run-pass/traits-issue-23003.rs b/src/test/run-pass/traits-issue-23003.rs
new file mode 100644 (file)
index 0000000..37b13d3
--- /dev/null
@@ -0,0 +1,39 @@
+// Copyright 2015 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.
+
+// Test stack overflow triggered by evaluating the implications. To be
+// WF, the type `Receipt<Complete>` would require that `<Complete as
+// Async>::Cancel` be WF. This normalizes to `Receipt<Complete>`
+// again, leading to an infinite cycle. Issue #23003.
+
+#![allow(dead_code)]
+#![allow(unused_variables)]
+
+use std::marker::PhantomData;
+
+trait Async {
+    type Cancel;
+}
+
+struct Receipt<A:Async> {
+    marker: PhantomData<A>,
+}
+
+struct Complete {
+    core: Option<()>,
+}
+
+impl Async for Complete {
+    type Cancel = Receipt<Complete>;
+}
+
+fn foo(r: Receipt<Complete>) { }
+
+fn main() { }
diff --git a/src/test/run-pass/traits-repeated-supertrait.rs b/src/test/run-pass/traits-repeated-supertrait.rs
new file mode 100644 (file)
index 0000000..fdaa8d6
--- /dev/null
@@ -0,0 +1,56 @@
+// Copyright 2015 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.
+
+// Test a case of a trait which extends the same supertrait twice, but
+// with difference type parameters. Test that we can invoke the
+// various methods in various ways successfully.
+// See also `compile-fail/trait-repeated-supertrait-ambig.rs`.
+
+trait CompareTo<T> {
+    fn same_as(&self, t: T) -> bool;
+}
+
+trait CompareToInts : CompareTo<i64> + CompareTo<u64> {
+}
+
+impl CompareTo<i64> for i64 {
+    fn same_as(&self, t: i64) -> bool { *self == t }
+}
+
+impl CompareTo<u64> for i64 {
+    fn same_as(&self, t: u64) -> bool { *self == (t as i64) }
+}
+
+impl CompareToInts for i64 { }
+
+fn with_obj(c: &CompareToInts) -> bool {
+    c.same_as(22_i64) && c.same_as(22_u64)
+}
+
+fn with_trait<C:CompareToInts>(c: &C) -> bool {
+    c.same_as(22_i64) && c.same_as(22_u64)
+}
+
+fn with_ufcs1<C:CompareToInts>(c: &C) -> bool {
+    CompareToInts::same_as(c, 22_i64) && CompareToInts::same_as(c, 22_u64)
+}
+
+fn with_ufcs2<C:CompareToInts>(c: &C) -> bool {
+    CompareTo::same_as(c, 22_i64) && CompareTo::same_as(c, 22_u64)
+}
+
+fn main() {
+    assert_eq!(22_i64.same_as(22_i64), true);
+    assert_eq!(22_i64.same_as(22_u64), true);
+    assert_eq!(with_trait(&22), true);
+    assert_eq!(with_obj(&22), true);
+    assert_eq!(with_ufcs1(&22), true);
+    assert_eq!(with_ufcs2(&22), true);
+}
index 7d1fad5d281646281ce096e2cad70b83f08a451f..432dbd72a294887c30c2f8d3ac7820077a9aac06 100644 (file)
@@ -32,13 +32,13 @@ fn r(i:int) -> r {
 pub fn main() {
     p_foo(r(10));
 
-    p_foo(box r(10));
-    p_foo(box 10);
+    p_foo::<Box<_>>(box r(10));
+    p_foo::<Box<_>>(box 10);
     p_foo(10);
 
-    s_foo(box 10);
+    s_foo::<Box<_>>(box 10);
     s_foo(10);
 
-    u_foo(box 10);
+    u_foo::<Box<_>>(box 10);
     u_foo(10);
 }
index cf8a09998daa01b6148fc0aafade82e0b17dab95..5d80cec2a05fda51ce76b1d5fa18f4b8eaca1a23 100644 (file)
@@ -16,11 +16,11 @@ struct S<T> {
 
 fn range_<F>(lo: uint, hi: uint, mut it: F) where F: FnMut(uint) {
     let mut lo_ = lo;
-    while lo_ < hi { it(lo_); lo_ += 1_usize; }
+    while lo_ < hi { it(lo_); lo_ += 1; }
 }
 
 fn create_index<T>(_index: Vec<S<T>> , _hash_fn: extern fn(T) -> uint) {
-    range_(0_usize, 256_usize, |_i| {
+    range_(0, 256, |_i| {
         let _bucket: Vec<T> = Vec::new();
     })
 }
index 48dc944382171395ff9ccfcb36b37eec4a564b31..c850c01753bd880cb8033e2eedfc91599b9c1cb9 100644 (file)
@@ -21,17 +21,17 @@ unsafe impl Sync for TestStruct {}
 
 
 pub fn main() {
-    let x: Vec<_> = (0_usize..5).collect();
+    let x: Vec<_> = (0..5).collect();
     let expected: &[uint] = &[0,1,2,3,4];
     assert_eq!(x, expected);
 
-    let x = (0_usize..5).collect::<Vec<_>>();
+    let x = (0..5).collect::<Vec<_>>();
     assert_eq!(x, expected);
 
     let y: _ = "hello";
     assert_eq!(y.len(), 5);
 
-    let ptr = &5_usize;
+    let ptr = &5;
     let ptr2 = ptr as *const _;
 
     assert_eq!(ptr as *const uint as uint, ptr2 as uint);
index 6ad320580dfec289d227aeb9d595111997b8da80..027bd7ca6806fccf19392ff09deae365a38c3ec9 100644 (file)
@@ -12,7 +12,7 @@
 
 
 pub fn main() {
-    let mut word: u32 = 200000u32;
-    word = word - 1u32;
-    assert_eq!(word, 199999u32);
+    let mut word: u32 = 200000;
+    word = word - 1;
+    assert_eq!(word, 199999);
 }
index 0a178b250af4f6d635bec9ebe05a26110be8be57..ff25d95d1fd211d0da4246e733377ef5e0650670 100644 (file)
 // These constants were chosen because they aren't used anywhere
 // in the rest of the generated code so they're easily grep-able.
 pub fn main() {
-    let mut x: u8 = 19u8; // 0x13
+    let mut x: u8 = 19; // 0x13
 
-    let mut y: u8 = 35u8; // 0x23
+    let mut y: u8 = 35; // 0x23
 
-    x = x + 7u8; // 0x7
+    x = x + 7; // 0x7
 
-    y = y - 9u8; // 0x9
+    y = y - 9; // 0x9
 
     assert_eq!(x, y);
 }
index 90ed3a5eec3a2fa928589d3f5aef48db8a6f3ddc..7f69d0781345f17500c8f7e96fa5e8ee9da1bf7c 100644 (file)
 
 
 pub fn main() {
-    let mut x: u8 = 12u8;
-    let y: u8 = 12u8;
-    x = x + 1u8;
-    x = x - 1u8;
+    let mut x: u8 = 12;
+    let y: u8 = 12;
+    x = x + 1;
+    x = x - 1;
     assert_eq!(x, y);
-    // x = 14u8;
-    // x = x + 1u8;
+    // x = 14;
+    // x = x + 1;
 
 }
index 2be9f75dae12ca2b1d071c262373524ee7b8c655..832c1f8802d1ff9ab3a67a5d0f5d303eb481b042 100644 (file)
@@ -46,11 +46,11 @@ fn baz(self: Bar<T>, x: int) -> int {
 }
 
 fn main() {
-    let foo = box Foo {
+    let foo: Box<_> = box Foo {
         f: 1,
     };
     println!("{} {} {}", foo.foo(2), foo.bar(2), foo.baz(2));
-    let bar = box Bar {
+    let bar: Box<_> = box Bar {
         f: 1,
     };
     println!("{} {} {}", bar.foo(2), bar.bar(2), bar.baz(2));
index 2ae63040d17850c373b507aeeea377fa03332a41..34cf44bba2efbf55508ea919425817d966f92fa8 100644 (file)
@@ -20,6 +20,6 @@ fn test(&self) -> i32 { *self }
 }
 
 fn main() {
-    let a: &Foo = &22_i32;
+    let a: &Foo = &22;
     assert_eq!(Foo::test(a), 22);
 }
index da647e90c00f6fdbb4b3389d2fbce7bcd0708838..52311544297ae1d52149caa20415d55f7a76ecdf 100644 (file)
 // Test that the call operator autoderefs when calling to an object type.
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 use std::ops::FnMut;
 
 fn make_adder(x: int) -> Box<FnMut(int)->int + 'static> {
-    box move |y| { x + y }
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    Box::new(move |y| { x + y })
 }
 
 pub fn main() {
index 8ee3c96f580d1edb6521039950d50b779b98321a..a34799fdcc543b8adc9a1720da70be8ccf8a326a 100644 (file)
@@ -9,13 +9,13 @@
 // except according to those terms.
 
 #![allow(unknown_features)]
-#![feature(box_syntax)]
 #![feature(unboxed_closures)]
 
 use std::ops::FnMut;
 
 fn make_adder(x: int) -> Box<FnMut(int)->int + 'static> {
-    box move |y| { x + y }
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    Box::new(move |y| { x + y })
 }
 
 pub fn main() {
index 535c4562362c0d3ba9620e768aa66a9855ba4ad3..056ae63b68488d5773ea9fb23d7a484744790367 100644 (file)
@@ -17,7 +17,8 @@
 
 fn main(){
     fn bar<'a, T:Clone+'a> (t: T) -> Box<FnMut()->T + 'a> {
-        box move || t.clone()
+        // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+        Box::new(move || t.clone())
     }
 
     let mut f = bar(42_u32);
index c8f0d5fde45efea490bee262988152a5cd764987..16a55ab550d2fcd46d501ae729bd98110af418de 100644 (file)
 #![feature(unboxed_closures)]
 
 fn main() {
-    let task: Box<Fn(int) -> int> = box |x| x;
+    // FIXME (#22405): Replace `Box::new` with `box` here when/if possible.
+    let task: Box<Fn(int) -> int> = Box::new(|x| x);
     task.call((0, ));
 
-    let mut task: Box<FnMut(int) -> int> = box |x| x;
+    let mut task: Box<FnMut(int) -> int> = Box::new(|x| x);
     task(0);
 
     call(|x| x, 22);
index 5c36832d9f67f50557abd1d0034578bd224e9d8f..ce05f077357f87c78ca53f593a7c262db297f012 100644 (file)
@@ -12,8 +12,8 @@
 //
 //    error: internal compiler error: get_unique_type_id_of_type() -
 //    unexpected type: closure,
-//    ty_closure(syntax::ast::DefId{krate: 0u32, node: 66u32},
-//    ReScope(63u32))
+//    ty_closure(syntax::ast::DefId{krate: 0, node: 66},
+//    ReScope(63))
 //
 // This is a regression test for issue #17021.
 //
@@ -28,8 +28,8 @@ pub fn replace_map<'a, T, F>(src: &mut T, prod: F) where F: FnOnce(T) -> T {
 }
 
 pub fn main() {
-    let mut a = 7_usize;
+    let mut a = 7;
     let b = &mut a;
     replace_map(b, |x: uint| x * 2);
-    assert_eq!(*b, 14_usize);
+    assert_eq!(*b, 14);
 }
index b7980ed9021e2f9a241b01ccf131e724e0ea54bf..d44a8cdcc24756ec1968e787bdb5270c6c9940fd 100644 (file)
@@ -27,7 +27,7 @@ fn change(mut self: Box<X>) -> Box<X> {
 }
 
 pub fn main() {
-    let x = box X { a: 32 };
+    let x: Box<_> = box X { a: 32 };
     let new_x = x.change();
     assert_eq!(new_x.a, 55);
 }
index c19063fe46483e796bb66b287b989ab3f9e1deae..78578bdb3c3a1159d8badf59cea88674fe9f5ba1 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let mut i = box 1;
+    let mut i: Box<_> = box 1;
     // Should be a copy
     let mut j;
     j = i.clone();
index 241258f089c56cdf7fb95207ea0f121b365899b2..9edd83d2c7cb96a4ed107a70cf9ccf181d4a85da 100644 (file)
@@ -13,8 +13,8 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 1;
-    let mut j = box 2;
+    let i: Box<_> = box 1;
+    let mut j: Box<_> = box 2;
     // Should drop the previous value of j
     j = i;
     assert_eq!(*j, 1);
index c8abb0808482fb813b3de7d03be0eaab10f8ee72..64f8b998096ed6e76a8e62fdd84eca1a5ccf03d0 100644 (file)
@@ -18,6 +18,6 @@ fn f<T>(t: T) -> T {
 }
 
 pub fn main() {
-    let t = f(box 100);
+    let t = f::<Box<_>>(box 100);
     assert_eq!(t, box 100);
 }
index cbcb6afb4c88c51ac1bc901d6bf2cc9c0fdf06a6..c9cbaf27c4f2ff73d0d0edd3a32ce41da3d3f31b 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let mut i;
+    let mut i: Box<_>;
     i = box 1;
     assert_eq!(*i, 1);
 }
index aab7f4108fba659f5a2099ab3ad1058a26b04bd4..3bab3a6b79a116b0d7f8b950fe7454a1cedc8c82 100644 (file)
@@ -14,7 +14,7 @@
 struct J { j: int }
 
 pub fn main() {
-    let i = box J {
+    let i: Box<_> = box J {
         j: 100
     };
     assert_eq!(i.j, 100);
index 30c4b2d7b565cb5a8d991517a3e9e46d8665ab40..1c94447392160ce0226f5fde8364eed03241ce18 100644 (file)
@@ -12,6 +12,6 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box vec!(100);
+    let i: Box<_> = box vec!(100);
     assert_eq!((*i)[0], 100);
 }
index a2962dc00d50300f34fac08b58d7e99697f472e8..8fe86455b4525785601685136f34b1d7b838131c 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 100;
+    let i: Box<_> = box 100;
     assert!(i == box 100);
     assert!(i < box 101);
     assert!(i <= box 100);
index e4099c94c2f1a6e93941fc059f41f9d747535d08..cb6e84ae1aa7387b052dc45a76bbb86854298ef7 100644 (file)
@@ -14,7 +14,7 @@
 pub fn main() {
     enum t { t1(int), t2(int), }
 
-    let _x = box t::t1(10);
+    let _x: Box<_> = box t::t1(10);
 
     /*alt *x {
       t1(a) {
index 975f1e9da827f42245b551a67ccd7cbf9794d7ca..7264b9fee9524d672ba809b9bc1ae003091fe114 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    box 100;
+    let _: Box<_> = box 100;
 }
 
 fn vec() {
index 3af38784add9fbf1687e371f623295f92666563c..14bb72f4412bed49871b612cb5a0605b049d0f28 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let mut i = box 1;
+    let mut i: Box<_> = box 1;
     // Should be a copy
     let mut j = i.clone();
     *i = 2;
index c9192748809af7a23b3d67c51ff3de686751b15e..803e7ba16ed4003aaeadc0f692cb8e809a81a579 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 1;
+    let i: Box<_> = box 1;
     let j = i;
     assert_eq!(*j, 1);
 }
index 96dd9f51fbe8fb4c0d11b5c1efcc1ef80fe971bd..360adaa638f96fcbcd9c5bec045948da8dfda016 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 100;
+    let i: Box<_> = box 100;
     let j = i;
     assert_eq!(*j, 100);
 }
index 41d3b87a003c0e8bf7b0d30289cb2c8bc02b3124..1c1228f924145090952bc7958017b50612cc777d 100644 (file)
@@ -12,6 +12,6 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 100;
+    let i: Box<_> = box 100;
     assert_eq!(*i, 100);
 }
index c5a0a4df2751da32803a7bdd0f36a2e408c1c334..745a55e06510facf894e3764eb21c3ed045bb6fb 100644 (file)
@@ -12,5 +12,5 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let _x = box vec!(0,0,0,0,0);
+    let _x: Box<_> = box vec!(0,0,0,0,0);
 }
index 3bde79fdce01be2c897aeec55285969293aff81d..20bf4bef1714dae413a5f886f154cab440456fe8 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let mut a = vec!(box 10);
+    let mut a: Vec<Box<_>> = vec!(box 10);
     let b = a.clone();
 
     assert_eq!(*a[0], 10);
index 05b0c7244deece4475096a0f13767794319f48d8..c24ec8fe44a3c396c9c2ad99128d0b098b949fa2 100644 (file)
@@ -12,6 +12,6 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let vect = vec!(box 100);
+    let vect : Vec<Box<_>> = vec!(box 100);
     assert!(vect[0] == box 100);
 }
index d3f13f1609f7551b936d7b8cef1060b679143060..44e8703aaf2febcf6f662c84c43a7721b4c2ee05 100644 (file)
@@ -12,5 +12,5 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let _i = box 100;
+    let _i: Box<_> = box 100;
 }
index 4c93c379b488a0d428540eb627ffce80f5d9797f..6bb1fdcf5627a5b72a20644832bff3bc7171a848 100644 (file)
@@ -23,11 +23,11 @@ fn g<T:Send + PartialEq>(i: T, j: T) {
         assert!(i != j);
     }
 
-    let i = box 100;
-    let j = box 100;
+    let i: Box<_> = box 100;
+    let j: Box<_> = box 100;
     f(i, j);
-    let i = box 100;
-    let j = box 101;
+    let i: Box<_> = box 100;
+    let j: Box<_> = box 101;
     g(i, j);
 }
 
@@ -41,11 +41,11 @@ fn g<T:PartialEq>(i: T, j: T) {
         assert!(i != j);
     }
 
-    let i = box 100;
-    let j = box 100;
+    let i: Box<_> = box 100;
+    let j: Box<_> = box 100;
     f(i, j);
-    let i = box 100;
-    let j = box 101;
+    let i: Box<_> = box 100;
+    let j: Box<_> = box 101;
     g(i, j);
 }
 
@@ -59,11 +59,11 @@ fn g<T:PartialEq>(i: T, j: T) {
         assert!(i != j);
     }
 
-    let i = box 100;
-    let j = box 100;
+    let i: Box<_> = box 100;
+    let j: Box<_> = box 100;
     f(i, j);
-    let i = box 100;
-    let j = box 101;
+    let i: Box<_> = box 100;
+    let j: Box<_> = box 101;
     g(i, j);
 }
 
index 4b21b949f8836bd0b4d3883456013cea4862b605..148ca4757ae927eccb8f1c5cb89e20f19a27c52f 100644 (file)
@@ -12,6 +12,6 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 100;
+    let i: Box<_> = box 100;
     println!("{}", i);
 }
index a1502c2eb8c0fa3ffda2425bf0e3984a7510fdf2..93614e86c7303fb0cebe3aa5ddf3352126599a97 100644 (file)
 
 // Issue #961
 
-#![allow(unknown_features)]
-#![feature(box_syntax)]
-
 fn altsimple() {
-    match box true {
+    match Box::new(true) {
       _ => { }
     }
 }
index 705b9d6e92c53193212bed767210aebaaa97f089..126cc646833a14b83bb938680b83ee1341096da3 100644 (file)
@@ -13,8 +13,8 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 100;
-    let j = box 200;
+    let i: Box<_> = box 100;
+    let j: Box<_> = box 200;
     let j = i;
     assert_eq!(*j, 100);
 }
index b6c24f5be289a7a6e4b4f1c8532af04a1369eadb..9ac5e86f87b54af426e54b9182a065020a2e9d13 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let mut i;
+    let mut i: Box<_>;
     i = box 100;
     assert_eq!(*i, 100);
 }
index ed13bf6a5c4f931378ba65f57ad14dd47bbea572..a54b343f2fa3d21862d88f6b412bdc9ea358fe6d 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let i = box 100;
+    let i: Box<_> = box 100;
     let mut j;
     j = i;
     assert_eq!(*j, 100);
index 403b8bf18b823f31d357995039bf33318ad3ec23..ca01c07ab80431e73f6dabfe2866e71a16eab114 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let mut i = box 0;
+    let mut i: Box<_> = box 0;
     *i = 1;
     assert_eq!(*i, 1);
 }
index 5db96bc3564f56d39f6bdfcb4c90cb7573640e74..8141e3bce3c2482003c6fd71536ca4c0ddb2acae 100644 (file)
@@ -17,7 +17,7 @@ struct Foo {a: int, b: uint}
 enum bar { u(Box<Foo>), w(int), }
 
 pub fn main() {
-    assert!(match bar::u(box Foo{a: 10, b: 40_usize}) {
+    assert!(match bar::u(box Foo{a: 10, b: 40}) {
               bar::u(box Foo{a: a, b: b}) => { a + (b as int) }
               _ => { 66 }
             } == 50);
index 756911d29fc8c3b3da3390898922bb17442186a6..c20604406b94c823769c184dbb1287848f003279 100644 (file)
@@ -14,7 +14,7 @@
 struct X { x: int }
 
 pub fn main() {
-    let x = box X {x: 1};
+    let x: Box<_> = box X {x: 1};
     let bar = x;
     assert_eq!(bar.x, 1);
 }
index 43824812ec546c44a6f90c6adf8f8f5d19d475f0..654ac9a095cb10d12ee181dde40c8243b72fcbd4 100644 (file)
@@ -20,9 +20,9 @@ fn child(tx: &Sender<Box<uint>>, i: uint) {
 
 pub fn main() {
     let (tx, rx) = channel();
-    let n = 100_usize;
-    let mut expected = 0_usize;
-    let _t = (0_usize..n).map(|i| {
+    let n = 100;
+    let mut expected = 0;
+    let _t = (0..n).map(|i| {
         expected += i;
         let tx = tx.clone();
         thread::spawn(move|| {
@@ -30,8 +30,8 @@ pub fn main() {
         })
     }).collect::<Vec<_>>();
 
-    let mut actual = 0_usize;
-    for _ in 0_usize..n {
+    let mut actual = 0;
+    for _ in 0..n {
         let j = rx.recv().unwrap();
         actual += *j;
     }
index 2a462e9cdd83ca72b35e99835e14e29e19b09eb2..72022afe5fd99a489415f631fd9a1ea35e3ac0ce 100644 (file)
@@ -14,7 +14,7 @@
 use std::sync::mpsc::channel;
 
 pub fn main() {
-    let (tx, rx) = channel();
+    let (tx, rx) = channel::<Box<_>>();
     tx.send(box 100).unwrap();
     let v = rx.recv().unwrap();
     assert_eq!(v, box 100);
index 2adb9c22f60c1563aebde48ccd08c6e3ac9b3640..1315e443816228c61613df4cf6a0eace2977d742 100644 (file)
@@ -14,8 +14,8 @@
 use std::mem::swap;
 
 pub fn main() {
-    let mut i = box 100;
-    let mut j = box 200;
+    let mut i: Box<_> = box 100;
+    let mut j: Box<_> = box 200;
     swap(&mut i, &mut j);
     assert_eq!(i, box 200);
     assert_eq!(j, box 100);
index ae175d27b0a4ea09b08f9ae0bdbd75e7de00032a..1a479d05d50936ff52b8902d2bbdef06f7866528 100644 (file)
@@ -7,8 +7,6 @@
 // <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-lexer-test FIXME #15879
 
 // Test syntax checks for `?Sized` syntax.
 
index 10b2f2fb7092423c2a2e77c772baf71b68abed31..e0d37ff40de59b4b62b475f31a1eefd9e61a6af5 100644 (file)
@@ -7,8 +7,6 @@
 // <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-lexer-test FIXME #15879
 
 #![allow(unknown_features)]
 #![feature(box_syntax)]
index 983152cd056d9ba7747bc856f5fed89c8323f275..5bd76d093d483f0da929237298ee55e373de605c 100644 (file)
@@ -66,19 +66,18 @@ struct Foo_<T> {
             f: [T; 3]
         }
 
-        let data = box Foo_{f: [1i32, 2, 3] };
+        let data: Box<Foo_<i32>> = box Foo_{f: [1, 2, 3] };
         let x: &Foo<i32> = mem::transmute(raw::Slice { len: 3, data: &*data });
         assert!(x.f.len() == 3);
         assert!(x.f[0] == 1);
-        assert!(x.f[1] == 2);
-        assert!(x.f[2] == 3);
 
         struct Baz_ {
             f1: uint,
             f2: [u8; 5],
         }
 
-        let data = box Baz_{ f1: 42, f2: ['a' as u8, 'b' as u8, 'c' as u8, 'd' as u8, 'e' as u8] };
+        let data: Box<_> = box Baz_ {
+            f1: 42, f2: ['a' as u8, 'b' as u8, 'c' as u8, 'd' as u8, 'e' as u8] };
         let x: &Baz = mem::transmute( raw::Slice { len: 5, data: &*data } );
         assert!(x.f1 == 42);
         let chs: Vec<char> = x.f2.chars().collect();
@@ -96,7 +95,7 @@ struct Qux_ {
         let obj: Box<St> = box St { f: 42 };
         let obj: &Tr = &*obj;
         let obj: raw::TraitObject = mem::transmute(&*obj);
-        let data = box Qux_{ f: St { f: 234 } };
+        let data: Box<_> = box Qux_{ f: St { f: 234 } };
         let x: &Qux = mem::transmute(raw::TraitObject { vtable: obj.vtable,
                                                         data: mem::transmute(&*data) });
         assert!(x.f.foo() == 234);
index 4e8fdda95631185c9fc4541c41e4af2b947c3491..9f20426aa218ecbb1ddb4e62558d6201a87e0198 100644 (file)
@@ -12,7 +12,7 @@
 #![feature(box_syntax)]
 
 pub fn main() {
-    let _x = box 1;
+    let _x: Box<_> = box 1;
     let lam_move = || {};
     lam_move();
 }
index d053b03a2ca8a298da6942129e7ce943cfbbd2fc..57534feec31214ac1377fae6bc1ad209cd19bd35 100644 (file)
@@ -18,6 +18,6 @@
 
 pub fn main()
 {
-    let y = box 1;
+    let y: Box<_> = box 1;
     y;
 }
index 4d90f71c830ba6db56bf83758047fb6119f50d78..b7229a00480cb0c112e73b150090b3197fed1eec 100644 (file)
@@ -14,7 +14,7 @@
 use std::thread;
 
 fn f() {
-    let _a = box 0;
+    let _a: Box<_> = box 0;
     panic!();
 }
 
index 96bba01068f2b3ecb722497931c7f9ba70c93688..4be54bd7080d2eab3aa7d837d6768fd2e6f9ff28 100644 (file)
@@ -24,7 +24,7 @@ pub fn main() {
     assert_eq!(y_diaeresis as int, 0xff);
     assert_eq!(pi as int, 0x3a0);
 
-    assert_eq!(pi as int, '\u03a0' as int);
+    assert_eq!(pi as int, '\u{3a0}' as int);
     assert_eq!('\x0a' as int, '\n' as int);
 
     let bhutan: String = "འབྲུག་ཡུལ།".to_string();
@@ -33,11 +33,11 @@ pub fn main() {
     let austria: String = "Österreich".to_string();
 
     let bhutan_e: String =
-        "\u0f60\u0f56\u0fb2\u0f74\u0f42\u0f0b\u0f61\u0f74\u0f63\u0f0d".to_string();
-    let japan_e: String = "\u65e5\u672c".to_string();
+        "\u{f60}\u{f56}\u{fb2}\u{f74}\u{f42}\u{f0b}\u{f61}\u{f74}\u{f63}\u{f0d}".to_string();
+    let japan_e: String = "\u{65e5}\u{672c}".to_string();
     let uzbekistan_e: String =
-        "\u040e\u0437\u0431\u0435\u043a\u0438\u0441\u0442\u043e\u043d".to_string();
-    let austria_e: String = "\u00d6sterreich".to_string();
+        "\u{40e}\u{437}\u{431}\u{435}\u{43a}\u{438}\u{441}\u{442}\u{43e}\u{43d}".to_string();
+    let austria_e: String = "\u{d6}sterreich".to_string();
 
     let oo: char = 'Ö';
     assert_eq!(oo as int, 0xd6);
index 84f605eef57001f1a1a60b268e5f2781a5e420f9..c54b3b69c688053d8a22cbb1b52b9ca29f35ae69 100644 (file)
 
 pub fn main() {
     // Chars of 1, 2, 3, and 4 bytes
-    let chs: Vec<char> = vec!('e', 'é', '€', '\U00010000');
+    let chs: Vec<char> = vec!('e', 'é', '€', '\u{10000}');
     let s: String = chs.iter().cloned().collect();
     let schs: Vec<char> = s.chars().collect();
 
-    assert!(s.len() == 10_usize);
-    assert!(s.chars().count() == 4_usize);
-    assert!(schs.len() == 4_usize);
+    assert!(s.len() == 10);
+    assert!(s.chars().count() == 4);
+    assert!(schs.len() == 4);
     assert!(schs.iter().cloned().collect::<String>() == s);
-    assert!(s.char_at(0_usize) == 'e');
-    assert!(s.char_at(1_usize) == 'é');
+    assert!(s.char_at(0) == 'e');
+    assert!(s.char_at(1) == 'é');
 
     assert!((str::from_utf8(s.as_bytes()).is_ok()));
     // invalid prefix
-    assert!((!str::from_utf8(&[0x80_u8]).is_ok()));
+    assert!((!str::from_utf8(&[0x80]).is_ok()));
     // invalid 2 byte prefix
-    assert!((!str::from_utf8(&[0xc0_u8]).is_ok()));
-    assert!((!str::from_utf8(&[0xc0_u8, 0x10_u8]).is_ok()));
+    assert!((!str::from_utf8(&[0xc0]).is_ok()));
+    assert!((!str::from_utf8(&[0xc0, 0x10]).is_ok()));
     // invalid 3 byte prefix
-    assert!((!str::from_utf8(&[0xe0_u8]).is_ok()));
-    assert!((!str::from_utf8(&[0xe0_u8, 0x10_u8]).is_ok()));
-    assert!((!str::from_utf8(&[0xe0_u8, 0xff_u8, 0x10_u8]).is_ok()));
+    assert!((!str::from_utf8(&[0xe0]).is_ok()));
+    assert!((!str::from_utf8(&[0xe0, 0x10]).is_ok()));
+    assert!((!str::from_utf8(&[0xe0, 0xff, 0x10]).is_ok()));
     // invalid 4 byte prefix
-    assert!((!str::from_utf8(&[0xf0_u8]).is_ok()));
-    assert!((!str::from_utf8(&[0xf0_u8, 0x10_u8]).is_ok()));
-    assert!((!str::from_utf8(&[0xf0_u8, 0xff_u8, 0x10_u8]).is_ok()));
-    assert!((!str::from_utf8(&[0xf0_u8, 0xff_u8, 0xff_u8, 0x10_u8]).is_ok()));
+    assert!((!str::from_utf8(&[0xf0]).is_ok()));
+    assert!((!str::from_utf8(&[0xf0, 0x10]).is_ok()));
+    assert!((!str::from_utf8(&[0xf0, 0xff, 0x10]).is_ok()));
+    assert!((!str::from_utf8(&[0xf0, 0xff, 0xff, 0x10]).is_ok()));
 }
index 5a476ed9ee2f89958d02a0cbb6abd8537eace2d0..b3fff6977a54574ece93ec601327129eba1331de 100644 (file)
@@ -13,7 +13,6 @@
 use std::ffi::{self, CString};
 use libc::{c_char, c_int};
 
-// ignore-fast doesn't like extern crate
 
 extern {
     fn sprintf(s: *mut c_char, format: *const c_char, ...) -> c_int;
index 015baea5fb5fe5f71a19a45a4e7b1907c844f889..a0b3564d84e17f3d58373be729f334fd503939b6 100644 (file)
@@ -17,11 +17,11 @@ pub fn main() {
     assert_eq!(x[2], 3);
     assert_eq!(x[3], 4);
 
-    assert_eq!(size_of::<[u8; 4]>(), 4_usize);
+    assert_eq!(size_of::<[u8; 4]>(), 4);
 
     // FIXME #10183
     // FIXME #18069
     //if cfg!(target_pointer_width = "64") {
-    //    assert_eq!(size_of::<[u8; (1 << 32)]>(), (1_usize << 32));
+    //    assert_eq!(size_of::<[u8; (1 << 32)]>(), (1 << 32));
     //}
 }
index 08d39e58b7ce292c2b849b8c809a226a470dfc00..a6f4b8299cb6898284ffa9e784b610173aad9cb7 100644 (file)
@@ -53,7 +53,7 @@ fn drop(&mut self) {
 }
 
 pub fn main() {
-    assert!(MAX_LEN <= std::usize::BITS);
+    assert!(MAX_LEN <= std::usize::BITS as usize);
     // len can't go above 64.
     for len in 2..MAX_LEN {
         for _ in 0..REPEATS {
index baea1b8826a470214fcae45cadfac80ae7e217b3..20e42575b277f9e03cec4c6f916fc5d16e95da5b 100644 (file)
@@ -65,7 +65,7 @@ fn canttouchthis() -> uint {
     fn p() -> bool { true }
     let _a = (assert!((true)) == (assert!(p())));
     let _c = (assert!((p())) == ());
-    let _b: bool = (println!("{}", 0) == (return 0_usize));
+    let _b: bool = (println!("{}", 0) == (return 0));
 }
 
 fn angrydome() {
index 1fd223b0dd3f6bd8c8d8ffaa83bd6a59ee8d3370..67757d7efa837cdf35b9cfb57428e199d67c09ee 100644 (file)
@@ -55,7 +55,7 @@ fn foo2<T>(x: &T)
 }
 
 fn main() {
-    let x = 42u32;
+    let x = 42;
     foo1(&x);
     foo2(&x);
     unsafe {
index dea58c8e86fbb8cbc1e2f6708c48d2fb6c770f1b..b884adb7a6ec3e92d1ed1e10cbdfee7097672fab 100644 (file)
@@ -22,7 +22,7 @@ mod kernel32 {
 #[cfg(windows)]
 pub fn main() {
     unsafe {
-        let expected = 1234_usize;
+        let expected = 1234;
         kernel32::SetLastError(expected);
         let actual = kernel32::GetLastError();
         println!("actual = {}", actual);
index 86c1ae0f51fd9c51ee0350d24cf010024b03b214..b5b9d95d87f8c9701c3ad8ae77299d97b2abba74 100644 (file)
@@ -30,10 +30,10 @@ pub fn HeapAlloc(hHeap: HANDLE, dwFlags: DWORD, dwBytes: SIZE_T)
 #[cfg(windows)]
 pub fn main() {
     let heap = unsafe { kernel32::GetProcessHeap() };
-    let mem = unsafe { kernel32::HeapAlloc(heap, 0u32, 100u32) };
-    assert!(mem != 0_usize);
-    let res = unsafe { kernel32::HeapFree(heap, 0u32, mem) };
-    assert!(res != 0u8);
+    let mem = unsafe { kernel32::HeapAlloc(heap, 0, 100) };
+    assert!(mem != 0);
+    let res = unsafe { kernel32::HeapFree(heap, 0, mem) };
+    assert!(res != 0);
 }
 
 #[cfg(not(windows))]